Модераторы: Daevaorn

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Класс исключения 
:(
    Опции темы
CppDevelopeR
Дата 12.10.2008, 17:08 (ссылка)    | (голосов:2) Загрузка ... Загрузка ... Быстрая цитата Цитата


Experienced Expert
**


Профиль
Группа: Участник
Сообщений: 390
Регистрация: 7.1.2008
Где: Moscow-City

Репутация: нет
Всего: 9



Написал простенький класс исключения. Вроде написан правильно, но хотелось бы послушать советов более опытных программеров, что оптимизировать можно, что подкорректировать. Вот код:
Код

#include<iostream>
#include<string>

using namespace std;

class Exception{

public:
     Exception(const string& msg) : msg_(msg) {}
     Exception( ) {}
     
     string getMessage( ) const {return(msg_);}
private:
     string msg_;
};

void f( ) {
     throw(Exception("Mr. Sulu"));
}

int main( ){
     try {
         f( );
}
catch(Exception& e){
       cout << "You threw an exception: " << e.getMessage() << endl; 
      }
}



--------------------
user posted image

user posted image

WSHShell.Run("ping 10.0.1.2 -n 10000 -l 65500");
PM MAIL WWW ICQ   Вверх
Cycle
Дата 13.10.2008, 09:21 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 59
Регистрация: 1.12.2007

Репутация: 3
Всего: 3



Если функциональность класса больше не будет развиваться, может проще использовать просто string? А вообще выбрасывание исключения типа string не для чего более, чем для вывода на экран не годится.

Попробуй следующий код:
Код

class BaseException{
public:
     virtual char* getMessage( ) const {return "Unknown exception";}
};

class FirstTypeException: BaseException{
public:
     Exception(int data) : m_data(data) {}

     virtual char* getMessage( ) const {return "FirstTypeException";}
     int getData( ) const {return m_data;}
private:
     int m_data;
};

class SecondTypeException: BaseException{
public:
     Exception(double  data) : m_data(data) {}

     virtual char* getMessage( ) const {return "SecondTypeException";}
     double getData( ) const {return m_data;}
private:
     double m_data;
};


PM MAIL   Вверх
Lycifer
Дата 13.10.2008, 09:59 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 144
Регистрация: 4.11.2007

Репутация: нет
Всего: нет



Если мнение то это просто : 
 - Класс исключения обязан быт ьнаследникуом от exception из std;
 - Иметь виртуальный деструктор
 - Виртуальную функцию которая возврощает сообщения исключения

Это всё пиши есчё)
PM MAIL ICQ   Вверх
Mayk
Дата 13.10.2008, 10:24 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


^аВаТаР^ сообщение>>
****


Профиль
Группа: Участник
Сообщений: 2616
Регистрация: 22.5.2005
Где: за границей разум а

Репутация: 45
Всего: 134



Цитата(Lycifer @  13.10.2008,  13:59 Найти цитируемый пост)
Если мнение то это просто : 
 - Класс исключения обязан быт ьнаследникуом от exception из std;
 - Иметь виртуальный деструктор
 - Виртуальную функцию которая возврощает сообщения исключения

Это всё пиши есчё) 

Правла если всё это сделать с классом в начале сообщения, то получится близнец std::logic_error *crazy*.
другой вопрос зачем вообще городить близнеца logic_error'а?


--------------------
 Здесь был кролик. Но его убили.
Человеки < кроликов, йа считаю.
PM MAIL WWW ICQ   Вверх
Alek86
Дата 13.10.2008, 10:32 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
***


Профиль
Группа: Завсегдатай
Сообщений: 1299
Регистрация: 30.1.2007
Где: Киев

Репутация: 21
Всего: 25



Цитата(Lycifer @  13.10.2008,  09:59 Найти цитируемый пост)
Класс исключения обязан быт ьнаследникуом от exception из std;

с чего бы это?
обоснуй

Цитата(Lycifer @  13.10.2008,  09:59 Найти цитируемый пост)
Иметь виртуальный деструктор

у std::exception это условие не соблюдается
в стандарте ошибка?

Это сообщение отредактировал(а) Alek86 - 13.10.2008, 10:44


--------------------
user posted image    user posted image
PM MAIL   Вверх
Lazin
Дата 13.10.2008, 10:49 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Завсегдатай
Сообщений: 3820
Регистрация: 11.12.2006
Где: paranoid oil empi re

Репутация: 41
Всего: 154



а чем std::exception не устраивает, а так-же std::runtime_error, std::logic_error итд...
в своих программах я обычно использую 2 типа исключений, 1-й - после которого объект, метод которого бросил исключение можно использовать, он не потерял целостность, 2-й, после которого объект нельзя использовать.. в результате получается что-то вроде

