Std exception c linux

C++ — Урок 011. Исключения

Что такое исключение? Это ситуация, которая не предусмотрена стандартным поведением программы. Например, попытка доступа к элементу в классе Vector (который мы разбирали в статье про классы ), который не существует. То есть происходит выход за пределы вектора. В данном случае можно воспользоваться исключениями, чтобы прервать выполнение программы. Это необходимо потому, что

  • Как правило в таких случаях, автор класса Vector не знает, как пользователь захочет использовать его класс, а также не знает в какой программе этот класс будет использоваться.
  • Пользователь класса Vector не может всегда контролировать правильность работы этого класса, поэтому ему нужно сообщить о том, что что-то пошло не так.

Для разрешения таких ситуация в C++ можно использовать технику исключений.

Рассмотрим, как написать вызов исключения в случае попытки доступа к элементу по индексу, который не существует в классе Vector.

Здесь применяется исключение out_of_range. Данное исключение определено в заголовочном файле .

Оператор throw передаёт контроль обработчику для исключений типа out_of_range в некоторой функции, которая прямо или косвенно вызывает Vector::operator[]() . Для того, чтобы обработать исключения необходимо воспользоваться блоком операторов try catch.

Инварианты

Также блоки try catch позволяют производить обработку нескольких различных исключений, что вносит инвариантность в работу механизма исключений C++.

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

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

  • Если в качестве аргумента size будет передано отрицательное значение
  • Если оператор new не сможет выделить память

length_error — это стандартный оператор исключений, поскольку библиотека std часто использует данные исключения при своей работе.

Обработка исключений будет выглядеть следующим образом:

Также можно выделить свои собственные исключения.

Виды исключений

Все исключения стандартной библиотеки наследуются от std::exception.

На данный момент существуют следующие виды исключений:

  • logic_error
    • invalid_argument
    • domain_error
    • length_error
    • out_of_range
    • future_error (C++11)
  • runtime_error
    • range_error
    • overflow_error
    • underflow_error
    • system_error (C++11)
      • ios_base::failure (начиная с C++11)
  • bad_typeid
  • bad_cast
  • bad_weak_ptr (C++11)
  • bad_function_call (C++11)
  • bad_alloc
    • bad_array_new_length (C++11)
  • bad_exception
  • ios_base::failure (до C++11)

std::logic_error

Исключение определено в заголовочном файле

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

Этот класс используется как основа для ошибок, которые могут быть определены только во время выполнения программы.

std::invalid_argument

Исключение определено в заголовочном файле

Наследован от std::logic_error. Определяет исключение, которое должно быть брошено в случае неправильного аргумента.

Например, на MSDN приведён пример, когда в объект класса bitset из стандартной библиотеки

В данном примере передаётся неправильная строка, внутри которой имеется символ ‘b’, который будет ошибочным.

std::domain_error

Исключение определено в заголовочном файле

Наследован от std::logic_error. Определяет исключение, которое должно быть брошено в случае если математическая функция не определена для того аргумента, который ей передаётся, например:

std::length_error

Исключение определено в заголовочном файле

Наследован от std::logic_error. Определяет исключение, которое должно быть броше в том случае, когда осуществляется попытка реализации превышения допустим пределов для объекта. Как это было показано для размера вектора в начале статьи.

Читайте также:  Windows 10 файл ответов пропустить

std::out_of_range

Исключение определено в заголовочном файле

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

std::future_error

Исключение определено в заголовочном файле

Наследован от std::logic_error. Данное исключение может быть выброшено в том случае, если не удалось выполнить функцию, которая работает в асинхронном режиме и зависит от библиотеки потоков. Это исключение несет код ошибки совместимый с std::error_code .

std::runtime_error

Исключение определено в заголовочном файле

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

std::range_error

Исключение определено в заголовочном файле

Исключение используется при ошибках при вычислении значений с плавающей запятой, когда компьютер не может обработать значение, поскольку оно является либо слишком большим, либо слишком маленьким. Если значение является значение интегрального типа, то должны использоваться исключения underflow_error или overflow_error .

