Wyjątki

Przypomnienie:

try
{
   int a=1;
   throw a;
}
catch(int b)
{
   // wyjatek typu int
}
catch(...)
{
   // wszystkie wyjatki
}

W pliku nagłówkowym wyjatki.h zadeklaruj klasy wyjątków: Wyjatek, ZlyIndeksWektora i BrakPamieci i dodaj do szablonu klasy Wektor polecenia rzucające obiekty tych klas w razie zaistnienia sytuacji wyjątkowych.

  • Klasa Wyjatek, stanowi ogólną klasę wyjątków po której będą dziedziczyły wszystkie inne typy wyjątków. Klasa ta zawiera:
    • pole chronione przechowujące komunikat o błędzie (string).
      Komunikat ustawiany jest przez konstruktor, np. : throw Wyjatek(„Pojawil sie nieoczekiwany blad!”).
    • metodę publiczną Komunikat() zwracająca tekst komunikatu.
  • Klasa ZlyIndeksWektora dziedziczy po klasie Wyjatek.
    Obiekt tej klasy będzie rzucany gdy podamy niepoprawny indeks tablicy (wektora).
    Klasa zawiera publiczne pole typu całkowitego inicjowane przez konstruktor, przechowujące wartość złego indeksu.

Przykład użycia dla klasy Wektor:

try
{
	//Wektor<int> a(-1);	// zly indeks
	Wektor<int> b(100);
	for(int i=0;i<30;i++) b.Dodaj(i);
	// b[-1] = 2;			// zly indeks
	b[29] = 2;
	// b[30] = 2;			// zly indeks
	cout << "Nie wystapil zaden wyjatek" << endl;
}
catch(ZlyIndeksWektora w)
{
	cout << "Wystapil wyjatek [zly indeks]: " <<  "Wartosc indeksu " << w.indeks << endl;
}
catch(...)
{
	cout << "Wystapil nieznany wyjatek\n";
}
  • Klasa BrakPamieci dziedziczy po klasie Wyjątek.
    Obiekt tej klasy rzucamy gdy zabraknie pamięci przy zwiększaniu wektora.
try
{
        int rozmiar = 1;
	while(1)
	{
		cout << "Rozmiar: " << rozmiar << " kB" << endl;
		Wektor<char> c(rozmiar*1024);		// w koncu zabraknie pamieci
		rozmiar*=2;
	}
	cout << "Nie wystapil zaden wyjatek" << endl;
}
catch(BrakPamieci w)
{
       cout << "Wyjatek [brak pamieci] " << endl; 
}catch(...)
{
	cout << "Wystapil nieznany wyjatek\n";
}
W zależności od onfiguracji, operator new w przypadku wystąpienia błędu może także rzucać wyjątek. Można temu zapobiec wymuszając aby w przypadku błędu operator ten zwracał NULL.

Przykład:

#include <new.h>
int *a = new(std::nothrow) int[1];
if(a==0) throw "Brak pamieci";
  • Klasy BrakPamieci i ZlyIndeksWektora dziedziczą po klasie Wyjatek, więc:
    • przeciążają odpowiednie konstruktory pozwalające dodać komunikat o błędzie przy tworzeniu obiektu (obiekty każdej z tych klas powinny być inicjowane odpowiednim domyślnym komunikatem)
    • zasłaniają metodę Komunikat() zwracając tekst odpowiednio sformatowany z zależności od sytuacji (od typu obiektu).

Przykładowy kod testowy:

try
{
      //Wektor<int> a(-1);	// zly indeks
 
	Wektor<int> b(100);
	for(int i=0;i<30;i++) b.Dodaj(i);
	// b[-1] = 2;			// zly indeks
	b[29] = 2;
	// b[30] = 2;			// zly indeks
 
	int rozmiar=1;
	while(1)
	{
		cout << "Rozmiar: " << rozmiar << " kB" << endl;
		Wektor<char> c(rozmiar*1024);		// w koncu zabraknie pamieci
		rozmiar*=2;
	}
 
	cout << "Nie wystapil zaden wyjatek" << endl;
}
catch(Wyjatek &w)
{
	 w.Komunikat() ;
}
catch(BrakPamieci &w)
{
	 w.Komunikat(); 
}
catch(ZlyIndeksWektora &w)
{
        w.Komunikat();
}
catch(...)
{
	cout << "Wystapil nieznany wyjatek\n";
}