2015-09-09 6 views
11

Ich habe festgestellt, dass Aufruf equals(""); in einer Methode einer Klasse keinen Fehler innerhalb Eclipse generiert. Ich habe nie .equals genannt ohne etwas wie string1.equals(string2); gesehen.Anruf gleich (""); selbst kompiliert und läuft

package voodoo; 

public class Equals { 

    public void method(){ 
     equals(""); 
    } 

} 

Was hier vor sich geht und wann würde equals() selbst ruft immer verwendet werden?

Wenn ich das in eine JUnit zu testen, es läuft und besteht.

+3

@WOUNDEDStevenJones: Warum würden Sie das denken? –

+0

Mit dieser Funktion ist auch nichts falsch: 'public void answerToLifeTheUniverseAndEverything() {42; } '. Diese 42 wird auf dem Bitboden abgelegt, genau wie Ihr 'equals (" ")'. –

+2

@DavidHammen Wird nicht kompiliert. Beliebige Ausdrücke sind gültige Anweisungen in C++ [aber nicht Java] (https://stackoverflow.com/questions/32406041/when-is-anunassigned-expression-a-valid-statement). – Boann

Antwort

16

equals die Sie anrufen, ist Object ‚s equals Methode, die auf this Referenz genannt werden kann, ohne es explizit angeben. Mit anderen Worten, ist Ihr Anruf

this.equals(""); 

Das ist vollkommen gültig

gleichwertig, obwohl eine gut erzogene Implementierung immer false zurückkehren. Beachten Sie, dass der Rückgabewert ignoriert wird, was ebenfalls zulässig ist.

können Sie sehen, was durch zwingende equals mit etwas vor sich geht, die eine Meldung ausgibt, als eine Angelegenheit von einem Experiment:

public class Equals { 

    public void method(){ 
     equals(""); 
    } 
    @Override 
    public boolean equals(Object other) { 
     System.out.println("I am being compared to '"+other+"'"); 
     return super.equals(other); 
    } 
} 
+1

"eine brave Implementierung muss immer falsch zurückgeben". "Ja wirklich?" Kann ich meine eigene erweiterte String-Klasse (vielleicht mit zusätzlichen Encodings) nicht erstellen und sie mit regulären Strings vergleichen? Nur um der Argumentation willen;) – LS97

+9

@ LS97 Es würde die [Symmetrie Anforderung] brechen (http://docs.oracle.com/javase/7/docs/api/java/lang/Object.html#equals (Java. lang.Object)), weil 'java.lang.String' für' 'java.lang.String'' false' zurückgibt und es nicht möglich ist, eine Unterklasse von 'java.lang.String' zu erstellen weil die Klasse "final" ist. – dasblinkenlight

+0

OK, wusste nicht über das "Finale". Ich denke, ich sollte meine Lektüre machen. – LS97

5

Da alles eine Unterklasse der Object-Klasse ist, rufen Sie hier die Methode super class (Object) equals auf. Und es empfängt Object als Parameter, wobei "" ein String-Objekt ist, kompiliert es gut.

Und es gibt tatsächlich boolean zurück, aber Sie ignorieren es zu empfangen. Das ist legal, um das Ergebnis zu ignorieren.

Wenn Sie es erhalten und überprüfen, dass false zurückgibt, da Ihre Equals Klasse nicht gleich einer leeren Zeichenfolge ist.

6

equals ist nicht statisch und es ruft equals von Object, die ähnlich wie das Aufrufen einer anderen Methode der Klasse ist. Außerdem ist unsere Klasse ein Kind von Object. Methodenaufruf ist so etwas wie thisObject.equals(emptyString) Hinweis hier String ist auch ein Object. Also, letztlich rufen wir currntObject.equals(object) Methode von Kind der Object.

Es ist ähnlich,

class A { 
    public boolean ok(Object str) { 
     return false; 
    } 
} 

class B extends A { 

    public void method(){ 
     ok(""); 
    } 
} 

Hier Kind hat nicht die so equals außer Kraft gesetzt, es wird die Methode nennen es ist Eltern, und es wird auf die aktuelle Instanz verweisen.

3

equals(...) ohne explizite Objekt ruft die Methode auf this. In Ihrem Beispiel vergleichen Sie die Instanz Equals mit einer leeren Zeichenfolge.

2

Die equals() öffentliche Methode bei Object Klasse. Alle Klassen standardmäßig eine direkte/indirekte Kindklasse der Klasse Object. Ihre Equals Klasse erbt keine Klasse explizit. Es ist also eine direkte Unterklasse von Object.

und das Verfahren in Objektklasse equals() wird wie folgt erklärt -

public boolean equals(Object obj){} 

So Ihr Code vollständig gültig ist. Sie rufen tatsächlich Equals.equals() unter method().