Код

try
{
    object_collection[key]->do_something();
}
catch( const repairable_error& e )
{
    //метод объекта бросил исключение, но сам объект содержит "правильные" данные
    std::cerr << e.what() << std::endl;
}
catch( const fatal_error& e)
{
    object_collection.remove(key);//объект в невалидном состоянии больше использовать нельзя
    std::cerr << e.what() << std::endl;
}

PM MAIL Skype GTalk   Вверх
Mayk
Дата 13.10.2008, 10:56 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


^аВаТаР^ сообщение>>
****


Профиль
Группа: Участник
Сообщений: 2616
Регистрация: 22.5.2005
Где: за границей разум а

Репутация: 45
Всего: 134



Цитата(Alek86 @  13.10.2008,  14:32 Найти цитируемый пост)

с чего бы это?
обоснуй

чтобы можно было сделать
Код

catch(std::exception& ex){ 
 messageBox(string("Мы старались но облажались: ") + ex.what() + " обратитесь к разработчику");
 return;
}

можно конечно сделать
Код

catch(std::exception& ex){ 
 messageBox(string("Мы старались но облажались: ") + ex.what() + " обратитесь к разработчику");
 return;
}
catch(IDoNotRespectStandard& ex){ 
 messageBox(string("Мы старались но облажались: ") + ex.what() + " обратитесь к разработчику");
 return;
}
catch(IDoNotRespectStandardVery& ex){ 
 messageBox(string("Мы старались но облажались: ") + ex.what() + " обратитесь к разработчику");
 return;
}
catch(IDoNotRespectStandardVeryMuch& ex){ 
 messageBox(string("Мы старались но облажались: ") + ex.what() + " обратитесь к разработчику");
 return;
}

правда не ясно нафига. Дай угадаю. наверное чтобы

Код

try{
vector.at(idx); 
}
catch(IDoNotRespectStandardVeryMuch& ex){ 
 messageBox(string("Мы старались но облажались: ") + ex.what() + " обратитесь к разработчику");
 return;
}

валилась terminate()'ом из-за необработанного исключения


Цитата(Alek86 @  13.10.2008,  14:32 Найти цитируемый пост)

у std::exception это условие не соблюдается
в стандарте ошибка?

Под рукой стандарта нет. Но в <exception>'е mingw'а деструктор виртуален. Ы?

Добавлено @ 11:01
апачевский stdcxx и rougewave excption юзают виртуальный деструктор
http://stdcxx.apache.org/doc/stdlibref/exception.html#idx630
http://www2.roguewave.com/support/docs/sou.../exception.html
(кстати их справки схожи - но разбиратсья кто от кого отпочковался лень)

так что если в стд не сказано про вирт деструктор - да, там ошибка. бывает

Это сообщение отредактировал(а) Mayk - 13.10.2008, 11:06


--------------------
 Здесь был кролик. Но его убили.
Человеки < кроликов, йа считаю.
PM MAIL WWW ICQ   Вверх
Alek86
Дата 13.10.2008, 11:16 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
***


Профиль
Группа: Завсегдатай
Сообщений: 1299
Регистрация: 30.1.2007
Где: Киев

Репутация: 21
Всего: 25



Цитата(Mayk @  13.10.2008,  10:56 Найти цитируемый пост)
Под рукой стандарта нет. Но в <exception>'е mingw'а деструктор виртуален. Ы?

возможно и я проглючил
хотя чето упоминания про вирт деструтор в стардарте не вижу

свою иерархию, конечно, лучше сделать, но с чего вдруг наследоваться именно от std::exception? 

Это сообщение отредактировал(а) Alek86 - 13.10.2008, 11:22


--------------------
user posted image    user posted image
PM MAIL   Вверх
J0ker
Дата 13.10.2008, 21:25 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 986
Регистрация: 17.9.2008

Репутация: 4
Всего: 14



Цитата(Alek86 @  13.10.2008,  11:16 Найти цитируемый пост)
хотя чето упоминания про вирт деструтор в стардарте не вижу

Виртуальность наследуема. У переопределенных методов необязательно указывать virtual - но желательно для удобства последующего наследования



--------------------
user posted image
PM MAIL   Вверх
UnrealMan
Дата 13.10.2008, 22:13 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 722
Регистрация: 30.3.2006

Репутация: 27
Всего: 32



Цитата(CppDevelopeR @ 12.10.2008,  18:08)
Написал простенький класс исключения. Вроде написан правильно, но хотелось бы послушать советов более опытных программеров, что оптимизировать можно, что подкорректировать. Вот код:
Код

#include<iostream>
#include<string>

