2014-11-16 15 views
6

Trong clojure v1.6.0, mã này chỉ chạy mãi mãi và tiêu thụ 100% của một lõi:Tại sao mã này không ném StackOverflow ngoại lệ

(defn average [x y] (/ (+ x y) 2)) 

(defn improve [guess x] 
    (average guess (/ x guess))) 

(defn sqrt-iter [guess x] 
    (sqrt-iter (improve guess x) x)) 

(sqrt-iter 1 4) 

tôi mong đợi nó để ném một StackOverflowError ngay lập tức, nhưng nó không.

Bất kỳ giải thích nào tại sao nó xảy ra?

Trả lời

8

Vì 1 dài. Mã bắt đầu tính toán các lý trí cực kỳ dài và chậm lại sau một vài lần lặp lại. Nếu bạn chạy nó với 1,0 và 4 nó thổi ngăn xếp rất nhanh sau một vài nghìn cuộc gọi (có thể thay đổi tùy thuộc vào các tham số jvm của bạn).

+1

Để tràn, cần thực hiện chỉ vài nghìn cuộc gọi. Là số học thực sự dài * mà chậm * để nó không thể tính toán 10k đơn vị và số tiền một cách nhanh chóng? – zerkms

+4

Nó không phải là số học dài. Đó là một Tỷ lệ, chứa BigIntegers trong mẫu số và tử số. BigIntegers sẽ phát triển tùy ý lâu dài. Xem https://github.com/clojure/clojure/blob/master/src/jvm/clojure/lang/Ratio.java –

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