Intervju med Java-unntak (+ svar)

Denne artikkelen er en del av en serie: • Java Collections Interview Questions

• Java Type System Interview Questions

• Java-samtalespørsmål om samtidighet (+ svar)

• Spørsmål om Java-klassestruktur og initialisering

• Java 8 intervjuspørsmål (+ svar)

• Minnehåndtering i Java-intervjuspørsmål (+ svar)

• Java Generics intervjuspørsmål (+ svar)

• Intervju med Java Flow Control (+ svar)

• Intervjuspørsmål om Java-unntak (+ svar) (nåværende artikkel) • Intervju med Java-merknader (+ svar)

• Spørsmål om topp vårrammeverk

1. Oversikt

Unntak er et viktig tema som alle Java-utviklere bør være kjent med. Denne artikkelen gir svar på noen av spørsmålene som kan dukke opp under et intervju.

2. Spørsmål

Q1. Hva er et unntak?

Et unntak er en unormal hendelse som oppstår under gjennomføringen av et program og forstyrrer den normale strømmen av programmets instruksjoner.

Q2. Hva er formålet med kaste og kaste nøkkelord?

De kaster nøkkelord brukes til å spesifisere at en metode kan heve et unntak under kjøringen. Det håndhever eksplisitt unntakshåndtering når du ringer til en metode:

