web-dev-qa-db-fra.com

Opérateur égal pour les zéros (BigDecimal / Double) dans Java

Quelques observations intéressantes par rapport à l'opérateur égal à 0 et 0,0

  1. new Double(0.0).equals(0) renvoie false, tandis que new Double(0.0).equals(0.0) renvoie true.

  2. BigDecimal.ZERO.equals(BigDecimal.valueOf(0.0)) renvoie false, tandis que BigDecimal.ZERO.equals(BigDecimal.valueOf(0)) renvoie true.

Il semble que la comparaison de chaînes soit effectuée dans les deux cas. Quelqu'un pourrait-il éclairer cela?.

Merci.

34
Manish Mulani

BigDecimal 'equals' compare la valeur et l'échelle. Si vous souhaitez uniquement comparer les valeurs (0 == 0,0), vous devez utiliser compareTo:

BigDecimal.ZERO.compareTo(BigDecimal.valueOf(0.0)) == 0 //true
BigDecimal.ZERO.compareTo(BigDecimal.valueOf(0)) == 0 //true

Voir javadoc .

Quant à la comparaison Double, comme expliqué par d'autres réponses, vous comparez un Double avec un Entier dans new Double(0.0).equals(0), qui retourne false car les objets ont des types différents. Pour référence, le code pour la méthode equals dans JDK 7 est:

public boolean equals(Object obj) {
    return (obj instanceof Double)
           && (doubleToLongBits(((Double)obj).value) ==
                  doubleToLongBits(value));
}

Dans votre cas, (obj instanceof Double) Est faux.

64
assylias
  1. Le 0 dans votre première expression est interprété comme un int, qui peut être placé automatiquement dans un Integer, mais pas dans un Double. Donc, le type des deux est différent, donc ils ne sont pas égaux. OTOH 0.0 est un double, qui est placé automatiquement dans un Double, donc les deux opérandes sont considérés comme égaux.

  2. Les BigDecimals contiennent également une échelle (c'est-à-dire le nombre de chiffres à droite du séparateur décimal). BigDecimal.ZERO a la valeur "0", donc son échelle est 0. Elle n'est donc pas égale à "0,0", dont l'échelle est 1.
    Si vous souhaitez comparer des valeurs, utilisez BigDecimal.compareTo :

    BigDecimal.ZERO.compareTo(BigDecimal.valueOf(0.0)) == 0
    BigDecimal.ZERO.compareTo(BigDecimal.valueOf(0)) == 0
    
5
Péter Török
new Double(0.0).equals(0); //false

comme l'argument que vous avez passé est un entier. et la classe equels () in Double vérifie si l'argument est od instance Double ou ne pas utiliser - instance de opérateur.

La méthode Doubleequals ().

if (!(argument instanceof Double))
  return false;

L'argument que vous avez passé est entier, qui n'est pas une instance de Double, il renvoie donc false.

1
Chandra Sekhar

new Double (0.0) .equals (0) est en fait encadré comme ceci:

new Double(0.0).equals(Integer.valueOf(0))

Double.equals (...) ne retournera jamais vrai sauf si on lui donne une autre instance Double.

1
Adam
new Double(0.0).equals(0)

Cette ligne compare une valeur double de 0 (qui n'est pas un zéro exact) avec un entier de 0.

BigDecimal.ZERO.equals(BigDecimal.valueOf(0.0))

BigDecimal comparera la longueur de l'échelle dans l'opération égale.

0
TheOutsider

Pour des considérations de performances BigDecimal, BigInteger met en cache les petites valeurs de 0 à 15 en cas de BigDecimal (sans fractions)

BigDecimal.ZERO sera le nouveau BigDecimal (BigInteger.ZERO, 0, 0, 1) et la méthode valueOf est généralement récupérée dans le cache pour 0 à 15 :)

0
Anish Dasappan
please try doublevalue instead of compareto if you feel is not as beautiful and readable as or simply need an alternative like below:

BigDecimal a = new BigDecimal("0.00");
BigDecimal b = new BigDecimal("0.0");
BigDecimal c = new BigDecimal("0");

if(a.doubleValue()==BigDecimal.ZERO.doubleValue()) {
System.out.println("a equals");
}

if(b.doubleValue()==BigDecimal.ZERO.doubleValue()) {
System.out.println("b equals");
}

if(c.doubleValue()==BigDecimal.ZERO.doubleValue()) {
System.out.println("c equals");
} 
0
Agassis