boost之跨平台 错误处理

  • Post author:
  • Post category:其他



system

C++中处理错误的最佳方式是使用异常,但操作系统和许多底层AP工不具有这个能力,它们一般使用更通用也更难以操作的错误代码来表示出错的原因,不同的操作系统的错误代码通常不是兼容的,这给编写跨平台的程序带来了很大的麻烦。

system库使用轻量级的对象封装了操作系统底层的错误代码和错误信息,使调用操作系统功能的程序可以被很容易地移植到其他操作系统。它作为基础部件被chronovfilesystem和 asio等库调用,并且被接受为c++标准(C++11.19.5)。

jamfile 指定 lib

lib boost_system;

system 库位于名字空间boost : :system,需要包含头文件<boost/system/error_code.hpp>(注意与C++标准的名字<system_error>不同),即:

#define BOOST_ERROR_CODE_HEADER_ONLY      //无需编译即可使用system库

#include <boost/system/error_code. hpp>

using namespace boost: :system;

错误值

system库在名字空间boost : :system: :errc下定义了一个很大的枚举类errc_t它定义了通用的可移植的错误代码,我们应当尽量使用它来标记错误原因:

namespace errc
{
    enum errc{
        success=0,
        address_family_not_supported,
        address_in_use,
        address_not_available,
        already_connected,
        ...

    }
}

system库还在头文件<boost/system/linux_error.hpp>和<boost/system/windows_error.hpp>里分别定义了Linux和windows操作系统特定的错误值枚举,分别位于名字空间boost::system : : linux_error和 boost ::system : : windows_error。如果针对这两个操作系统做特定编程,则可以包含这两个头文件。

错误类别

system库的核心类是error_category、error_code和error_condition。


error category

是一个抽象基类,用于标识错误代码的类别,它的类摘要如下:

class error_category:public noncopyable
{
    public:
    virtual const char* name() const BOOST_SYSTEM_NOEXCEPT=0;
    virtual string message(error_code::value_type ev)const =0;
    virtual error_condition default_error_condition(int ev)const;
    virtual bool equiavlent(int code,const error_condition&condition);
    virtual bool equiavlent(const error_code&code,int condition);
}

成员函数name( )可以获得类别的名称;

message()可以获得错误代码ev对应的描述信息;

default_error_condition ()是一个工厂方法,它由错误代码 ev产生一个error_condition对象;

equivalent()用于比较两个错误代码是否相等。

error_category 不能直接使用,必须使用继承的方式生成它的子类。system库在匿名名字空间里预定义了两个子类system_error_category和generic_error_category,用于表示系统错误和通用的可移植错误,可以用位于名字空间boost ::system的自由函数system_category()和 generic_category ()间接访问。

class my_category:public error_category
{
    public:
    virtual const char* name()const BOOST_SYSTEM_NOEXCEPT
    {return "myapp_category";}
    virtual std::string message(int ev)const{
       std::string msg;
       switch (ev)
       {
       case 0:
       msg="ok"/* constant-expression */:
        /* code */
        break;
       
       default:
       msg="some error";
        break;
       }
       return msg;

    }
};

错误代码

error_code和 error_condition都用于表示错误代码,但error_code更接近操作系统和底层API,而error_condition则更偏重于可移植。两者的声明很类似,但

error_code 多了一个 default_error_condition ()的方法,可以把 error_code 转换成error_condition。

class error_code
{
    public:
    error_code();
    error_code(int val,const error_category&cat);
    void assign(int val,const error_category& cat);
    void clear();
    int value() const;
    const error_category&category()const;
    error_condition default_error_condition()const;
    std::string message()const;
    ...

};

error_code和 error_condition都可以从一个整数错误值或者errc_t枚举构造,并同时指定所属的错误类别。如果无参构造,那么错误值将会是0(无错误)。

error_code对象内部的值可以用value ()获得,获得错误描述要使用message ( ) ,它将调用error_category的message ()返回描述信息。函数category ()可以返回错误代码所属的类别,因此message ()相当于:

ec.category().message(ec.value)

不同的错误类别决定了error_code 的含义,相同的错误代码如果属于不同的类别,那么将具有不同的含义。

void error_category1()
{
      my_category my_cat;
      error_code ec(10,my_cat);
      std::cout<<ec.value()<<ec.message()<<std::endl;
      ec=error_code(10,system_category());
      std::cout<<ec.value()<<ec.message()<<std::endl;

}
//
10 some error
10 No child processes

错误异常

system库还提供一个异常类system_error,它是 std: :runtime_error的子类,是对error_code的一个适配,可以把error_code应用到C++的异常处理机制之中。

system_error位于名字空间boost : : system,使用时需要另外包含头文件<boost/system/ system_error.hpp>,即;

#include <boost/ system/ system_error.hpp>

using namespace boost: :system;

示范用法:

try{
throw system_error(
error_code(5,system_category()));

}
catch(system_error&e)
{
cout<<e.what()
}



版权声明:本文为qq_62309585原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。