Megjegyzés
Az oldalhoz való hozzáféréshez engedély szükséges. Megpróbálhat bejelentkezni vagy módosítani a címtárat.
Az oldalhoz való hozzáféréshez engedély szükséges. Megpróbálhatja módosítani a címtárat.
A C++/CX hibakezelése kivételeken alapul. A windowsos futtatókörnyezet összetevői a legalapvetőbb szinten HRESULT értékekként jelentik a hibákat. A C++/CX fájlban ezek az értékek erősen beírt kivételekké alakulnak, amelyek egy HRESULT értéket és egy programozott módon elérhető sztringleírást tartalmaznak. A kivételek a ref class következőből Platform::Exceptionszármaznak: . A Platform névtér különböző kivételosztályokat határoz meg a leggyakoribb HRESULT értékekhez; az összes többi értéket az Platform::COMException osztályon keresztül jelenti. Minden kivételosztály rendelkezik kivétel::HResult mezővel, amellyel lekérheti az eredeti HRESULT-t. A hibakeresőben megvizsgálhatja a felhasználói kód hívásveremadatait is, amelyek segítenek a kivétel eredeti forrásának rögzítésében, még akkor is, ha az a C++-tól eltérő nyelven írt kódból származik.
Kivételek
A C++ programban windowsos futtatókörnyezeti műveletből, vagy felhasználó által definiált típusból std::exceptionszármazó kivételt hozhat létre és foghat ki. Windows futtatókörnyezeti kivételt csak akkor kell megadnia, ha az átlépi az alkalmazás bináris interfészének (ABI) határát, például ha a kivételt elkapó kód JavaScriptben van megírva. Amikor egy nem Windows-futtatókörnyezeti C++ kivétel eléri az ABI határát, a kivétel kivételré Platform::FailureException lesz lefordítva, amely egy E_FAIL HRESULT-ot jelöl. További információ az ABI-ról: Windows futtatókörnyezeti összetevők létrehozása a C++-ban.
A Platform::Exception paraméter deklarálható egy HRESULT paramétert vagy egy HRESULT paramétert és egy platform::String^ paramétert tartalmazó két konstruktor egyikével, amely az ABI-n keresztül továbbítható bármely olyan Windows Futtatókörnyezeti alkalmazásnak, amely kezeli azt. Deklarálhat kivételt két kivétel::CreateException metódus túlterhelések egyikével, amelyek egy HRESULT paramétert, vagy egy HRESULT paramétert és egy paramétert Platform::String^ vesznek fel.
Standard kivételek
A C++/CX szabványkivételeket támogat, amelyek tipikus HRESULT-hibákat jelölnek. Minden standard kivétel a Platform::COMException függvényből származik, amely a következőből Platform::Exceptionszármazik: . Ha kivételt ad át az ABI-határon, a szokásos kivételek egyikét kell megadnia.
A saját kivételtípus nem származtatható a fájlból Platform::Exception. Egyéni kivétel létrehozásához használjon felhasználó által definiált HRESULT-t egy COMException objektum létrehozásához.
Az alábbi táblázat a szokásos kivételeket sorolja fel.
| Név | Mögöttes HRESULT | Leírás |
|---|---|---|
| COMException | felhasználó által definiált hresult | A nem felismert HRESULT egy COM-metódushívásból való visszaadásakor jön létre. |
| AccessDeniedException | E_ACCESSDENIED | Akkor jelenik meg, ha a hozzáférés megtagadva van egy erőforráshoz vagy szolgáltatáshoz. |
| ChangedStateException | ÁLLAPOT_VÁLTOZÁS_TÖRTÉNT | A rendszer a szülőgyűjtemény módosítása után meghívja a gyűjtemény iterátorának vagy gyűjteménynézetének metódusait, ezáltal érvényteleníti a metódus eredményeit. |
| ClassNotRegisteredException | REGDB_E_CLASSNOTREG | Akkor van beállítva, ha egy COM-osztály nincs regisztrálva. |
| DisconnectedException | RPC_E_DISCONNECTED | Egy objektum leválasztása az ügyfelekről. |
| FailureException | E_FAIL | A művelet meghiúsulásakor a rendszer eldobja. |
| ÉrvénytelenArgumentumKivétel | E_INVALIDARG (Érvénytelen argumentum) | A metódushoz megadott argumentumok egyike érvénytelen. |
| InvalidCastException | E_NOINTERFACE | Akkor dobják ki, ha egy típust nem lehet más típusra leadni. |
| NotImplementedException | E_NOTIMPL (Nem megvalósított funkció) | Akkor kerül végrehajtásra, ha egy interfészmetódus nem lett implementálva egy osztályon. |
| NullReferenceException | E_POINTER | Null objektumhivatkozás hivatkozásának törlésére tett kísérlet esetén történik. |
| ObjectDisposedException | RO_E_CLOSED | Eldobva, amikor egy műveletet hajtanak végre egy megsemmisített objektumon. |
| OperationCanceledException | E_ABORT (Megszakítási hibakód) | A művelet megszakításakor történik. |
| OutOfBoundsException | E_BOUNDS | Akkor történik, amikor egy művelet megpróbál hozzáférni az érvényes tartományon kívüli adatokhoz. |
| OutOfMemoryException | E_OUTOFMEMORY | Ha nincs elegendő memória a művelet végrehajtásához. |
| WrongThreadException | RPC_E_WRONG_THREAD | Akkor dobott, amikor egy szál egy interfészmutatón keresztül telefonál, amely olyan proxyobjektumhoz tartozik, amely nem tartozik a szál lakásához. |
A HResult és az Üzenet tulajdonságai
Minden kivételhez HResult tulajdonság és Üzenet tulajdonság tartozik. A Kivétel::HResult tulajdonság lekéri a kivétel mögöttes numerikus HRESULT-értékét. A Kivétel::Üzenet tulajdonság lekéri a kivételt leíró rendszer által megadott sztringet. Windows 8 rendszerben az üzenet csak a hibakeresőben érhető el, és írásvédett. Ez azt jelenti, hogy a kivétel ismételt létrehozásakor nem módosíthatja azt. A Windows 8.1-ben programozott módon érheti el az üzenetsztringet, és új üzenetet jeleníthet meg, ha újrakezdi a kivételt. A hibakeresőben jobb híváshívási információk is elérhetők, beleértve az aszinkron metódushívások hívásait is.
Példák
Ez a példa bemutatja, hogyan lehet windowsos futtatókörnyezeti kivételt kivenni a szinkron műveletekhez:
String^ Class1::MyMethod(String^ argument)
{
if (argument->Length() == 0)
{
auto e = ref new Exception(-1, "I'm Zork bringing you this message from across the ABI.");
//throw ref new InvalidArgumentException();
throw e;
}
return MyMethodInternal(argument);
}
A következő példa bemutatja, hogyan lehet elkapni a kivételt.
void Class2::ProcessString(String^ input)
{
String^ result = nullptr;
auto obj = ref new Class1();
try
{
result = obj->MyMethod(input);
}
catch (/*InvalidArgument*/Exception^ e)
{
// Handle the exception in a way that's appropriate
// for your particular scenario. Assume
// here that this string enables graceful
// recover-and-continue. Why not?
result = ref new String(L"forty two");
// You can use Exception data for logging purposes.
Windows::Globalization::Calendar calendar;
LogMyErrors(calendar.GetDateTime(), e->HResult, e->Message);
}
// Execution continues here in both cases.
//#include <string>
std::wstring ws(result->Data());
//...
}
Az aszinkron művelet során megjelenő kivételek fogásához használja a feladatosztályt, és adjon hozzá egy hibakezelési folytatást. A hibakezelési folytatás a többi szálra a hívó szálra visszadobott kivételeket rögzíti, így a kód egyetlen pontján kezelheti az összes lehetséges kivételt. További információ: Aszinkron programozás a C++-ban.
UnhandledErrorDetected esemény
A Windows 8.1-ben előfizethet a Windows::ApplicationModel::Core::CoreApplication::UnhandledErrorDetected statikus eseményre , amely hozzáférést biztosít a folyamat leállítására készülő nem kezelt hibákhoz. A hiba forrásától függetlenül windowsos::ApplicationModel::Core::UnhandledError objektumként éri el ezt a kezelőt, amely az esemény args-ével lett átadva. Amikor meghívja Propagate az objektumot, az létrehoz és eldob egy Platform::*Exception , a hibakódnak megfelelő típust. A fogási blokkokban szükség esetén mentheti a felhasználói állapotot, majd engedélyezheti a folyamat leállítását hívással throw, vagy tehet valamit a program ismert állapotba való visszaállításához. Az alábbi példa az alapmintát mutatja be:
Az app.xaml.h fájlban:
void OnUnhandledException(Platform::Object^ sender, Windows::ApplicationModel::Core::UnhandledErrorDetectedEventArgs^ e);
A app.xaml.cpp:
// Subscribe to the event, for example in the app class constructor:
Windows::ApplicationModel::Core::CoreApplication::UnhandledErrorDetected += ref new EventHandler<UnhandledErrorDetectedEventArgs^>(this, &App::OnUnhandledException);
// Event handler implementation:
void App::OnUnhandledException(Platform::Object^ sender, Windows::ApplicationModel::Core::UnhandledErrorDetectedEventArgs^ e)
{
auto err = e->UnhandledError;
if (!err->Handled) //Propagate has not been called on it yet.
{
try
{
err->Propagate();
}
// Catch any specific exception types if you know how to handle them
catch (AccessDeniedException^ ex)
{
// TODO: Log error and either take action to recover
// or else re-throw exception to continue fail-fast
}
}
Megjegyzések
A C++/CX nem használja a záradékot finally .