public void simpleMethod () kaster unntak {// ...}

De kaste nøkkelord lar oss kaste et unntaksobjekt for å avbryte den normale flyt av programmet. Dette brukes oftest når et program ikke oppfyller en gitt tilstand:

if (task.isTooComplicated ()) {throw new TooComplicatedException ("Oppgaven er for komplisert"); }

Q3. Hvordan kan du håndtere et unntak?

Ved å bruke en prøv-fang-endelig uttalelse:

prøv {// ...} catch (ExceptionType1 ex) {// ...} catch (ExceptionType2 ex) {// ...} endelig {// ...}

Kodeblokken der unntak kan forekomme, er vedlagt i a prøve blokkere. Denne blokken kalles også "beskyttet" eller "beskyttet" kode.

Hvis et unntak oppstår, vil å fange blokk som samsvarer med unntaket som kastes, blir utført, hvis ikke, alt å fange blokker blir ignorert.

De endelig blokken utføres alltid etter prøve blokkeringsutganger, enten det ble kastet et unntak eller ikke inne i det.

Q4. Hvordan kan du få flere unntak?

Det er tre måter å håndtere flere unntak i en kodeblokk.

Den første er å bruke en å fange blokk som kan håndtere alle unntakstyper som kastes:

prøv {// ...} fange (Unntak ex) {// ...}

Du bør huske at anbefalt praksis er å bruke unntakshåndterere som er så nøyaktige som mulig.

Unntakshåndterere som er for brede, kan gjøre koden din mer utsatt for feil, fange unntak som ikke var forventet og forårsake uventet oppførsel i programmet ditt.

Den andre måten er å implementere flere fangstblokker:

prøv {// ...} catch (FileNotFoundException ex) {// ...} catch (EOFException ex) {// ...}

Vær oppmerksom på at hvis unntakene har et arveforhold; barnetypen må komme først og foreldretypen senere. Hvis vi ikke klarer dette, vil det føre til en kompileringsfeil.

Den tredje er å bruke en flerfangsblokk:

prøv {// ...} fange (FileNotFoundException | EOFException ex) {// ...}

Denne funksjonen ble først introdusert i Java 7; reduserer duplisering av kode og gjør det lettere å vedlikeholde.

Q5. Hva er forskjellen mellom et kontrollert og et ukontrollert unntak?

Et avkrysset unntak må håndteres innenfor en prøvefangst blokkere eller erklært i en kaster klausul; mens et ukontrollert unntak ikke kreves behandlet eller erklært.

Merkede og ukontrollerte unntak er også kjent som henholdsvis kompileringstid og kjøretid unntak.

Alle unntak er merkede unntak, unntatt de som er angitt av Feil, RuntimeException, og deres underklasser.

Q6. Hva er forskjellen mellom et unntak og en feil?

Et unntak er en hendelse som representerer en tilstand som er mulig å gjenopprette, mens feil representerer en ekstern situasjon vanligvis umulig å gjenopprette fra.

Alle feil kastet av JVM er forekomster av Feil eller en av underklassene, de vanligste inkluderer, men er ikke begrenset til:

  • OutOfMemoryError - kastet når JVM ikke kan tildele flere objekter fordi det ikke er minne, og søppeloppsamleren ikke klarte å gjøre mer tilgjengelig
  • StackOverflowError - oppstår når stabelplassen for en tråd er tom, vanligvis fordi et program gjentas for dypt
  • ExceptionInInitializerError - signaliserer at et uventet unntak skjedde under evalueringen av en statisk initialisering
  • NoClassDefFoundError - kastes når klasselasteren prøver å laste definisjonen av en klasse og ikke kunne finne den, vanligvis fordi det kreves klasse filer ble ikke funnet i klassestien
  • Ikke-støttetClassVersionError - oppstår når JVM prøver å lese en klasse fil og bestemmer at versjonen i filen ikke støttes, vanligvis fordi filen ble generert med en nyere versjon av Java

Selv om en feil kan håndteres med en prøve uttalelse, dette er ikke en anbefalt praksis siden det ikke er noen garanti for at programmet vil være i stand til å gjøre noe pålitelig etter at feilen ble kastet.

Q7. Hvilket unntak blir kastet ved å utføre følgende kodeblokk?

Heltall [] [] ints = {{1, 2, 3}, {null}, {7, 8, 9}}; System.out.println ("value =" + ints [1] [1] .intValue ());

Det kaster en ArrayIndexOutOfBoundsException siden vi prøver å få tilgang til en posisjon som er større enn lengden på matrisen.

Q8. Hva er unntakskjede?

Oppstår når et unntak kastes som svar på et annet unntak. Dette lar oss oppdage den komplette historien om vårt reiste problem:

prøv {task.readConfigFile (); } catch (FileNotFoundException ex) {throw new TaskException ("Kunne ikke utføre oppgave", ex); }

Q9. Hva er en stacktrace og hvordan har den et unntak?

Et stakkspor gir navnene på klassene og metodene som ble kalt, fra starten av applikasjonen til det punktet et unntak skjedde.

Det er et veldig nyttig feilsøkingsverktøy siden det gjør det mulig for oss å bestemme nøyaktig hvor unntaket ble kastet i applikasjonen og de opprinnelige årsakene som førte til det.

Q10. Hvorfor vil du underklasse et unntak?

Hvis unntakstypen ikke er representert av de som allerede finnes i Java-plattformen, eller hvis du trenger å gi mer informasjon til klientkoden for å behandle den på en mer presis måte, bør du opprette et tilpasset unntak.

Å avgjøre om et tilpasset unntak skal kontrolleres eller fjernes, avhenger helt av forretningssaken. Imidlertid som en tommelfingerregel; Hvis koden som bruker unntaket ditt, kan forventes å gjenopprette fra den, kan du opprette et avkrysset unntak, ellers gjør den ukontrollert.

Du bør også arve fra det mest spesifikke Unntak underklasse som er nært knyttet til den du vil kaste. Hvis det ikke er en slik klasse, så velg Unntak som foreldre.

Q11. Hva er noen fordeler med unntak?

Tradisjonelle feilsøkings- og håndteringsteknikker fører ofte til spaghettikode som er vanskelig å vedlikeholde og vanskelig å lese. Unntak gjør det imidlertid mulig for oss å skille kjernelogikken i søknaden vår fra detaljene om hva vi skal gjøre når noe uventet skjer.

Siden JVM søker bakover gjennom samtalestakken for å finne noen metoder som er interessert i å håndtere et bestemt unntak; vi får muligheten til å overføre en feil opp i samtalestakken uten å skrive tilleggskode.

Også fordi alle unntak som kastes i et program er objekter, kan de grupperes eller kategoriseres basert på klassens hierarki. Dette lar oss fange en gruppe unntak i en enkelt unntakshåndterer ved å spesifisere unntakets superklasse i å fange blokkere.

Q12. Kan du kaste noe unntak i kroppen til et Lambda-uttrykk?

Når du bruker et standard funksjonelt grensesnitt som allerede er levert av Java, kan du bare kaste ukontrollerte unntak fordi standard funksjonelle grensesnitt ikke har en "kaster" -klausul i metodesignaturer:

Liste heltall = Arrays.asList (3, 9, 7, 0, 10, 20); heltall.forEach (i -> {if (i == 0) {kast nytt IllegalArgumentException ("Null ikke tillatt");} System.out.println (Math.PI / i);});

Imidlertid, hvis du bruker et tilpasset funksjonelt grensesnitt, er det mulig å kaste avmerkede unntak:

@FunctionalInterface offentlig statisk grensesnitt CheckedFunction {void apply (T t) kaster Unntak; }
public void processTasks (List taks, CheckedFunction checkedFunction) {for (Task task: taks) {try {checkedFunction.apply (task); } fange (Unntak e) {// ...}}} prosessoppgaver (oppgaveliste, t -> {// ... kaste nytt unntak ("Noe skjedde");});

Q13. Hva er reglene vi må følge når vi tilsidesetter en metode som gir unntak?

Flere regler dikterer hvordan unntak må erklæres i forbindelse med arv.

Når foreldreklassemetoden ikke gir noen unntak, kan ikke barnemetoden kaste noe avmerket unntak, men det kan hende at det ikke er merket av.

Her er en eksempelkode for å demonstrere dette:

class Parent {void doSomething () {// ...}} class Child extends Parent {void doSomething () throw IllegalArgumentException {// ...}}

Det neste eksemplet kan ikke kompileres siden den overordnede metoden kaster et avkrysset unntak som ikke er deklarert i den overstyrte metoden:

class Parent {void doSomething () {// ...}} class Child extends Parent {void doSomething () throw IOException {// Compilation error}}

Når foreldreklassemetoden kaster et eller flere avmerkede unntak, kan barneklassemetoden kaste ethvert ukontrollert unntak; alt, ingen eller en delmengde av de deklarerte sjekket unntakene, og enda et større antall av disse så lenge de har samme omfang eller smalere.

Her er en eksempelkode som følger den forrige regelen:

klasse Forelder {void doSomething () kaster IOException, ParseException {// ...} void doSomethingElse () kaster IOException {// ...}} class Child utvider Forelder {void doSomething () kaster IOException {// ...} ugyldig doSomethingElse () kaster FileNotFoundException, EOFException {// ...}}

Merk at begge metodene respekterer regelen. Den første kaster færre unntak enn den overstyrte metoden, og den andre, selv om den kaster mer; de er smalere.

Imidlertid, hvis vi prøver å kaste et avkrysset unntak som overordnet klassemetode ikke erklærer, eller vi kaster et med et bredere omfang; vi får en kompileringsfeil:

klasse Forelder {void doSomething () kaster FileNotFoundException {// ...}} klasse Child utvider Forelder {void doSomething () kaster IOException {// Kompilasjonsfeil}}

Når overordnet klassemetode har en kasteklausul med et ukontrollert unntak, kan barneklassemetoden ikke kaste noen eller et hvilket som helst antall ukontrollerte unntak, selv om de ikke er relatert.

Her er et eksempel som respekterer regelen:

class Parent {void doSomething () throw IllegalArgumentException {// ...}} class Child extends Parent {void doSomething () throw ArithmeticException, BufferOverflowException {// ...}}

Q14. Vil følgende kode kompilere?

ugyldig doSomething () {// ... kast nytt RuntimeException (nytt unntak ("lenket unntak")); }

Ja. Når unntakene kjedes, bryr kompilatoren seg bare om den første i kjeden, og fordi den oppdager et ukontrollert unntak, trenger vi ikke å legge til en kasteklausul.

Q15. Er det noen måte å kaste et kontrollert unntak fra en metode som ikke har en klausul?

Ja. Vi kan dra nytte av typen sletting utført av kompilatoren og få den til å tro at vi kaster et ukontrollert unntak, når det faktisk er; vi kaster et avkrysset unntak:

offentlig T sneakyTrow (Throwable ex) kaster T {throw (T) ex; } public void methodWithoutThrows () {this.sneakyThrow (new Exception ("Checked Exception")); }

3. Konklusjon

I denne artikkelen har vi utforsket noen av spørsmålene som sannsynligvis vil vises i tekniske intervjuer for Java-utviklere, angående unntak. Dette er ikke en uttømmende liste, og den skal bare behandles som starten på videre forskning.

Vi i Baeldung ønsker deg lykke til i kommende intervjuer.

Neste » Spørsmål om Java-merknader (+ svar) « Tidligere spørsmål om Java Flow Control-intervju (+ svar)

$config[zx-auto] not found$config[zx-overlay] not found