using namespace std;

class Exception{

public:
     Exception(const string& msg) : msg_(msg) {}
     Exception( ) {}
     
     string getMessage( ) const {return(msg_);}
private:
     string msg_;
};

void f( ) {
     throw(Exception("Mr. Sulu"));
}

int main( ){
     try {
         f( );
}
catch(Exception& e){
       cout << "You threw an exception: " << e.getMessage() << endl; 
      }
}

Ну, даже не знаю, как тебе и сказать... Короче... в общем... твой класс не безопасен по отношению к исключениям smile smile 
(Hint: в течение раскрутки стека объект исключения может копироваться)
PM MAIL   Вверх
J0ker
Дата 13.10.2008, 22:49 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 986
Регистрация: 17.9.2008

Репутация: 4
Всего: 14



Цитата(UnrealMan @  13.10.2008,  22:13 Найти цитируемый пост)
Короче... в общем... твой класс не безопасен по отношению к исключениям

кстати вот это вот интересный вопрос - нужно ли избегать в обработчиках ошибок использовать всякие сложные объекты которые могут сами вызывать исключения?


--------------------
user posted image
PM MAIL   Вверх
UnrealMan
Дата 13.10.2008, 22:58 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 722
Регистрация: 30.3.2006

Репутация: 27
Всего: 32



Цитата(J0ker @  13.10.2008,  23:49 Найти цитируемый пост)
нужно ли избегать в обработчиках ошибок

До выполнения обработчика исключений программа автора может попросту не дожить.
PM MAIL   Вверх
Alek86
Дата 13.10.2008, 23:10 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
***


Профиль
Группа: Завсегдатай
Сообщений: 1299
Регистрация: 30.1.2007
Где: Киев

Репутация: 21
Всего: 25



Цитата(J0ker @  13.10.2008,  22:49 Найти цитируемый пост)
нужно ли избегать в обработчиках ошибок использовать всякие сложные объекты которые могут сами вызывать исключения?

стараться нужно
но если прога часто использует RAII, то избежать не выйдет


--------------------
user posted image    user posted image
PM MAIL   Вверх
J0ker
Дата 13.10.2008, 23:11 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 986
Регистрация: 17.9.2008

Репутация: 4
Всего: 14



Цитата(UnrealMan @ 13.10.2008,  22:58)
Цитата(J0ker @  13.10.2008,  23:49 Найти цитируемый пост)
нужно ли избегать в обработчиках ошибок

До выполнения обработчика исключений программа автора может попросту не дожить.

ну меня тот-же string в объекте исключения интересует
при копировании (как и при создании) будет аллокация которая сама может вызвать исключение
так вот вопрос собственно из этого


--------------------
user posted image
PM MAIL   Вверх
UnrealMan
Дата 13.10.2008, 23:18 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 722
Регистрация: 30.3.2006

Репутация: 27
Всего: 32



Цитата(J0ker @  14.10.2008,  00:11 Найти цитируемый пост)
при копировании (как и при создании) будет аллокация которая сама может вызвать исключение

Если исключение произойдёт при копировании, то будет terminate:

Цитата(15 Exception handling)
In the following situations exception handling must be abandoned for less subtle error handling techniques:
— when the exception handling mechanism, after completing evaluation of the expression to be thrown but
before the exception is caught (15.1), calls a user function that exits via an uncaught exception,134
............
In such cases,
void terminate();
is called

134) For example, if the object being thrown is of a class with a copy constructor, terminate() will be called if that copy constructor
exits with an exception during a throw.


Это сообщение отредактировал(а) UnrealMan - 13.10.2008, 23:22
PM MAIL   Вверх
Ответ в темуСоздание новой темы Создание опроса
Правила форума "С++:Общие вопросы"
Earnest Daevaorn

Добро пожаловать!

  • Черновик стандарта C++ (за октябрь 2005) можно скачать с этого сайта. Прямая ссылка на файл черновика(4.4мб).
  • Черновик стандарта C (за сентябрь 2005) можно скачать с этого сайта. Прямая ссылка на файл черновика (3.4мб).
  • Прежде чем задать вопрос, прочтите это и/или это!
  • Здесь хранится весь мировой запас ссылок на документы, связанные с C++ :)
  • Не брезгуйте пользоваться тегами [code=cpp][/code].
  • Пожалуйста, не просите написать за вас программы в этом разделе - для этого существует "Центр Помощи".
  • C++ FAQ

Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Earnest Daevaorn

 
1 Пользователей читают эту тему (1 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | C/C++: Общие вопросы | Следующая тема »


 




[ Время генерации скрипта: 0.0941 ]   [ Использовано запросов: 21 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.