DerGuteMoritz - use of lazy-seq (tested after DeeEff comment) pasted by arthurmaciel on Wed Jul 15 15:42:54 2015
CHICKEN (c) 2008-2014, The Chicken Team (c) 2000-2007, Felix L. Winkelmann Version 4.9.0.1 (stability/4.9.0) (rev 8b3189b) linux-unix-gnu-x86-64 [ 64bit manyargs dload ptables ] bootstrapped 2014-06-07 #;1> (use lazy-seq) ; loading /usr/local/lib/chicken/7/lazy-seq.import.so ... ; loading /usr/local/lib/chicken/7/chicken.import.so ... ; loading /usr/local/lib/chicken/7/srfi-1.import.so ... ; loading /usr/local/lib/chicken/7/extras.import.so ... ; loading /usr/local/lib/chicken/7/lazy-seq.so ... #;2> (define odd-numbers (lazy-filter odd? (lazy-numbers))) #;3> odd-numbers #<lazy-seq 1 ...> #;4> (lazy-ref 132413247103298471032894710329 odd-numbers) [panic] out of memory - cannot allocate heap segment - execution terminated <syntax> <eval> <-- Process scheme exited abnormally with code 1
explanation added by DerGuteMoritz on Wed Jul 15 16:09:37 2015
;; The issue with the above example is that `odd-numbers' (and `#3' for that matter) hold a reference to the head of the sequence so the intermediate results can never be reclaimed which is why it runs out of memory eventually. There is no apparent way the `lazy-seq' implementation could guard against this kind of situation. ;; One way to make this example run in constant space is to turn `odd-numbers' into a procedure, like this: #;1> (use lazy-seq) #;2> (define (odd-numbers) (lazy-filter odd? (lazy-numbers))) #;3> (lazy-ref 10000000 (odd-numbers)) 20000001 ;; You will note that this is very slow, though, as it creates a lot of intermediate garbage, putting heavy pressure on the GC.