2015-04-10 1 views
1

Я написал следующий класс исключений:C++ Обработка исключений и Enum Scoping

class generic_exception : public std::exception 
{ 

    public: 

    generic_exception(std::string where, int err_code , bool fatal) 
    : where_(where) , errcode_(err_code) ,fatal_(fatal) {} 

     inline int get_errcode() 
     { 
     return errcode_; 
     } 

     inline bool is_fatal() 
     { 
     return (fatal_ == true ? true : false); 
     } 

     inline std::string get_where() 
     { 
     return where_; 
     } 

    ~generic_exception() throw() { } 

    private: 

    std::string where_; 
    int errcode_; 
    bool fatal_; 

}; 

я использовал это для обработки ошибок, не создавая класс один исключений для каждого типа ошибки. Все значения err_code являются важными значениями перечислителя (все из них определены в отдельных классах, требующих проверки ошибок), используемых в качестве кодов ошибок.

несколько примеров класс:

class A 
{ 
    enum one{a,b,c} 
}; 

class B 
{ 
    enum two{d,e,f} 
}; 

попытка поймать пример:

try 
    { 
     //something 
     throw generic_exception("where" , one::a , true); 
     throw generic_exception("where" , two::a , true); 

    } 
    catch(generic_exception e) 
    { 
     switch(e.get_errcode()) 
     { 
     case one::a: 
      break; 
     case two::b: 
      break; 
     } 
    } 
    } 

У меня возникают проблемы, когда два значения из разных перечислений, но то же целое значение появляется в том же переключатель сазе. Когда это происходит, как в приведенном выше примере, компилятор печатает «ошибку: дублирующее значение случая». Я предполагаю, что причиной этой ошибки является , относящаяся к целочисленной «природе» двух семейств. Как я могу решить эту проблему? Я обязан изменить эту «общую схему исключения» на полиморфную схему (один класс исключений для одного типа ошибки)?

+0

Если эти коды ошибок должны быть уникальными, вам нужно будет использовать одно перечисление для этих кодов ошибок или вам нужно будет сделать трюк, чтобы второе перечисление начиналось с последнего значения вашего первого перечисления, увеличенного на 1. –

ответ

1

Вы можете либо:

1) Использование глобального перечисление:

enum ErrorCode 
{ 
    A_one, 
    A_two, 
    A_three, 
    //... 

    B_one, 
    B_two, 
    //... 
}; 

2) Или использовать счетчики подсчет:

class A 
{ 
public: 
    enum 
    { 
     Err_one, 
     Err_two, 
     Err_three, 
     //... 

     Last_error 
    }; 
}; 

class B 
{ 
public: 
    enum 
    { 
     Err_one = A::Last_error, 
     Err_two, 
     Err_three, 
     //... 

     Last_error 
    }; 
}; 

Trick с Last_error приятно, потому что вы можете определить много перечислений таким образом, и если вы добавите/удалите некоторые enu merators, ни один из них не требует обновления. Если вы хотите избежать определения дополнительных счетчиков, вы должны назначить первому счету значение последнего перечислителя в предыдущем перечислении, увеличенное на 1.

Но обратите внимание, что в этом случае даже небольшое изменение перечисления, заданное в A, может потребовать обновления перечисления определенный в классе B (потому что другой перечислитель может стать последним после изменения).

Смежные вопросы