; project euler 12
(define (factors n)
(if (even? n) (cons 2 (factors (/ n 2)))
(let loop ((n n) (f 3) (fs '()))
(cond ((< n (* f f)) (reverse (cons n fs)))
((zero? (modulo n f)) (loop (/ n f) f (cons f fs)))
(else (loop n (+ f 2) fs))))))
(define (numdiv n)
(let ((fs (factors n)))
(let loop ((prev (car fs)) (fs (cdr fs)) (f 2) (d 1))
(cond ((null? fs) (* d f))
((= (car fs) prev) (loop prev (cdr fs) (+ f 1) d))
(else (loop (car fs) (cdr fs) 2 (* d f)))))))
(define (euler-12 n)
(let loop ((i 1) (tri 1))
(if (< n (numdiv tri)) tri
(loop (+ i 1) (+ tri i 1)))))
(time (begin (display (euler-12 500)) (newline)))