В чем разница между try / catch и mfc try / catch?

Я занимаюсь рефакторингом устаревшего кода C++ MFC и наткнулся на эту конструкцию:

TRY
{
    // do some stuff
}
CATCH
{
    // do some other stuff
}
END_CATCH

Мне это кажется довольно необычным, и я пытаюсь понять, в чем преимущество использования TRY/CATCH в пользу try/catch.

Я вижу, что TRY создает экземпляр AFX_EXCEPTION_LINK, и я не совсем понимаю цель этого. Мои навыки поиска в Google с треском провалились.

C++ try / catch имеет источник DOS, и его поддержка по умолчанию отключена, например, в cl / link, в то время как обработчики mfc могут работать там.

Алексей Неудачин 26.10.2018 10:54

@ Але: MS DOS был введен в 1981 году. C++ впервые появился в 1985 году, с исключениями, которые вводились только после 1990 года. То, что вы говорите, неверно. Основными языками программирования для DOS были C и Pascal.

IInspectable 26.10.2018 16:40
5
2
429
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

MFC (и его макросы обработка исключений) появились раньше спецификации языка C++ 98. Макросы пытаются абстрагироваться от общего шаблонного кода при использовании исключений в MFC. Шаблонный код необходим из-за проектного решения, что исключения в MFC динамически распределяются 1 и должны быть удалены вручную.

Шаги, необходимые для замены макросов обработки исключений MFC обработкой исключений C++, описаны в разделе Исключения: преобразование из макросов исключений MFC:

To convert code using macros to use the C++ exception-handling keywords

  1. Locate all occurrences of the MFC macros TRY, CATCH, AND_CATCH, END_CATCH, THROW, and THROW_LAST.

  2. Replace or delete all occurrences of the following macros:

    • TRY (Replace it with try)
    • CATCH (Replace it with catch)
    • AND_CATCH (Replace it with catch)
    • END_CATCH (Delete it)
    • THROW (Replace it with throw)
    • THROW_LAST (Replace it with throw)
  3. Modify the macro arguments so that they form valid exception declarations.

    For example, change

    CATCH(CException, e)
    

    to

    catch(CException* e)
    
  4. Modify the code in the catch blocks so that it deletes exception objects as necessary. For more information, see the article Exceptions: Catching and Deleting Exceptions.

Here is an example of exception-handling code using MFC exception macros. Note that because the code in the following example uses the macros, the exception e is deleted automatically:

TRY
{
   // Do something to throw an exception.
   AfxThrowUserException();
}
CATCH(CException, e)
{
   if (m_bPassExceptionsUp)
      THROW_LAST();
   if (m_bReturnFromThisFunction)
      return;
   // Not necessary to delete the exception e.
}
END_CATCH

The code in the next example uses the C++ exception keywords, so the exception must be explicitly deleted:

try
{
   // Do something to throw an exception.
   AfxThrowUserException();
}
catch(CException* e)
{
   if (m_bPassExceptionsUp)
      throw;
   if (m_bThrowDifferentException)
   {
      e->Delete();
      throw new CMyOtherException;
   }
   if (m_bReturnFromThisFunction)
   {
      e->Delete();
      return;
   }
   e->Delete();
}

Преобразование почти механическое, если вы не забываете вручную удалять исключения MFC, вызывая CException :: Удалить.


1Это контрастирует с сегодняшним соглашением об обработке исключений C++: выбрасывать по значению, ловить по (константной) ссылке.

Другие вопросы по теме