2011-09-02 42 views
64

Khi tôi gọi Math.ceil(5.2) khoản hoàn lại là double6.0. Độ nghiêng tự nhiên của tôi là để nghĩ rằng Math.ceil(double a) sẽ trả lại một long. Từ các tài liệu:Tại sao Math.ceil trả lại gấp đôi?

ceil(double a)

Trả nhỏ nhất (gần nhất đến vô cùng tiêu cực) double giá trị đó là không ít hơn so với lập luận và bằng một số nguyên toán học.

Nhưng tại sao trả lại double thay vì số long khi kết quả là số nguyên? Tôi nghĩ rằng hiểu được lý do đằng sau nó có thể giúp tôi hiểu Java tốt hơn một chút. Nó cũng có thể giúp tôi tìm ra nếu tôi gặp rắc rối bằng cách chuyển sang một số long, ví dụ: là

long b = (long)Math.ceil(a);

luôn là điều tôi nghĩ? Tôi sợ rằng có thể có một số trường hợp ranh giới có vấn đề.

+0

Xem http://stackoverflow.com/questions/3412449/why-does-math-round-return-a-long-but-math-floor-return-a-double – starblue

Trả lời

61

Phạm vi của double lớn hơn giá trị của long. Ví dụ:

double x = Long.MAX_VALUE; 
x = x * 1000; 
x = Math.ceil(x); 

gì bạn mong chờ dòng cuối cùng để làm gì nếu Math.ceil trở long?

Lưu ý rằng ở các giá trị rất lớn (dương hoặc âm) các số sẽ được phân phối rất thưa thớt - vì vậy số nguyên tiếp theo lớn hơn số nguyên x sẽ không là x + 1 nếu bạn hiểu ý tôi.

+0

Tôi đoán câu cuối cùng của bạn là nói về một sự thiếu chính xác nhưng tôi nghĩ rằng không phụ thuộc vào số lượng cao nhưng về số lượng chữ số đáng kể của nó (trong nhị phân). Tôi sẽ cố gắng tìm một ví dụ. – aalku

+0

@ user270349: Khoảng cách tuyệt đối giữa các giá trị kép liên tiếp trở nên lớn hơn khi giá trị trở nên lớn hơn. Số chữ số có nghĩa đại diện vẫn giữ nguyên (trừ các số phụ). –

+2

Ví dụ: '2^60' có thể được biểu diễn dưới dạng gấp đôi trong khi' 2^60 (+/-) 1' không thể – aalku

13

Một đôi có thể lớn hơn Long.MAX_VALUE. Nếu bạn gọi số Math.ceil() trên giá trị như vậy, bạn sẽ mong đợi trả về cùng một giá trị. Tuy nhiên nếu nó trả về một thời gian dài, giá trị sẽ không chính xác.

+0

giá trị 'double' lớn hơn' Long.MAX_VALUE' có thể không được biểu diễn chính xác, do đó kết quả 'double' của' ceil (big_double) 'sẽ không là' big_double + 1'. Vì vậy, nó vẫn không chính xác ... –

+0

@CiprianTomoiaga bạn đúng rằng nó sẽ không được big_double +1 vì đây sẽ là big_double. Bất kỳ giá trị nào quá lớn để được biểu diễn dưới dạng 'long' không có phần phân số. –

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