std::overflow_error

Исключение определено в заголовочном файле

Исключение используется при ошибках при вычислении значений с плавающей запятой интегрального типа, когда число имеет слишком большое положительное значение, положительную бесконечность, при которой происходит потеря точности, т.е. результат настолько большой, что не может быть представлен числом в формате IEEE754.

std::underflow_error

Исключение определено в заголовочном файле

Исключение используется при ошибках при вычислении значений с плавающей запятой интегрального типа, при которой происходит потеря точности, т.е. результат настолько мал, что не может быть представлен числом в формате IEEE754.

std::system_error

Исключение определено в заголовочном файле

std::system_error — это тип исключения, которое вызывается различными функциями стандартной библиотеки (как правило, функции, которые взаимодействуют с операционной системой, например, конструктор std::thread ), при этом исключение имеет соответствующий std::error_code .

std::ios_base::failure

Исключение определено в заголовочном файле

Отвечает за исключения, которые выбрасываются при ошибках функций ввода вывода.

std::bad_typeid

Исключение определено в заголовочном файле

Исключение этого типа возникает, когда оператор typeid применяется к нулевому указателю полиморфного типа.

std::bad_cast

Исключение определено в заголовочном файле

Данное исключение возникает в том случае, когда производится попытка каста объекта в тот тип объекта, который не входит с ним отношения наследования.

std::bad_weak_ptr

Исключение определено в заголовочном файле

std::bad_weak_ptr – тип объекта, генерируемый в качестве исключения конструкторами std::shared_ptr , которые принимают std::weak_ptr в качестве аргумента, когда std::weak_ptr ссылается на уже удаленный объект.

std::bad_function_call

Исключение определено в заголовочном файле

Данное исключение генерируется в том случае, если был вызван метод std::function::operator() объекта std::function , который не получил объекта функции, то есть ему был передан в качестве инициализатора nullptr, например, а объект функции так и не был передан.

std::bad_alloc

Исключение определено в заголовочном файле

Вызывается в том случае, когда не удаётся выделить память.

std::bad_array_new_length

Исключение определено в заголовочном файле

Исключение вызывается в следующих случаях:

  1. Массив имеет отрицательный размер
  2. Общий размер нового массива превысил максимальное значение, определяемое реализацией
  3. Количество элементов инициализации превышает предлагаемое количество инициализирующих элементов

std::bad_exception

Исключение определено в заголовочном файле

std::bad_exception — это тип исключения в C++, которое выполняется в следующих ситуациях:

  1. Если нарушается динамическая спецификация исключений
  2. Если std::exception_ptr хранит копию пойманного исключения, и если конструктор копирования объекта исключения поймал current_exception, тогда генерируется исключение захваченных исключений.

Рекомендуем хостинг TIMEWEB

Рекомендуемые статьи по этой тематике

Источник

Creating new exception in C++

I have a C++ class and I am trying to run it in Ubuntu:

Читайте также:  Zabbix настройка активного агента windows

when I try to compile it, the compiler gives me this error:

Can anyone tell me what am I doing wrong? I tried changing the message variable to string or const string or const string& but it didn’t help.

Here is how I use the new exception that I created from main:

6 Answers 6

First, #pragma once is the wrong way to go about it, learn about header include guards. Related question on SO explains why using #pragma once is the wrong way to go about it. Wikipedia explains how to use include guards which serve the same purpose without any of the downsides.

Second, you are calling the constructor of std::exception with a parameter it does not know, in this case a pointer to a character array.

Would probably be what you want. For more information on exceptions, check out C++ FAQ Lite article on Exceptions and the exceptions article at cplusplus.com.

std::exception does not have a constructor that takes any kind of string, only a virtual what() method that returns the exception description.

You will have to store the string yourself and return it from there.

My advice would be:

  1. Inherit from std::runtime_error . As advised by X-Istence above. It is conceptually a runtime error, and also the std::runtime_error constructor accepts a std::string as argument describing what happened.
  2. About your catching the exception. I’d use catch(WrongParameterException const& e) (note the const reference) instead of catch(WrongParameterException e) , because first, the exception is normally constant in your case, and, also, using the reference, you catch any subclass of WrongParameterException in case your code evolves with some more refined exception handling.

