C ++

Rukovanje iznimkama na C ++

Rukovanje iznimkama na C ++
Postoje tri vrste softverskih pogrešaka. To su sintaksne pogreške, logičke pogreške i pogreške pri izvođenju.

Sintaksne pogreške

Pogrešno upisan izraz, izjava ili konstrukcija sintaksna je pogreška.

Razmotrite sljedeće dvije izjave:

int arr [] = 1, 2, 3; // ispravan
int arr = 1, 2, 3; // sintaksna pogreška, nedostaje []

Definicije su istog niza. Prvi je točan. Nedostaje drugi [], a to je sintaksna pogreška. Program s sintaksnom pogreškom ne uspijeva sastaviti. Kompilacija ne uspijeva s porukom pogreške koja ukazuje na sintaksnu pogrešku. Dobra stvar je što se sintaksna pogreška uvijek može popraviti ako programer zna što radi.

Logička pogreška

Logička pogreška je pogreška koju programer počini kada se izvrši neko pogrešno logičko kodiranje. To može biti rezultat neznanja programera o značajkama programskog jezika ili nerazumijevanja onoga što program treba učiniti.

U ovoj se situaciji program uspješno sastavlja. Program dobro funkcionira, ali daje pogrešne rezultate. Takva pogreška može nastati zbog ponavljanja petlje pet puta kada je napravljena ponavljanje 10 puta. Može se dogoditi i da je petlja nesvjesno napravljena da se beskrajno ponavlja. Jedini način da se riješi takva vrsta pogreške je pažljivo programiranje i temeljito testiranje programa prije nego što ga predate kupcu.

Runtime pogreške

Pogrešni ili iznimni ulazi uzrokuju runtime pogreške. U ovom je slučaju program sastavljen uspješno i dobro funkcionira u mnogim situacijama. U određenim situacijama program se ruši (i zaustavlja).

Zamislite da u segmentu programskog koda 8 treba podijeliti s određenim brojem nazivnika. Dakle, ako se brojnik 8 podijeli s nazivnikom 4, odgovor (količnik) bi bio 2. Međutim, ako korisnik unese 0 kao nazivnik, program će se srušiti. Podjela s 0 nije dopuštena u matematici, a nije dopuštena ni u računarstvu. Dijeljenje po nuli treba spriječiti u programiranju. Rukovanje iznimkama obrađuje pogreške tijekom izvođenja, poput dijeljenja po nuli. Sljedeći program pokazuje kako riješiti problem dijeljenja po nuli bez korištenja značajke iznimke u C ++:

#include
pomoću prostora imena std;
int main ()

int brojnik = 8;
int nazivnik = 2;
ako (nazivnik != 0)

int rezultat = brojnik / nazivnik;
cout << result << '\n';

drugo

cout << "Division by zero is not permitted!" << '\n';

return 0;

Izlaz je 4. Da je nazivnik 0, izlaz bi bio:

“Podjela s nulom nije dopuštena!"

Glavni kod ovdje je if-else konstrukcija. Ako nazivnik nije 0, izvršit će se podjela; ako je 0, podjela se neće izvršiti. Korisniku će se poslati poruka o pogrešci, a program nastavlja raditi bez pada. Rutacijske pogreške obično se rješavaju izbjegavanjem izvršenja segmenta koda i slanjem poruke o pogrešci korisniku.

Značajka iznimke u C ++-u koristi blok proba za if-blok i catch-block za else-blok za obradu pogreške, baš kako slijedi:

#include
pomoću prostora imena std;
int main ()

int brojnik = 8;
int nazivnik = 2;
probati

ako (nazivnik != 0)

int rezultat = brojnik / nazivnik;
cout << result << '\n';

drugo

baciti 0;


uhvatiti (int err)

ako (pogreška == 0)
cout << "Division by zero is not permitted!" << '\n';

return 0;

