2010-10-23 2 views
3

Сначала я нашел в cplusplus.com следующей цитаты:Поймать с несколькими параметрами

Формат улова похож на регулярную функцию, которая всегда имеет по крайней мере один параметр.

Но я попытался это:

try 
{ 
    int kk3,k4; 
    kk3=3; 
    k4=2; 
    throw (kk3,"hello"); 
} 
catch (int param) 
{ 
    cout << "int exception"<<param<<endl;  
} 
catch (int param,string s) 
{ 
    cout<<param<<s; 
} 
catch (char param) 
{ 
    cout << "char exception"; 
} 
catch (...) 
{ 
    cout << "default exception"; 
} 

Компилятор не жалуется на бросок с фигурными скобками и несколькими аргументами. Но на самом деле он жалуется на улов с несколькими параметрами, несмотря на то, что говорится в ссылке. Я смущен. try и catch допускают эту множественность или нет? И что, если бы я хотел создать исключение, которое включает более одной переменной с одним типом или без него.

+0

Читайте на оператора запятой. Вы не бросаете '(kk3," hello ")', вы бросаете '" hello "'. – delnan

+0

, так что это только один аргумент в обоих? –

ответ

10

(kk3, "hello") - выражение для запятой. Выражение для запятой оценивает все свои аргументы слева направо, а результат - самый правый аргумент. Таким образом, в выражении

int i = (1,3,4); 

я становлюсь 4.

Если вы действительно хотите бросить оба из них (по некоторым причинам) вы могли бы бросить, как этот

throw std::make_pair(kk3, std::string("hello")); 

и поймать, как это:

catch(std::pair<int, std::string>& exc) 
{ 
} 

И оговорка задвижка имеет ровно на е аргумент или

... 

НТН

+0

спасибо большое :), что было очень полезно. –

2

В дополнение к другим ответам, я бы порекомендовал вам создать свой собственный класс исключений, который может содержать более чем одну часть информации. Он предпочтительно должен быть получен от std::exception. Если вы сделаете это стратегией, вы всегда можете поймать свои исключения с помощью одного catch(std::exception&) (полезно, если вы хотите только освободить какой-то ресурс, а затем перестроить исключение - вам не нужно иметь обработчики уловов gazilion для каждого исключения типа вы бросаете).

Пример:

class MyException : public std::exception { 
    int x; 
    const char* y; 

public: 
    MyException(const char* msg, int x_, const char* y_) 
     : std::exception(msg) 
     , x(x_) 
     , y(y_) { 
    } 

    int GetX() const { return x; } 
    const char* GetY() const { return y; } 
}; 

... 

try { 
    throw MyException("Shit just hit the fan...", 1234, "Informational string"); 
} catch(MyException& ex) { 
    LogAndShowMessage(ex.what()); 
    DoSomething(ex.GetX(), ex.GetY()); 
} 
+2

"полезно, если вы хотите только освободить какой-то ресурс, а затем повторно создать исключение". В этом случае вам нужно просто сделать catch (...) {/ * ... */throw; } '. Кроме того, 'std :: exception' не имеет конструктора, который принимает аргумент. (Хотя я знаю, что VS имеет такой же вариант.) – GManNickG

+0

Проблема с catch (...) заключается в том, что она (по крайней мере на платформе Windows) также ловушки структурированных исключений, выпущенных ОС, когда есть плохой доступ к памяти или что у вас есть , Я был поражен, когда часть моего кода не разбила программу. У меня был catch (...), окружающий цепочку вызовов, и он захватил доступ к указателю NULL. Я немного опасаюсь возиться с любым утверждением, если состояние процесса находится в неизвестном состоянии. –

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