Inspired by the syntax of if
from the exercise 1.4 from SICP,
I tried to code something similar but with cond
:
#!/usr/bin/env racket
#lang racket/base
(define (b x) (display (bytes-append #"\033[1m" (string->bytes/utf-8 x) #"\33[m")))
(define (i x) (display (bytes-append #"\33[3m" (string->bytes/utf-8 x) #"\33[m")))
#|
(define (formatted-printer s)
((if (equal? s "You have to be bold to do it.\n") b i) s)); Works fine, preferred as it is concise. Do the same with cond!!!
(define (formatted-printer s)
(if (equal? s "You have to be bold to do it.\n")
(b s)
(i s))); Works fine, too verbose, though.|#
#|
(define (formatted-printer s); Works fine
(cond
((equal? s "You have to be bold to do it.\n") (b s))
((equal? s "You have to be Italian in order to eat pasta.\n") (i s))
))
|#
(define (formatted-printer s)
((cond
((equal? s "You have to be bold to do it.\n") b)
((equal? s "You have to be Italian in order to eat pasta.\n") i)
s)));Does not work: cond: bad syntax (clause is not a test-value pair)
(formatted-printer "You have to be bold to do it.\n")
(formatted-printer "You have to be Italian in order to eat pasta.\n")
Sadly, when I try to apply double parentheses around cond
, as it did the trick around if
, I get:
cond: bad syntax (clause is not a test-value pair)
at: s
in: (cond ((equal? s "You have to be bold to do it.\n") b) ((equal? s "You have to be Italian in order to eat pasta.\n") i) s)
location...:
The comments hint what I am aiming at.
Is it at all doable to select with cond
only the operator like it is with if
?
In your if
version you are ending the if
form aplying the result with s
as the operand. In the cond
version you don't. It should be like this:
(define (formatted-printer s)
((cond
((equal? s "You have to be bold to do it.\n") b)
((equal? s "You have to be Italian in order to eat pasta.\n") i)
(else (error "no matching string for formatted-printer")))
s))
Notice the else
. If you don't have that you can in the future end up with a weird application: not a procedure for #<void>
since if none of the strings match and you don't have an else
Racket will use its undefined value as the result and that can not be called as a procedure.
You can even make it more clear:
(define (formatted-printer s)
(define formatter
(cond
((equal? s "You have to be bold to do it.\n") b)
((equal? s "You have to be Italian in order to eat pasta.\n") i)
(else (error "no matching string for formatted-printer"))))
(formatter s))
Since you're using Racket and probably DrRacket you can even debug this much easier with adding a breakpoint at (formatter s)
to investigate the result of what formatter
was set to.