#| Euler #44 in Racket """ Pentagonal numbers are generated by the formula, P(n)=n(3nāˆ’1)/2. The first ten pentagonal numbers are: 1, 5, 12, 22, 35, 51, 70, 92, 117, 145, ... It can be seen that P(4) + P(7) = 22 + 70 = 92 = P(8). However, their difference, 70 āˆ’ 22 = 48, is not pentagonal. Find the pair of pentagonal numbers, P(j) and P(k), for which their sum and difference is pentagonal and D = |P(k) āˆ’ P(j)| is minimised; what is the value of D? """ This Racket program was created by Hakan Kjellerstrand, hakank@gmail.com See also my Racket page: http://www.hakank.org/racket/ |# #lang racket (provide (all-defined-out)) (require (only-in math/number-theory pentagonal-number)) (require (only-in "utils_hakank.rkt" time-function )) ;;; A little too slow ;;; cpu time: 1134 real time: 1136 gc time: 90 (define (euler44a) (let ([t (for/hash ([n (range 1 2501)]) (values (pentagonal-number n) 1) )] [d 10000000]) (for* ([j (sort (hash-keys t) >) ] [k (sort (hash-keys t) >)] #:do [(define a (+ j k)) (define b (abs (- j k)))] #:when (and (< j k) (< a d) (hash-has-key? t a) (< b d) (hash-has-key? t b) )) (set! d b)) d) ) ;;; Rearranging #:when's and #:do's ;;; and just one sort (which is the real booster) ;;; cpu time: 126 real time: 126 gc time: 0 (define (euler44b) (let* ([t (for/hash ([n (range 1 2501)]) (values (pentagonal-number n) 1) )] [d 10000000] [hs (sort (hash-keys t) >)]) (for* ([j hs] [k hs] #:when (< j k) #:do [(define a (+ j k))] #:when (and (< a d) (hash-has-key? t a)) #:do [(define b (abs (- j k)))] #:when (and (< b d) (hash-has-key? t b) )) (set! d b)) d) ) (define (run) ;;; (time-function euler44a) (time-function euler44b) ) (run)