std::exception’s constructor doesn’t take a string argument. You’re trying to give it one, which is what causes the compile error.

You need to store your string, which would be better to handle as a std::string rather than a raw pointer, and return it from the what() method.

Looking at the declaration of the exception class in MS VS2K5, the constructor you want is:

so try changing your constructor to:

and see if that helps. Otherwise, store the pointer in your own class and implement all the relevant methods.

A simple solution is to design your exception diferently. Here is a simple example:

Then you can simply use your exception message as you please. This is because Exception does not have a contructor that excepts a String, so you have to stlre it on your own.

Linked

Hot Network Questions

Subscribe to RSS

To subscribe to this RSS feed, copy and paste this URL into your RSS reader.

site design / logo © 2021 Stack Exchange Inc; user contributions licensed under cc by-sa. rev 2021.10.8.40416

By clicking “Accept all cookies”, you agree Stack Exchange can store cookies on your device and disclose information in accordance with our Cookie Policy.

Источник

How to throw a C++ exception

I have a very poor understanding of exception handling(i.e., how to customize throw, try, catch statements for my own purposes).

For example, I have defined a function as follows: int compare(int a, int b)

I’d like the function to throw an exception with some message when either a or b is negative.

How should I approach this in the definition of the function?

Читайте также:  Mac os mavericks vmware amd

5 Answers 5

The Standard Library comes with a nice collection of built-in exception objects you can throw. Keep in mind that you should always throw by value and catch by reference:

You can have multiple catch() statements after each try, so you can handle different exception types separately if you want.

You can also re-throw exceptions:

And to catch exceptions regardless of type:

Though this question is rather old and has already been answered, I just want to add a note on how to do proper exception handling in C++11:

Use std::nested_exception and std::throw_with_nested

It is described on StackOverflow here and here, how you can get a backtrace on your exceptions inside your code without need for a debugger or cumbersome logging, by simply writing a proper exception handler which will rethrow nested exceptions.

Since you can do this with any derived exception class, you can add a lot of information to such a backtrace! You may also take a look at my MWE on GitHub, where a backtrace would look something like this:

Just add throw where needed, and try block to the caller that handles the error. By convention you should only throw things that derive from std::exception , so include first.

You could define a message to throw when a certain error occurs:

or you could define it like this:

Typically, you would have a try . catch block like this:

Adding to this answer, as it doesn’t seem advantageous to create another answer for this Q&A at this time.

In the case where you create your own custom exception, that derives from std::exception , when you catch «all possible» exceptions types, you should always start the catch clauses with the «most derived» exception type that may be caught. See the example (of what NOT to do):

NOTE:

The proper order should be vice-versa, i.e.- first you catch (const MyException& e) which is followed by catch (const std::exception& e) .

As you can see, when you run the program as is, the first catch clause will be executed (which is probably what you did NOT want in the first place).

Even though the type caught in the first catch clause is of type std::exception , the «proper» version of what() will be called — cause it is caught by reference (change at least the caught argument std::exception type to be by value — and you will experience the «object slicing» phenomena in action).

In case that the «some code due to the fact that XXX exception was thrown. » does important stuff WITH RESPECT to the exception type, there is misbehavior of your code here.

This is also relevant if the caught objects were «normal» object like: class Base<>; and class Derived : public Base <> .

g++ 7.3.0 on Ubuntu 18.04.1 produces a warning that indicates the mentioned issue:

In function ‘void illustrateDerivedExceptionCatch()’: item12Linux.cpp:48:2: warning: exception of type ‘MyException’ will be caught catch(const MyException& e) ^

item12Linux.cpp:43:2: warning: by earlier handler for ‘std::exception’ catch (const exception& e) ^

Again, I will say, that this answer is only to ADD to the other answers described here (I thought this point is worth mentioning, yet could not depict it within a comment).

Источник

Оцените статью