2016-04-07 14 views
1

Ich schreibe gerade eine Funktion, die ein Objekt aus einer Liste nach einem bestimmten Kriterium zurückgibt. Es sieht wie folgt aus:Ist "Behauptung falsch"; eine gute Praxis?

for (Object object : list) { 
    if (condition(object)) { 
     return object; 
    } 
} 

Diese Funktion sollte immer etwas aus der Liste zurückzukehren, und in dem Fall wurde kein passendes Objekt gefunden, es ein schlechter Ruf war, ein kritischer Fehler, und das Programm beenden sollte. So

, wie ich mit Behauptungen arbeiten aktiviert, ich habe folgende kurz nach der Schleife:

assert false; // Will always trigger in debug mode. 
return null; // No matter anyway, an AssertionException has already been thrown. 

Aber ich frage mich, ob ich gut war oder nicht?
Wenn nicht, was soll ich stattdessen tun? Fällt mir selbst eine Ausnahme?

In jedem Fall gibt es irgendeine Art von Norm über diese Situation?

+1

Scheint wie ein Narr http://stackoverflow.com/questions/28480068/assertfalse-vs-runtimeexception, aber ich will nicht auf mir meinen einseitigen Betrogene-Hammer werfen ... – yshavit

+0

Der Kontext ist ein ganzes andere, sowie das Problem, ich glaube nicht, dass Sie Ihren Hammer werfen müssen. +1 um mich über den Dump-Hammer um 8 Uhr bei der Arbeit lachen zu lassen: D –

Antwort

4

Ich würde lieber versuchen, den Rückgabewert der Funktion beim Aufruf zu überprüfen.

if (yourFunctionWithList(parameter) == null) 
    //error handling, maybe throw new NPException or whatever. 
else 
    //some object was returned 

Sie können auch Ihre eigene Exception-Klasse schreiben und so behandeln, wie Sie möchten.

Ich persönlich denke nicht, assert false ist eine gute Praxis.

EDIT

Wenn es um die AssertionException ist, die ausgelöst wird, dann könnte man auch verwenden, wie

throw new AssertionError ("your error msg here"); 

So können Sie es auf die gleiche Weise behandeln

+0

Aber was ist, wenn ich es aus vielen Code-Stücken rufe? Wäre es nicht einfacher, es am Ende der Funktion ein für allemal zu überprüfen, statt jedes Mal, wenn ich es nenne? – Aracthor

+1

@yshavit richtig, habe sie seit langer Zeit nicht mehr benutzt. Fehlinformationen auf meiner Seite, hinzugefügt eine Bearbeitung –

+0

@Aracthor Besonders wenn Sie es mehrmals aufrufen, sollten Sie die Syntax verwenden, um eine detailliertere Möglichkeit der Fehlerbehandlung zu haben. Aber vielleicht bekomme ich nicht die Kommentar-Frage falsch –

1

ich persönlich vertraue ihnen nicht; Sie sind oft sogar in der Entwicklungsumgebung deaktiviert. Das kann dazu führen, dass sie ein sehr falsches Sicherheitsgefühl vermitteln - sowohl statische Analysetools als auch andere Programmierer können fälschlicherweise annehmen, dass sie wie erwartet funktionieren.

1

Sie sollten eine Ausnahme werfen, die die richtige Art und Weise in Java ist:

for (Object object : list) { 
    if (condition(object)) { 
     return object; 
    } 
} 
throw new Exception('Failed: no matching item found!'); 

Wenn Sie Ihren Geist eines Tages ändern und nicht das Programm beenden möchten, können Sie die Ausnahme fangen.

+1

Sie können AssertionError von assert geworfen abfangen. – titogeo

+0

Sie können 'IllegalStateException' oder' IllegalArgumentException' dafür verwenden (abhängig davon, ob 'list' eine Instanzvariable oder ein Methodenargument ist) –

+0

@titogeo, aber dann erhalten Ihre Methoden keine throws-Signatur, was irgendwie die Ausnahme bildet unsichtbar und irrelevant :) –

2

Das Problem mit der Geltendmachung oder dem Auslösen einer Ausnahme besteht darin, dass Sie die Ausnahmebehandlung verwenden müssen, um etwas zu behandeln, das nicht wirklich ein Ausnahmefall ist.

Darüber hinaus können Sie nicht wirklich sicher sein, was die Ausnahme/Behauptung, die Sie gefangen haben, ausgelöst hat.Es könnte an der Stelle geworfen werden, die Sie erwarten, aber es könnte alternativ in den Filtercode zum Beispiel geworfen worden sein - so nach einer Ausnahme zu suchen, um den "nicht gefunden" -Fall zu finden, kann andere Probleme mit diesem Fall

verschmelzen

eine Alternative ist Optional (eine ähnliche Klasse existiert in Guava für Pre-Java 8, oder Sie ein Set<Object> verwenden können einfach, aber das nicht ersichtlich, dass Sie genau 0 oder 1 Wert erwarten zu finden) zu verwenden:

Optional<Object> method(List<?> list) { 
    for (Object object : list) { 
     if (condition(object)) { 
      return Optional.of(object); 
     } 
    } 
    return Optional.empty(); 
} 

Jetzt wissen Sie in Ihrem aufrufenden Code explizit, dass Sie möglicherweise kein Element in der Liste gefunden haben:

Optional<Object> opt = method(list); 
if (opt.isPresent()) { 
    Object obj = opt.get(); 
    // Handle the fact it was found. 
} else { 
    // Handle the fact it wasn't found. 
} 

eher als Ausnahmebehandlung, die Sie möglicherweise vergessen zu ergänzen.

Verwandte Themen