Время жизни брошенного объекта, пойманного по ссылке - PullRequest
3 голосов
/ 23 января 2010

Стандарт C ++, пункт 15.1.4, говорит:

Память для временной копии создаваемого исключения распределяется неопределенным образом, за исключением случаев, указанных в 3.7.3.1. Временное состояние сохраняется до тех пор, пока для этого исключения выполняется обработчик.

Мне интересно, почему этот код падает (я знаю, что это не лучшая практика):

class magicException
{
private:
    char* m_message;

public:
    magicException(const char* message)
    {
        m_message = new char[strlen(message) + 1];
        strcpy(m_message, message);
    }

    ~magicException()
    {
        cout << "Destructor called." << endl;
        delete[] m_message;
    }

    char* getMessage()
    {
        return m_message;
    }
};

void someFunction()
{
    throw magicException("Bang!");
}

int main(int argc, char * argv[])
{
    try
    {
        someFunction();
    }
    catch (magicException& ex)
    {
        cout << ex.getMessage() << endl;
    }

    return 0;
}

В частности, деструктор брошенного объекта magicException вызывается перед блоком catch. Однако если я добавлю конструктор копирования в свой класс:

magicException(const magicException& other)
{
    cout << "Copy constructor called." << endl;
    m_message = new char[strlen(other.m_message) + 1];
    strcpy(m_message, other.m_message);
}

Затем код работает, деструктор вызывается в ожидаемом месте (конец блока catch), но, что интересно, конструктор копирования по-прежнему не вызывается. Это оптимизировано компилятором (Visual C ++ 2008 с отключенной оптимизацией), или я что-то упустил?

1 Ответ

4 голосов
/ 23 января 2010

В частности, деструктор брошенный объект magicException получает вызывается перед блоком catch.

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

...