Yönetilen Özel Durumları Kullanmaya İlişkin Temel Kavramlar
Bu konu başlığında yönetilen uygulamalarda özel durum işleme açıklanmaktadır. Diğer bir ifadeyle, /clr derleyici seçeneğiyle derlenmiş bir uygulamadır.
Bu konuda,
Açıklamalar
/clr seçeneğiyle derliyorsanız, CLR özel durumlarını işleyebilirsiniz ve standart Exception sınıf CLR özel durumlarını işlemek için birçok yararlı yöntem sağlar ve kullanıcı tanımlı özel durum sınıfları için temel sınıf olarak önerilir.
Bir arabirimden türetilen özel durum türlerinin yakalanması /clr altında desteklenmez. Ayrıca, ortak dil çalışma zamanı yığın taşması özel durumlarını yakalamanıza izin vermez; yığın taşması özel durumu işlemi sonlandıracaktır.
Yönetilen ve yönetilmeyen uygulamalarda özel durum işleme farklılıkları hakkında daha fazla bilgi için bkz. C++ için Yönetilen Uzantılar Altında Özel Durum İşleme Davranışındaki Farklılıklar.
/clr Altında Özel Durumlar Oluşturma
C++ throw ifadesi, CLR türüne tanıtıcı oluşturacak şekilde genişletilir. Aşağıdaki örnek özel bir özel durum türü oluşturur ve ardından bu türün bir örneğini oluşturur:
// clr_exception_handling.cpp
// compile with: /clr /c
ref struct MyStruct: public System::Exception {
public:
int i;
};
void GlobalFunction() {
MyStruct^ pMyStruct = gcnew MyStruct;
throw pMyStruct;
}
Bir değer türü, oluşturulmadan önce kutulanmalıdır:
// clr_exception_handling_2.cpp
// compile with: /clr /c
value struct MyValueStruct {
int i;
};
void GlobalFunction() {
MyValueStruct v = {11};
throw (MyValueStruct ^)v;
}
CLR Uzantıları için Try/Catch Blokları
Aynı try
/catch
blok yapısı hem CLR hem de yerel özel durumları yakalamak için kullanılabilir:
// clr_exception_handling_3.cpp
// compile with: /clr
using namespace System;
ref struct MyStruct : public Exception {
public:
int i;
};
struct CMyClass {
public:
double d;
};
void GlobalFunction() {
MyStruct^ pMyStruct = gcnew MyStruct;
pMyStruct->i = 11;
throw pMyStruct;
}
void GlobalFunction2() {
CMyClass c = {2.0};
throw c;
}
int main() {
for ( int i = 1; i >= 0; --i ) {
try {
if ( i == 1 )
GlobalFunction2();
if ( i == 0 )
GlobalFunction();
}
catch ( CMyClass& catchC ) {
Console::WriteLine( "In 'catch(CMyClass& catchC)'" );
Console::WriteLine( catchC.d );
}
catch ( MyStruct^ catchException ) {
Console::WriteLine( "In 'catch(MyStruct^ catchException)'" );
Console::WriteLine( catchException->i );
}
}
}
Çıktı
In 'catch(CMyClass& catchC)'
2
In 'catch(MyStruct^ catchException)'
11
C++ Nesneleri için Geri Sarmama Sırası
Geri sarma, oluşturma işlevi ile işleme işlevi arasında çalışma zamanı yığınında olabilecek yıkıcılara sahip tüm C++ nesneleri için gerçekleşir. CLR türleri yığında ayrıldığından, geri sarma bunlar için geçerli değildir.
Oluşturulan özel durum için olayların sırası aşağıdaki gibidir:
Çalışma zamanı, özel durumu yakalamak için uygun catch yan tümcesini veya SEH dışında bir filtreyi arayan yığını gösterir. Catch yan tümceleri önce sözcük düzeninde aranır ve ardından çağrı yığınını dinamik olarak aşağı doğru aşağı doğru arar.
Doğru işleyici bulunduktan sonra yığın bu noktaya kadar kaldırılır. Yığındaki her işlev çağrısı için yerel nesneleri yok edilir ve __finally bloklar çoğu iç içe dışa doğru yürütülür.
Yığın kaldırıldıktan sonra catch yan tümcesi yürütülür.
Yönetilmeyen Türleri Yakalama
Yönetilmeyen bir nesne türü oluşturulduğunda, türü SEHExceptionözel durumuyla sarmalanır. Uygun catch
yan tümceyi ararken iki olasılık vardır.
Yerel bir C++ türüyle karşılaşılırsa, özel durum eşlenmemiştir ve karşılaşılan türle karşılaştırılır. Bu karşılaştırma, yerel bir C++ türünün normal şekilde yakalanmasını sağlar.
Ancak, SEHException türünde bir
catch
yan tümcesi veya temel sınıflarından herhangi biri önce incelenirse, yan tümcesi özel duruma müdahale eder. Bu nedenle, CLR türlerinin catch yan tümcelerinden önce yerel C++ türlerini yakalayan tüm catch yan tümcelerini yerleştirmeniz gerekir.
Aşağıdakilere dikkat edin:
catch(Object^)
ile
catch(...)
her ikisi de SEH özel durumları dahil olmak üzere herhangi bir tür yakalar.
Yönetilmeyen bir tür catch(Object^) tarafından yakalanırsa, atılan nesneyi yok etmeyecektir.
Yönetilmeyen özel durumlar oluştururken veya yakalarken, /EHs veya /EHa yerine /EHsc derleyici seçeneğini kullanmanızı öneririz.