Mangarevan Counting
June 20, 2017
Here are our conversion functions:
(define (integer->mangareva n) (when (not (<= 1 n 799)) (error 'integer->mangareva "out of range")) (let loop ((n n) (m (list))) (cond ((<= 80 n) (loop (remainder n 80) (cons "V" (cons (number->string (quotient n 80)) m)))) ((<= 40 n) (loop (- n 40) (cons "T" m))) ((<= 20 n) (loop (- n 20) (cons "P" m))) ((<= 10 n) (loop (- n 10) (cons "K" m))) ((<= 1 n) (loop 0 (cons (number->string n) m))) (else (apply string-append (reverse m))))))
(define (mangareva->integer str) (define (digit? c) (char<=? #\1 c #\9)) (let loop ((cs (string->list str)) (n 0)) (list-match cs (() n) ((m) (digit? m) (loop '() (+ n (char->integer m) -48))) ((#\K . rest) (loop rest (+ n 10))) ((#\P . rest) (loop rest (+ n 20))) ((#\T . rest) (loop rest (+ n 40))) ((m #\V . rest) (digit? m) (loop rest (+ n (* (- (char->integer m) 48) 80)))) (else (error 'mangareva->integer "not a number")))))
We used pattern matching for the conversion from Mangarevan to integer, because it’s much easier to read than parsing each element of the number. Note that our error checking is not sufficient to find all mis-formed Mangarevan numbers. It’s easy to do an exhaustive test:
> (do ((n 1 (+ n 1))) ((= n 800)) (assert (mangareva->integer (integer->mangareva n)) n))
That writes nothing, on the theory that no news is good news. Here’s a complete list of Mangarevan counting numbers:
> (map integer->mangareva (range 1 800)) ("1" "2" "3" "4" "5" "6" "7" "8" "9" "K" "K1" "K2" "K3" "K4" "K5" "K6" "K7" "K8" "K9" "P" "P1" "P2" "P3" "P4" "P5" "P6" "P7" "P8" "P9" "PK" "PK1" "PK2" "PK3" "PK4" "PK5" "PK6" "PK7" "PK8" "PK9" "T" "T1" "T2" "T3" "T4" "T5" "T6" "T7" "T8" "T9" "TK" "TK1" "TK2" "TK3" "TK4" "TK5" "TK6" "TK7" "TK8" "TK9" "TP" "TP1" "TP2" "TP3" "TP4" "TP5" "TP6" "TP7" "TP8" "TP9" "TPK" "TPK1" "TPK2" "TPK3" "TPK4" "TPK5" "TPK6" "TPK7" "TPK8" "TPK9" "1V" "1V1" "1V2" "1V3" "1V4" "1V5" "1V6" "1V7" "1V8" "1V9" "1VK" "1VK1" "1VK2" "1VK3" "1VK4" "1VK5" "1VK6" "1VK7" "1VK8" "1VK9" "1VP" "1VP1" "1VP2" "1VP3" "1VP4" "1VP5" "1VP6" "1VP7" "1VP8" "1VP9" "1VPK" "1VPK1" "1VPK2" "1VPK3" "1VPK4" "1VPK5" "1VPK6" "1VPK7" "1VPK8" "1VPK9" "1VT" "1VT1" "1VT2" "1VT3" "1VT4" "1VT5" "1VT6" "1VT7" "1VT8" "1VT9" "1VTK" "1VTK1" "1VTK2" "1VTK3" "1VTK4" "1VTK5" "1VTK6" "1VTK7" "1VTK8" "1VTK9" "1VTP" "1VTP1" "1VTP2" "1VTP3" "1VTP4" "1VTP5" "1VTP6" "1VTP7" "1VTP8" "1VTP9" "1VTPK" "1VTPK1" "1VTPK2" "1VTPK3" "1VTPK4" "1VTPK5" "1VTPK6" "1VTPK7" "1VTPK8" "1VTPK9" "2V" "2V1" "2V2" "2V3" "2V4" "2V5" "2V6" "2V7" "2V8" "2V9" "2VK" "2VK1" "2VK2" "2VK3" "2VK4" "2VK5" "2VK6" "2VK7" "2VK8" "2VK9" "2VP" "2VP1" "2VP2" "2VP3" "2VP4" "2VP5" "2VP6" "2VP7" "2VP8" "2VP9" "2VPK" "2VPK1" "2VPK2" "2VPK3" "2VPK4" "2VPK5" "2VPK6" "2VPK7" "2VPK8" "2VPK9" "2VT" "2VT1" "2VT2" "2VT3" "2VT4" "2VT5" "2VT6" "2VT7" "2VT8" "2VT9" "2VTK" "2VTK1" "2VTK2" "2VTK3" "2VTK4" "2VTK5" "2VTK6" "2VTK7" "2VTK8" "2VTK9" "2VTP" "2VTP1" "2VTP2" "2VTP3" "2VTP4" "2VTP5" "2VTP6" "2VTP7" "2VTP8" "2VTP9" "2VTPK" "2VTPK1" "2VTPK2" "2VTPK3" "2VTPK4" "2VTPK5" "2VTPK6" "2VTPK7" "2VTPK8" "2VTPK9" "3V" "3V1" "3V2" "3V3" "3V4" "3V5" "3V6" "3V7" "3V8" "3V9" "3VK" "3VK1" "3VK2" "3VK3" "3VK4" "3VK5" "3VK6" "3VK7" "3VK8" "3VK9" "3VP" "3VP1" "3VP2" "3VP3" "3VP4" "3VP5" "3VP6" "3VP7" "3VP8" "3VP9" "3VPK" "3VPK1" "3VPK2" "3VPK3" "3VPK4" "3VPK5" "3VPK6" "3VPK7" "3VPK8" "3VPK9" "3VT" "3VT1" "3VT2" "3VT3" "3VT4" "3VT5" "3VT6" "3VT7" "3VT8" "3VT9" "3VTK" "3VTK1" "3VTK2" "3VTK3" "3VTK4" "3VTK5" "3VTK6" "3VTK7" "3VTK8" "3VTK9" "3VTP" "3VTP1" "3VTP2" "3VTP3" "3VTP4" "3VTP5" "3VTP6" "3VTP7" "3VTP8" "3VTP9" "3VTPK" "3VTPK1" "3VTPK2" "3VTPK3" "3VTPK4" "3VTPK5" "3VTPK6" "3VTPK7" "3VTPK8" "3VTPK9" "4V" "4V1" "4V2" "4V3" "4V4" "4V5" "4V6" "4V7" "4V8" "4V9" "4VK" "4VK1" "4VK2" "4VK3" "4VK4" "4VK5" "4VK6" "4VK7" "4VK8" "4VK9" "4VP" "4VP1" "4VP2" "4VP3" "4VP4" "4VP5" "4VP6" "4VP7" "4VP8" "4VP9" "4VPK" "4VPK1" "4VPK2" "4VPK3" "4VPK4" "4VPK5" "4VPK6" "4VPK7" "4VPK8" "4VPK9" "4VT" "4VT1" "4VT2" "4VT3" "4VT4" "4VT5" "4VT6" "4VT7" "4VT8" "4VT9" "4VTK" "4VTK1" "4VTK2" "4VTK3" "4VTK4" "4VTK5" "4VTK6" "4VTK7" "4VTK8" "4VTK9" "4VTP" "4VTP1" "4VTP2" "4VTP3" "4VTP4" "4VTP5" "4VTP6" "4VTP7" "4VTP8" "4VTP9" "4VTPK" "4VTPK1" "4VTPK2" "4VTPK3" "4VTPK4" "4VTPK5" "4VTPK6" "4VTPK7" "4VTPK8" "4VTPK9" "5V" "5V1" "5V2" "5V3" "5V4" "5V5" "5V6" "5V7" "5V8" "5V9" "5VK" "5VK1" "5VK2" "5VK3" "5VK4" "5VK5" "5VK6" "5VK7" "5VK8" "5VK9" "5VP" "5VP1" "5VP2" "5VP3" "5VP4" "5VP5" "5VP6" "5VP7" "5VP8" "5VP9" "5VPK" "5VPK1" "5VPK2" "5VPK3" "5VPK4" "5VPK5" "5VPK6" "5VPK7" "5VPK8" "5VPK9" "5VT" "5VT1" "5VT2" "5VT3" "5VT4" "5VT5" "5VT6" "5VT7" "5VT8" "5VT9" "5VTK" "5VTK1" "5VTK2" "5VTK3" "5VTK4" "5VTK5" "5VTK6" "5VTK7" "5VTK8" "5VTK9" "5VTP" "5VTP1" "5VTP2" "5VTP3" "5VTP4" "5VTP5" "5VTP6" "5VTP7" "5VTP8" "5VTP9" "5VTPK" "5VTPK1" "5VTPK2" "5VTPK3" "5VTPK4" "5VTPK5" "5VTPK6" "5VTPK7" "5VTPK8" "5VTPK9" "6V" "6V1" "6V2" "6V3" "6V4" "6V5" "6V6" "6V7" "6V8" "6V9" "6VK" "6VK1" "6VK2" "6VK3" "6VK4" "6VK5" "6VK6" "6VK7" "6VK8" "6VK9" "6VP" "6VP1" "6VP2" "6VP3" "6VP4" "6VP5" "6VP6" "6VP7" "6VP8" "6VP9" "6VPK" "6VPK1" "6VPK2" "6VPK3" "6VPK4" "6VPK5" "6VPK6" "6VPK7" "6VPK8" "6VPK9" "6VT" "6VT1" "6VT2" "6VT3" "6VT4" "6VT5" "6VT6" "6VT7" "6VT8" "6VT9" "6VTK" "6VTK1" "6VTK2" "6VTK3" "6VTK4" "6VTK5" "6VTK6" "6VTK7" "6VTK8" "6VTK9" "6VTP" "6VTP1" "6VTP2" "6VTP3" "6VTP4" "6VTP5" "6VTP6" "6VTP7" "6VTP8" "6VTP9" "6VTPK" "6VTPK1" "6VTPK2" "6VTPK3" "6VTPK4" "6VTPK5" "6VTPK6" "6VTPK7" "6VTPK8" "6VTPK9" "7V" "7V1" "7V2" "7V3" "7V4" "7V5" "7V6" "7V7" "7V8" "7V9" "7VK" "7VK1" "7VK2" "7VK3" "7VK4" "7VK5" "7VK6" "7VK7" "7VK8" "7VK9" "7VP" "7VP1" "7VP2" "7VP3" "7VP4" "7VP5" "7VP6" "7VP7" "7VP8" "7VP9" "7VPK" "7VPK1" "7VPK2" "7VPK3" "7VPK4" "7VPK5" "7VPK6" "7VPK7" "7VPK8" "7VPK9" "7VT" "7VT1" "7VT2" "7VT3" "7VT4" "7VT5" "7VT6" "7VT7" "7VT8" "7VT9" "7VTK" "7VTK1" "7VTK2" "7VTK3" "7VTK4" "7VTK5" "7VTK6" "7VTK7" "7VTK8" "7VTK9" "7VTP" "7VTP1" "7VTP2" "7VTP3" "7VTP4" "7VTP5" "7VTP6" "7VTP7" "7VTP8" "7VTP9" "7VTPK" "7VTPK1" "7VTPK2" "7VTPK3" "7VTPK4" "7VTPK5" "7VTPK6" "7VTPK7" "7VTPK8" "7VTPK9" "8V" "8V1" "8V2" "8V3" "8V4" "8V5" "8V6" "8V7" "8V8" "8V9" "8VK" "8VK1" "8VK2" "8VK3" "8VK4" "8VK5" "8VK6" "8VK7" "8VK8" "8VK9" "8VP" "8VP1" "8VP2" "8VP3" "8VP4" "8VP5" "8VP6" "8VP7" "8VP8" "8VP9" "8VPK" "8VPK1" "8VPK2" "8VPK3" "8VPK4" "8VPK5" "8VPK6" "8VPK7" "8VPK8" "8VPK9" "8VT" "8VT1" "8VT2" "8VT3" "8VT4" "8VT5" "8VT6" "8VT7" "8VT8" "8VT9" "8VTK" "8VTK1" "8VTK2" "8VTK3" "8VTK4" "8VTK5" "8VTK6" "8VTK7" "8VTK8" "8VTK9" "8VTP" "8VTP1" "8VTP2" "8VTP3" "8VTP4" "8VTP5" "8VTP6" "8VTP7" "8VTP8" "8VTP9" "8VTPK" "8VTPK1" "8VTPK2" "8VTPK3" "8VTPK4" "8VTPK5" "8VTPK6" "8VTPK7" "8VTPK8" "8VTPK9" "9V" "9V1" "9V2" "9V3" "9V4" "9V5" "9V6" "9V7" "9V8" "9V9" "9VK" "9VK1" "9VK2" "9VK3" "9VK4" "9VK5" "9VK6" "9VK7" "9VK8" "9VK9" "9VP" "9VP1" "9VP2" "9VP3" "9VP4" "9VP5" "9VP6" "9VP7" "9VP8" "9VP9" "9VPK" "9VPK1" "9VPK2" "9VPK3" "9VPK4" "9VPK5" "9VPK6" "9VPK7" "9VPK8" "9VPK9" "9VT" "9VT1" "9VT2" "9VT3" "9VT4" "9VT5" "9VT6" "9VT7" "9VT8" "9VT9" "9VTK" "9VTK1" "9VTK2" "9VTK3" "9VTK4" "9VTK5" "9VTK6" "9VTK7" "9VTK8" "9VTK9" "9VTP" "9VTP1" "9VTP2" "9VTP3" "9VTP4" "9VTP5" "9VTP6" "9VTP7" "9VTP8" "9VTP9" "9VTPK" "9VTPK1" "9VTPK2" "9VTPK3" "9VTPK4" "9VTPK5" "9VTPK6" "9VTPK7" "9VTPK8" "9VTPK9")
You can run the program at http://ideone.com/5lLuG2.
In Python, abusing the eval() function.
(@Praxis, your parsing function does not look right. I see it missing newlines and cut short.)
@Jussi: Fixed. Thanks. WordPress recently updated its editor, again, and every time they do something breaks.
In Python with checks on input.
From Mangarevan.c:
To Mangarevan.c:
The programs are known to run on an Apple Power Mac G4 (AGP Graphics) (450MHz processor, 1GB memory) on both Mac OS 9.2.2 (International English) (the programs interpreted using Leonardo IDE 3.4.1) and Mac OS X 10.4.11 (the programs compiled using Xcode 2.2.1).
(I’ve just completed a gig at London South Bank University and so I’m again just trying to solve the problems posed by this ‘site whilst I try to get a job; I’m well-aware that my solutions are far from the best – but, in my defence, I don’t have any traditional qualifications in computer science :/ )