Gestern hatte ich ein zweistündiges technisches Telefoninterview (das ich bestanden habe, woohoo!), Aber ich habe die folgende Frage bezüglich der dynamischen Bindung in Java vollständig beantwortet. Und es ist doppelt rätselhaft, weil ich Studenten vor einigen Jahren als TA dieses Konzept beigebracht habe. Die Aussicht, dass ich ihnen Fehlinformationen gegeben habe, ist also etwas beunruhigend ...
Hier ist das Problem, das mir gegeben wurde:
/* What is the output of the following program? */
public class Test {
public boolean equals( Test other ) {
System.out.println( "Inside of Test.equals" );
return false;
}
public static void main( String [] args ) {
Object t1 = new Test();
Object t2 = new Test();
Test t3 = new Test();
Object o1 = new Object();
int count = 0;
System.out.println( count++ );// prints 0
t1.equals( t2 ) ;
System.out.println( count++ );// prints 1
t1.equals( t3 );
System.out.println( count++ );// prints 2
t3.equals( o1 );
System.out.println( count++ );// prints 3
t3.equals(t3);
System.out.println( count++ );// prints 4
t3.equals(t2);
}
}
Ich habe behauptet, dass die Ausgabe zwei separate Druckanweisungen innerhalb der überschriebenen equals()
Methode sein sollte: at t1.equals(t3)
und t3.equals(t3)
. Der letztere Fall ist offensichtlich genug, und im ersteren Fall wird er, obwohl er t1
eine Referenz vom Typ Object hat, als Typ Test instanziiert, sodass die dynamische Bindung die überschriebene Form der Methode aufrufen sollte.
Scheinbar nicht. Mein Interviewer ermutigte mich, das Programm selbst auszuführen, und siehe da, es gab nur eine einzige Ausgabe der überschriebenen Methode: an der Leitung t3.equals(t3)
.
Meine Frage ist dann, warum? Wie bereits erwähnt, sollte die dynamische Bindung dafür sorgen, dass die spezifischste Version der Methode basierend auf dem instanziierten Typ der Referenz aufgerufen wird, obwohl t1
es sich um eine Referenz vom Typ Object handelt (statische Bindung würde also die equals()
Methode von Object aufrufen ) . Was vermisse ich?