12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091 |
- ;; https://projecteuler.net/problem=24
- ;; Lexicographic permutations
- ;; Problem 24
- ;; A permutation is an ordered arrangement of objects. For
- ;; example, 3124 is one possible permutation of the digits
- ;; 1, 2, 3 and 4. If all of the permutations are listed
- ;; numerically or alphabetically, we call it lexicographic
- ;; order. The lexicographic permutations of 0, 1 and 2 are:
- ;; 012 021 102 120 201 210
- ;; What is the millionth lexicographic permutation of the
- ;; digits 0, 1, 2, 3, 4, 5, 6, 7, 8 and 9?
- (import
- (except (rnrs base) let-values map)
- (only (guile)
- lambda* λ)
- (ice-9 match)
- (srfi srfi-1) ; list stuff
- (contract)
- (prefix (lib math) math:)
- (lib list-helpers))
- ;; 0123456789 + 9 (9*1)
- ;; 0123456798 + 81 (9*9)
- ;; 0123456879 + 18 (9*2)
- ;; 0123456897 + 81 (9*9)
- ;; 0123456978 + 9 (9*1)
- ;; 0123456987 + 702 (9*9*9 - 9*3 = 9*78)
- ;; 0123457689 ...
- ;; There seems to be some pattern there, but not sure what
- ;; it is exactly.
- ;; I guess one has to really implement permutating a list so
- ;; that the permutations are in order.
- ;; idea: stream of permutations? If I can find the function
- ;; to generate them ...
- ;; '(0 1 2 3 4 5 6 7 8 9)
- ;; - - rotate last 2
- ;; go until numbers no longer become bigger
- ;; then swap the last numbers
- ;; '(0 1 2 3 4 5 6 7 9 8)
- ;; '(0 1 2 3 4 5 6 8 7 9)
- ;; '(0 1 2 3 4 5 6 8 9 7)
- ;; '(0 1 2 3 4 5 6 9 7 8)
- ;; '(0 1 2 3 4 5 6 9 8 7)
- ;; '(0 0 0 0 0 0 0 0 0 0)
- ;; '(0 0 0 0 0 0 0 0 0 1)
- ;; '(0 0 0 0 0 0 0 0 1 0)
- ;; '(0 0 0 0 0 0 0 0 1 1)
- ;; '(0 0 0 0 0 0 0 1 0 0)
- ;; *
- ;; / \
- ;; 0 *
- ;; / \
- ;; 1 *
- ;; / \
- ;; 2 3
- ;; '(0 1 2)
- ;; '(0 2 1)
- ;; '(1 0 2)
- ;; '(1 2 0)
- ;; '(2 0 1)
- ;; '(2 1 0)
- ;; if the smallest number is the last -> something must be
- ;; swapped further at the front
- (define permutations
- (sort (permute math:+decimal-digits+)
- (make-list-comparator <)))
- (simple-format (current-output-port)
- "millionth permutation: ~a\n"
- (list-ref permutations (- (expt 10 6) 1)))
|