2012-04-03 36 views
32

Một vài quan sát thú vị w.r.t bằng hành trên 0 và 0,0Equals điều hành cho số không (BigDecimal/Double) trong Java

  1. new Double(0.0).equals(0) lợi nhuận sai sự thật, trong khi new Double(0.0).equals(0.0) trả về true.

  2. BigDecimal.ZERO.equals(BigDecimal.valueOf(0.0)) trả về false, trong khi BigDecimal.ZERO.equals(BigDecimal.valueOf(0)) trả về true.

Có vẻ như việc so sánh chuỗi đang được thực hiện trong cả hai trường hợp. Ai có thể ném một số ánh sáng về điều này.

Cảm ơn.

Trả lời

59

BigDecimal 'equals' so sánh giá trị và tỷ lệ. Nếu bạn chỉ muốn so sánh giá trị (0 == 0.0), bạn nên sử dụng compareTo:

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

Xem javadoc.

Đối với so sánh Đôi, như được giải thích bởi các câu trả lời khác, bạn đang so sánh một Đôi với số nguyên trong new Double(0.0).equals(0), trả về false vì các đối tượng có các loại khác nhau. Để tham khảo, số code for the equals method in JDK 7 là:

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

Trong trường hợp của bạn, (obj instanceof Double) là sai.

1
new Double(0.0).equals(0); //false 

làm đối số bạn đã chuyển là số nguyên. và equels() trong đúp kiểm tra lớp dù các đối số là od dụ đúp hoặc không sử dụng thể hiện của điều hành.

Phương thức Double 's bằng().

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

Đối số bạn trôi qua là nguyên, mà không phải là thể hiện của đúp, vì vậy nó trả về false.

5
  1. Các 0 trong biểu đầu tiên của mình được hiểu như là một int, có thể được autoboxed thành một Integer, nhưng không phải để một Double. Vì vậy, loại của hai là khác nhau, do đó họ không bằng nhau. OTOH 0.0double, được tự động chuyển thành một số Double, do đó hai toán hạng được coi là bằng nhau.

  2. BigDecimals cũng chứa tỷ lệ (tức là số chữ số ở bên phải dấu chấm dấu thập phân). BigDecimal.ZERO có giá trị là "0", vì vậy tỷ lệ của nó là 0. Do đó, nó không bằng "0.0", có thang tỷ lệ là 1.
    Nếu bạn muốn so sánh giá trị, sử dụng BigDecimal.compareTo:

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

mới đôi (0.0) Equals (0) là thực sự đóng hộp như một cái gì đó như thế này:

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

Double.equals (...) sẽ không bao giờ trả về true trừ khi được đưa ra một cá thể Double khác.

+0

@LukasEder Cảm ơn, cập nhật. – Adam

0
new Double(0.0).equals(0) 

dòng này so sánh một giá trị gấp đôi từ 0 (không chính xác không) với số nguyên của 0.

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

BigDecimal sẽ so sánh độ dài quy mô trong hoạt động bình đẳng.

0

Đối với cân nhắc hiệu suất BigDecimal, BigInteger lưu trữ các giá trị nhỏ 0-15 trong trường hợp BigDecimal (không phân)

BigDecimal.ZERO sẽ mới BigDecimal (BigInteger.ZERO, 0, 0, 1) & valueOf phương pháp thường lấy từ bộ nhớ cache từ 0 đến 15 :)

0
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"); 
} 
+1

Biến đổi một BigDecimal thành một đôi có thể dẫn đến mất độ chính xác và khác 0 nhưng BigDecimal được chuyển thành một Double có thể trở thành 0. Bạn nên so sánh bằng phương thức 'compareTo' trong BigDecimal –

Các vấn đề liên quan