Imajte na umu da zaglavlje try nema argument. Također imajte na umu da catch-block, koji je poput definicije funkcije, ima parametar. Tip parametra mora biti jednak operandu (argumentu) izraza throw. Izraz bacanja nalazi se u bloku try. Baca argument po izboru programera koji je povezan s pogreškom, a catch-block je hvata. Na taj se način kôd u try-bloku ne izvršava. Zatim blok catch prikazuje poruku o pogrešci.

Ovaj članak objašnjava postupanje s iznimkama u C-u++. Osnovno znanje na jeziku C ++ preduvjet je da čitatelj razumije ovaj članak.

Sadržaj članka:

  • Funkcija bacanja iznimke
  • Više blokova ulova za jedan pokušaj bloka
  • Ugniježđeni blokovi pokušaj / ulov
  • noexcept-specifikator
  • Posebna funkcija std :: terminate ()
  • Zaključak

Funkcija bacanja iznimke:

Funkcija također može izbaciti izuzetak baš kao što to čini pokušaj blokiranja. Bacanje se odvija unutar definicije funkcije. Sljedeći program to ilustrira:

#include
pomoću prostora imena std;
praznina fn (const char * str)

if (islower (str [0]))
baciti 'l';

int main ()

probati

fn ("kovač");

ulov (char ch)

ako (ch == 'l')
cout << "Person's name cannot begin in lowercase!" << '\n';

return 0;

Primijetite da ovaj put blok try ima samo poziv funkcije. Pozvana funkcija ima operaciju bacanja. Blok catch hvata iznimku, a izlaz je:

“Ime osobe ne može počinjati malim slovima!"

Ovaj put, bačeni i ulovljeni tip je char.

Više blokova ulova za jedan pokušaj bloka:

Za jedan pokušaj može biti više blokova ulova. Zamislite situaciju u kojoj ulaz može biti bilo koji od znakova tipkovnice, ali ne znamenka i ne abeceda. U ovom slučaju moraju postojati dva bloka za ulov: jedan za cijelu vrijednost za provjeru znamenke i jedan za znak za provjeru abecede. Sljedeći kod to ilustrira:

#include
pomoću prostora imena std;
char input = '*';
int main ()

probati

if (isdigit (input))
bacanje 10;
if (isalpha (input))
baciti 'z';

uhvatiti (int)

cout << "Digit input is forbidden!" << '\n';

ulov (char)

cout << "Character input is forbidden!" << '\n';

return 0;

Nema rezultata. Ako je vrijednost unosa bila znamenka, e.g., '1', izlaz bi bio:

"Unos znamenki je zabranjen!"

Ako je vrijednost unosa abeceda, npr.g., 'a', izlaz bi bio:

"Unos znakova je zabranjen!"

Imajte na umu da na popisu parametara dva bloka ulova nema imena identifikatora. Također imajte na umu da u definiciji dva bloka ulova nisu provjereni pojedini bačeni argumenti jesu li njihove vrijednosti točne ili ne.

Za ulov je važan tip; ulov mora odgovarati vrsti bačenog operanda. Određena vrijednost bačenog argumenta (operanda) može se koristiti za daljnju provjeru ako je potrebno.

Više od jednog rukovatelja za isti tip

Moguće je imati dva rukovatelja iste vrste. Kada se izuzme izuzetak, kontrola se prenosi na najbliži obrađivač s odgovarajućim tipom. Sljedeći program to ilustrira:

#include
pomoću prostora imena std;
char input = '1';
int main ()

probati

if (isdigit (input))
bacanje 10;

uhvatiti (int)

cout << "Digit input is forbidden!" << '\n';

uhvatiti (int)

cout << "Not allowed at all: digit input!" << '\n';

return 0;

Izlaz je:

"Unos znamenki je zabranjen!"

Ugnježđeni blokovi pokušaj / ulov:

try / catch blokovi se mogu ugnijezditi. Ovdje se ponavlja gornji program za unos nealfanumeričkih znakova s ​​tipkovnice, ali s ugniježđenim abecednim kodom pogreške:

#include
pomoću prostora imena std;
char input = '*';
int main ()

probati

if (isdigit (input))
bacanje 10;
probati

if (isalpha (input))
baciti 'z';

