32 votes

Peut-on remplacer .equals de telle sorte que a.equals (a) retourne false?

Je suis encore assez frais pour tout cela, mais je suis en train de travailler sur la réalisation de mon OCAJP de certification (Java). Je me suis souvenu de lecture précédemment que l' .méthode equals pourrait être remplacée lorsque je suis venu à cette question:

Question from Enthuware prep materials:

Maintenant que ces questions ont été assez mal pour autant que je suis concerné. La torsion de chaque petite chose que vous pensez que vous savez de vous forcer à apprendre tous les détails. Maintenant, j'avais deviné E, mais je ne pense pas que D est correcte. Je veux dire 99,9% du temps, bien sûr, mais je pensais que c'était une question piège fondée sur le libellé.

Cela m'a fait penser, est-ce vrai? Je veux dire, si je reçois la question à l'examen, je sais comment y répondre maintenant, mais dans la profondeur de l'abîme obscur de l'annulation de la folie, est-il possible de créer une situation où un.est égal à(a) renvoie la valeur faux? Je me sens comme ce serait Aristote en colère...

47voto

Eran Points 35360

Notez que a . b et c sont des instances de classes de wrapper primitives (telles que Integer, Double, etc ...). Ces classes sont finales et ne peuvent pas être étendues. Vous ne pouvez donc pas remplacer leur implémentation equals .

Par conséquent, a.equals(a) retournera toujours la valeur true, car ces classes implémentent correctement equals .

21voto

Gergely Kőrössy Points 358

Depuis equals(...) n'est pas une méthode finale de Object, oui, il est très bien possible dans une situation différente.

@Override
public boolean equals(Object obj) {
    return false;
}

Cette question, cependant, spécifiquement dit que ce sont des primitifs wrappers (par exemple, Integer, Boolean, etc.) et depuis ces classes sont au final, on ne peut pas prolonger, ainsi a.equals(a) retournera toujours true.

7voto

Falco Points 451

Entier une.est égal à( a ) peut retourner false

Mais vous devez être vraiment mal et l'utilisation de réflexions et de Multithreading:

Si vous exécutez ce code, il y a une chance qu'une condition de course peut changer la Valeur interne de l' myInt alors que la comparaison a lieu. Si vous voulez simuler cette condition, il suffit de mettre un point d'arrêt à l'intérieur de l' Integer.intValue() d'exécuter le code en debug et frappé continuer. Cela va créer un retard qui crée la condition de la course artificiellement et la console sera de retour faux.

class IntegerEqualsTest
{
    public static void main( final String[] args )
    {
        final Integer myInt = new Integer( 420 );

        new Thread() {
            public void run() {
                try {
                    final Field f = Integer.class.getDeclaredField( "value" );
                    f.setAccessible( true );
                    f.setInt( myInt, 100 );
                } catch( final Exception e ) {}
            }; }.start();

        System.out.println( myInt.equals( myInt ) );
    }
}

6voto

sleske Points 29978

Les autres réponses ont déjà répondu à votre question - non, ce n'est pas possible avec le Java de la primitive de classes wrapper.

Je vais essayer de répondre à la "question derrière la question": Est-ce possible avec d'autres classes?

[...] dans les profondeurs de l'abîme obscur de l'annulation de la folie, est-il possible de créer une situation où un.est égal à(a) renvoie la valeur faux? J'ai l'impression que c' ferait Aristote en colère...

C'est effectivement une bonne question, et la réponse est: Oui, il est possible de créer une telle situation, et oui, il serait Aristote en colère. En fait, je ne sais pas si il serait Aristote en colère, de ne pas l'avoir connu, mais il sera certainement causer beaucoup de douleur pour celui qui doit travailler avec le code.

Le truc, c'est: Il y a un contrat associé à Object.equals():

La méthode equals met en œuvre une relation d'équivalence sur la non-null les références de l'objet:

[...]

Il est réflexive: pour toute non-nulle de la valeur de référence x, x.est égal à(x) doit retourner true.

Javadoc de l'Objet.est égal à

Oui, lors de la création de votre propre classe, vous pouvez violer ce contrat. Il n'y a (malheureusement) rien dans le compilateur ou de l'exécution d'arrêt vous.

Cependant, beaucoup de code s'appuie sur le présent contrat, donc si vous violer, le code qui utilise equals échoueront probablement de façon mystérieuse.

Un exemple: Java propre Collection de classes (java.util.Collection et amis) s'appuient sur l' equals. Si une instance d'une classe qui n'est pas une mise en œuvre correcte equals est mis dans une collection, des choses étranges se produisent, tels que la collecte, parfois, contenant l'instance et parfois pas.

1voto

Yair Zaslavsky Points 2647

Vous pouvez jeter un coup d'œil aux implémentations de tous les wrappers primitifs, à savoir: Integer, Boolean, Character etc ... vous verrez que l'implémentation est correcte.
La raison est qu'avec equals, une des vérifications effectuées consiste à vérifier l'égalité de référence, et x.equals (x) en tant qu'objet et en tant qu'argument sont le même objet.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X