Exercise 148: Design a program that encodes text files numerically.
Each letter in a word should be encoded as a numeric three-letter string with a value between 0 and 256. Here is our encoding function for letters:
; 1String -> String
; auxiliary for stating tests
;(define (code1 c)
; (number->string (string->int c)))
;
;(check-expect (encode-letter "\t")
; (string-append "00" (code1 "\t")))
;(check-expect (encode-letter "a")
; (string-append "0" (code1 "a")))
;(check-expect (encode-letter "z") (code1 "z"))
;
;(define (encode-letter s)
; (cond
; [(< (string->int s) 10) (string-append "00" (code1 s))]
; [(< (string->int s) 100) (string-append "0" (code1 s))]
; [else (code1 s)]))
; Before you start, explain this function. Also recall how
; a string can be converted into a list of 1Strings.
; Again, use read-words/line to preserve the organization of
; the file into lines and words.
They don't specify in the question what they want you to do with the output, so I'm going to return it as a plain string with no padding between the groups.
(require racket/base)
; 1String -> String
; convert the given 1string into a three-letter numeric string
; 1String -> String
; auxiliary for stating tests
(define (code1 c)
(number->string (string->int c)))
(check-expect (encode-letter "\t")
(string-append "00" (code1 "\t")))
(check-expect (encode-letter "a")
(string-append "0" (code1 "a")))
(check-expect (encode-letter "z")
(code1 "z"))
(define (encode-letter s)
(cond
[(< (string->int s) 10) (string-append "00" (code1 s))]
[(< (string->int s) 100) (string-append "0" (code1 s))]
[else (code1 s)]))
Explaining how it works is straight forward. code1 calls string->int, which will convert the char passed in into an int. (Presumably it's ascii code decimal equivilant). This is then converted to a string and returned.
As this will be a straight int (eg, no leading zero's) the function encode-letter will prepend "00" if the number is less than 10, or prepend "0" if the number is greater than 10 but less than 100.
; encode a list of numbers - returns a list of strings of
; encoded chars
; 1String -> String
(define (process-word loc)
(cond ((empty? loc) "")
((cons? loc) (string-append (encode-letter (first loc))
(process-word (rest loc))))))
(check-expect (process-word (list "t" "h" "e")) "116104101")
; Process the entire line of words into integer codes. Note the
; use of the 'explode' function here. I was originally trying
; to use string->list which will not work!
; List-of-Strings->String
(define (process-line los)
(cond ((empty? los)
"")
((cons? los)
(string-append (process-word (explode (first los)))
(process-line (rest los))))))
(check-expect (process-line (list "the" "cat" "in" "the" "hat"))
"116104101099097116105110116104101104097116")
No comments:
Post a Comment