Na forum 4programmers.net korzystamy z plików cookies. Część z nich jest niezbędna do funkcjonowania
naszego forum, natomiast wykorzystanie pozostałych zależy od Twojej dobrowolnej zgody, którą możesz
wyrazić poniżej. Klikając „Zaakceptuj Wszystkie” zgadzasz się na wykorzystywanie przez nas plików cookies
analitycznych oraz reklamowych, jeżeli nie chcesz udzielić nam swojej zgody kliknij „Tylko niezbędne”.
Możesz także wyrazić swoją zgodę odrębnie dla plików cookies analitycznych lub reklamowych. W tym celu
ustaw odpowiednio pola wyboru i kliknij „Zaakceptuj Zaznaczone”. Więcej informacji o technologii cookie
znajduje się w naszej polityce prywatności.
Zastanawiam się czy operator delete rzuca wyjątek gdy coś pójdzie nie tak...
np. będę próbował zdealokować pamięć do ktorej mam w programie wskaźnik, lecz ona wcześniej została zaalokowana statycznie, a nie dynamicznie.
jak zachowa się operator delete?
Usunąć wpis?
Tej operacji nie będzie można cofnąć.
Świętowit
Świętowit
0
Zachowa się tak jak system operacyjny - pewnie program się wypieprzy.
Operator delete zwyczajnie przekierowuje wskaźnik do systemu, jeżeli nie jest zerem. Na szczęście i nieszczęście odwołuje się do funkcji HeapFree która może rzucić wyjątkiem gdy wskaźnik pochodzi z innego heapu - np. gdy moduł exe odwoła się do delete ze wskaźnikiem zaalokowanym w module dll, który zapewne używa swojego prywatnego heapu.
Wyjątek wyskoczy też gdy odwołasz się do heapu po nadpisaniu zwolnionej pamięci:
Kopiuj
void*ptr1 =new...;void*ptr2 = ptr1;// ptr2 jest gdzieś w innej części programudelete ptr1;// ptr2 nie wie że nie ptr1 został zwolniony// bug trudny do wykrycia:*ptr2 = wartość;// możliwy wyjątek gdy strona pamięci nie ma więcej referencji// wyjątek:
ptr1 =new...;// lub jakiś inny delete
Usunąć wpis?
Tej operacji nie będzie można cofnąć.
Świętowit
Świętowit
0
Warto zauważyć, że to zachowanie niezdefiniowane, zaś potencjalny wyjątek nie jest wyjątkiem C++, zwykłe try/catch nie musi być w stanie go złapać (zależne od implementacji).
Warto też zayważyć, że rzucanie wyjątkiem z destruktorow jest wysoce niewskazane.
Dopowiadając, wyjątki o których mówi sapero i świętowit (jak ów już zauważył) tylko przypadkiem się nazywają wyjątkami. Nazwijmy je BLE.
BLE nie pochodzi z C++, cpp nie ma o nim pojęcia. Z punktu widzenia C++, desktruktory nigdy nie rzucaja wyjątkami, chyba ze programista jadac maluchem za mocno w dach głową przygrzmocił, albo -- wrecz przeciwnie, ma genialny master plan, a wszystko jest dokladnie zabezpieczone, doszlifowane i pasy mocno zapięte.. *)
BLE pochodzi z systemu operacyjnego klasy np. Windows i jest mechanizmem podobnym do wyjatkow, dzieki ktoremu system potrafi Ci dac znac ze cos tragicznie nie wyszlo. Nie, ze jakis tam iostream jest w zlym stanie, czy ze format napisu sie nie zgadza. Cos naprawde tragicznego - np. uszkodzenie pamieci, uszkodzenie stosu, jakis dziwny nieznany kod instrukcji maszynowej itd.
Mechanizm ten jest w miare wygodny i tak podobny do wyjatkow w obsludze, ze sie go wrecz nazywa wyjatkami, a do jego obslugi stosuje __try __except. Ale C++ try/catch go nie zlapią i C++owe mechanizmy go nie wykryja. Przeleci przez nie tak samo jak wyjatek C++ przez kod jezyka C. Bo nie jest wyjątek -- to jest "wyjątek ustrukturyzowany", BLE nazywa sie SEH: http://msdn.microsoft.com/en-us/library/ms680657(VS.85).aspx