2012-02-29 18 views
7

vorrei rilevare un'eccezione, log, impostare una bandiera, e il rethrow la stessa eccezionejava: non può rigenerare eccezione: non gestita di tipo eccezione eccezione

ho questo codice:

public Boolean doJobWithResult() { 
    boolean result = true; 
    final Feed feed = Feed.findById(feedId); 
    try { 
     feed.fetchContents(); 
    } catch (Exception ex) { 
     result = false; 
     Logger.info("fetching feed(%d) failed", feedId); 
     throw ex; 
    } 
    return result; 
} 

Ma eclipse si lamenta al lancio ex, dicendo che "Eccezione tipo eccezione non gestita", e mi suggerisce di aggiungere un blocco try-catch attorno ad esso.

In realtà, voglio il processo di chiamare questo metodo per gestire l'eccezione, e non gestire da solo ... voglio solo ritornare vero se tutto va bene, e di accedervi se c'è un'eccezione

On D'altra parte, posso avvolgere l'eccezione dentro un'altra eccezione, ma non posso lanciare la stessa ..

qualche idea?

risposta

2

Penso che ci sono varie cose da ricordare qui:

  1. Si sia desidera doJobWithResult() per tornare vero in caso di successo e falso in caso di fallimento, o di ritorno nulla in caso di successo e gettare un'eccezione in caso di fallimento. Entrambi allo stesso tempo non sono possibili. Nel primo caso, intercettare l'eccezione, registrarla e restituire false, nel secondo caso modificare la firma per restituire void e lanciare un'eccezione e gestirla nel chiamante.
  2. È un Non chiamare per rilevare un'eccezione, registrarlo e rilanciarlo. Perché? Perché un potenziale chiamante del tuo metodo non sa che lo stai già loggando, e puoi anche registrarlo. O lanciare un'eccezione (nel qual caso il chiamante deve occuparsene) o prenderla e gestirla (registrarla).
  3. Nota che il lancio di Exception non fornisce al chiamante del metodo alcun indizio su cosa potrebbe potenzialmente andare storto nel tuo metodo, è sempre meglio lanciare eccezioni più specifiche, o avvolgere un'eccezione in una definita dall'utente e rilanciarla .
  4. Inoltre, se si lancia Exception, un chiamante potrebbe essere tentato di catturare Exception senza notare che questo catturerà anche ogni RuntimeException (poiché è derivata da Exception), che potrebbe non essere il comportamento desiderato.
+0

tutte le risposte sono state abbastanza utili, penso che questo dia anche alcuni suggerimenti su come gestire le eccezioni ... – opensas

2

Dal Exception è checked, in alternativa alla cattura il Exception è quello di dichiarare il vostro metodo di come buttare:

public Boolean doJobWithResult() throws Exception { 
    // ... 
} 
7

Il tuo metodo doJobWithResult ha bisogno di dichiarare che può gettare Eccezione:

public Boolean doJobWithResult() { 

diventa

public Boolean doJobWithResult() throws Exception { 
3

Se doJobWithResult non deve gestire l'eccezione, rimuovere il blocco catch e aggiungere "throws Exception" alla firma del metodo. La registrazione delle eccezioni può essere eseguita nella classe/metodo che deve gestire l'eccezione in un blocco try/catch corrispondente.

2

Non è necessario impostare il risultato come falso nel blocco catch, poiché il valore non verrà restituito (poiché stiamo generando un'eccezione).

Il metodo deve anche dichiarare che genera un'eccezione e quindi il client sarà costretto a gestirlo.

Considerare inoltre l'utilizzo di un'eccezione più specifica che verrà generata in questo caso particolare.

4

È possibile generare la stessa eccezione se si aggiunge throws Exception alla firma del metodo. Altrimenti puoi lanciare un RuntimeException.

public Boolean doJobWithResult() { 
    boolean result = true; 
    final Feed feed = Feed.findById(feedId); 
    try { 
     feed.fetchContents(); 
    } catch (Exception ex) { 
     result = false; 
     Logger.info("fetching feed(%d) failed", feedId); 
     throw new RuntimeException(ex); 
    } 
    return result; 
} 

In tal caso, non è necessario indicare che public Boolean doJobWithResult() getta qualcosa, ma fare in modo di gestire correttamente in seguito (cattura o aspettate che il vostro filo per fermare ... è una RuntimeException dopotutto).

0

Si potrebbe generare un'eccezione incontrollato

Logger.info("fetching feed(%d) failed", feedId); 
throw new RuntimeException(ex); 
1

Aggiungi throws Exception al metodo. Non è inoltre necessario aggiungere result = false; nel blocco catch.

1

Penso che il modo in cui gestisci questa eccezione sia davvero appropriato se non è possibile ripristinare alcun errore del metodo feed.fetchContents().(L'idea è meglio fermarsi piuttosto che continuare) Oltre a ciò, suggerirei di utilizzare una gerarchia di eccezioni più specifica.

Un'altra cosa che ho ricevuto da un java book efficace è che se si scrive un metodo di questo tipo è necessario documentarlo con @throw (nei commenti) con il motivo.