Sdílet prostřednictvím


Výjimky: Použití výjimek v makrech MFC a jazyce C++

Tento článek popisuje aspekty psaní kódu, který používá makra zpracování výjimek MFC i klíčová slova zpracování výjimek jazyka C++.

Tento článek se zabývá následujícími tématy:

Kombinování klíčových slov výjimek a maker

Makra výjimek MFC a klíčová slova výjimek jazyka C++ můžete kombinovat ve stejném programu. Makra MFC s klíčovými slovy výjimek jazyka C++ však nelze kombinovat ve stejném bloku, protože makra odstraňují objekty výjimek automaticky, když přejdou mimo rozsah, zatímco kód využívající klíčová slova zpracování výjimek ne. Další informace najdete v článku Výjimky: Zachytávání a odstraňování výjimek.

Hlavním rozdílem mezi makry a klíčovými slovy je, že makra "automaticky" odstraní zachycenou výjimku, když výjimka zmizí z oboru. Kód využívající klíčová slova ne; Výjimky zachycené v bloku catch musí být explicitně odstraněny. Kombinování maker a klíčových slov výjimek jazyka C++ může způsobit nevracení paměti, pokud objekt výjimky není odstraněn, nebo poškození haldy při odstranění výjimky dvakrát.

Následující kód například zneplatní ukazatel výjimky:

TRY
{
   TRY
   {
   // Do something to throw an exception.
   AfxThrowUserException();
}
CATCH(CException, e)  // The "inner" catch block
{
   throw;  // Invalid attempt to throw exception
         // to the outer catch block below.
}
END_CATCH
}
CATCH(CException, e)  // The "outer" catch block
{
   // Pointer e is invalid because
   // it was deleted in the inner catch block.
}
END_CATCH

K tomuto problému dochází, protože e je odstraněn, když provádění projde z "vnitřní" CATCH bloku. Použití makra THROW_LAST místo příkazu THROW způsobí, že "vnější" blok CATCH obdrží platný ukazatel:

TRY
{
   TRY
   {
   // Do something to throw an exception.
   AfxThrowUserException();
}
CATCH(CException, e)  // The "inner" catch block
{
   THROW_LAST(); // Throw exception to the outer catch block below.
}
END_CATCH
}
CATCH(CException, e)  // The "outer" catch block
{
   // Pointer e is valid because
   // THROW_LAST() was used.
}
END_CATCH

Vyzkoušet bloky uvnitř bloků catch

Aktuální výjimku nelze znovu vyvolat z try bloku, který je uvnitř bloku CATCH . Následující příklad je neplatný:

TRY
{
   // Do something to throw an exception.
   AfxThrowUserException();
}
CATCH(CException, e)
{
   try
   {
      throw;  // Wrong.  Causes e (the exception 
            // being thrown) to be deleted.
   }
   catch (CException* exception)
   {
      exception->ReportError();
   }
}
END_CATCH

Další informace naleznete v tématu Výjimky: Zkoumání obsahu výjimky.

Viz také

Zpracování výjimek