ulov (char)

cout << "Character input is forbidden!" << '\n';


uhvatiti (int)

cout << "Digit input is forbidden!" << '\n';

return 0;

Abecedni blok pokušaja / hvatanja pogreške ugniježđen je u blok pokušaja znamenkanog koda. Rad ovog programa i prethodna operacija iz koje je kopiran jednaki su.

noexcept-specifikator

Razmotrite sljedeću funkciju:

praznina fn (const char * str), osim

if (islower (str [0]))
baciti 'l';

Obratite pažnju na specifikator 'noexcept' odmah nakon desne zagrade popisa parametara funkcije. To znači da funkcija ne smije donijeti iznimku. Ako funkcija izbaci iznimku, kao u ovom slučaju, sastavit će se s porukom upozorenja, ali se neće pokrenuti. Pokušaj pokretanja programa pozvat će posebnu funkciju std :: terminate (), koja bi trebala graciozno zaustaviti program, umjesto da samo dopusti da se doslovno sruši.

Specifikator noexcept je u različitim oblicima. To su kako slijedi:

upišite func () noexcept; : ne dopušta izraz bacanja
upišite func () noexcept (true); : dopušta izraz bacanja
upišite func () throw (); : ne dopušta izraz bacanja
upišite func () noexcept (false); : dopušta izraz bacanja, koji nije obvezan
upišite func (); : dopušta izraz bacanja, koji nije obvezan

true ili false u zagradi se mogu zamijeniti izrazom koji rezultira true ili false.

Posebna funkcija std :: terminate ():

Ako se iznimka ne može obraditi, treba je ponovno baciti. U ovom slučaju, bačeni izraz može ili ne mora imati operand. Posebna funkcija std :: terminate () pozvat će se tijekom izvođenja, što bi trebalo graciozno zaustaviti program, umjesto da mu se samo omogući da se doslovno sruši.

Upišite, kompajlirajte i pokrenite sljedeći program:

#include
pomoću prostora imena std;
char input = '1';
int main ()

probati

if (isdigit (input))
bacanje 10;

uhvatiti (int)

bacanje;

return 0;

Nakon uspješne kompilacije, program se prekinuo bez pokretanja, a poruka o pogrešci s računara autora glasi:

“Završava se poziva nakon bacanja instance 'int'

Prekinuto (jezgra bačena) "

Zaključak:

Značajka iznimke u C ++-u sprječava izvršavanje segmenta koda na temelju neke vrste unosa. Program se nastavlja po potrebi. Konstrukcija iznimke (sprečavanje pogrešaka) sastoji se od bloka proba i bloka hvatanja. Blok pokušaja ima segment koda od interesa koji se može zaobići, ovisno o nekim ulaznim uvjetima. Blok try ima izraz throw, koji baca operand. Ovaj se operand naziva i iznimkom. Ako su tip operanda i tip za parametar catch bloka jednaki, tada se iznimka hvata (obrađuje). Ako se iznimka ne uhvati, program će se prekinuti, ali ipak budite sigurni jer nije izveden segment koda koji je trebao biti izveden da bi dao pogrešan rezultat. Tipično rukovanje iznimkama znači zaobilaženje segmenta koda i slanje poruke o pogrešci korisniku. Segment koda se izvršava za normalan unos, ali se zaobilazi za pogrešne ulaze.

Najbolje aplikacije za mapiranje gamepada za Linux
Ako volite igrati igre na Linuxu s gamepadom umjesto tipičnim sustavom za unos tipkovnice i miša, za vas postoji nekoliko korisnih aplikacija. Mnoge r...
Korisni alati za Linux igrače
Ako volite igrati igre na Linuxu, velika je vjerojatnost da ste možda koristili aplikacije i uslužne programe poput Wine, Lutris i OBS Studio za pobol...
HD Remastered igre za Linux koje ranije nisu imale Linux izdanje
Mnogi programeri i izdavači igara dolaze s HD remasterom starih igara kako bi produžili životni vijek franšize, molimo obožavatelje da zatraže kompati...