조건문: if, cond, and, or
조건문: if, cond, and, or
조건 분기는 Racket 프로그램에서 가장 자주 만나는 형태 중 하나예요. if부터 시작해서 분기가 여럿일 때 쓰는 cond, 그리고 여러 조건을 묶는 and와 or까지 차례로 살펴볼게요.
출처: Racket Reference
본문
조건문에 대한 소개는 The Racket Guide의 Conditionals에서 다룹니다.
if 구문
syntax
(if test-expr then-expr else-expr)
test-expr를 평가합니다. 그 결과가 #f가 아닌 어떤 값이든 생기면 then-expr가 평가되고, 그 결과가 if 폼의 결과가 됩니다. 그 외의 경우에는 else-expr가 평가되고, 그 결과가 if 폼의 결과가 됩니다. then-expr와 else-expr는 if 폼에 대해 꼬리 위치(tail position)에 있습니다.
예시:
> (if (positive? -5) (error "doesn't get here") 2)
2
> (if (positive? 5) 1 (error "doesn't get here"))
1
> (if 'we-have-no-bananas "yes" "no")
"yes"
cond 구문
syntax
(cond cond-clause ...)
cond-clause = [test-expr then-body ...+]
| [else then-body ...+]
| [test-expr => proc-expr]
| [test-expr]
cond에 대한 소개는 The Racket Guide의 Chaining Tests: cond에서 다룹니다.
else로 시작하는 cond-clause는 마지막 cond-clause여야 합니다.
cond-clause가 하나도 없으면 결과는 #<void>입니다.
[else then-body ...+]만 있는 경우에는 then-body들이 평가됩니다. 마지막 then-body를 제외한 나머지의 결과는 무시됩니다. cond 폼에 대해 꼬리 위치에 있는 마지막 then-body의 결과가 전체 cond 폼의 결과가 됩니다.
그 외의 경우에는 첫 번째 test-expr가 평가됩니다. 그 결과가 #f라면, 결과는 나머지 cond-clause들을 가진 cond 폼과 같으며, 이는 원래 cond 폼에 대해 꼬리 위치에 있습니다. 그 외의 경우 평가는 cond-clause의 형태에 따라 달라집니다:
[test-expr then-body ...+]
then-body들이 순서대로 평가되고, 마지막 then-body를 제외한 나머지의 결과는 무시됩니다. cond 폼에 대해 꼬리 위치에 있는 마지막 then-body의 결과가 전체 cond 폼의 결과를 제공합니다.
[test-expr => proc-expr]
proc-expr가 평가되어 인자를 하나 받는 프로시저를 만들어야 하며, 그렇지 않으면 exn:fail:contract 예외가 발생합니다. 이 프로시저는 cond 표현식에 대해 꼬리 위치에 있는 test-expr의 결과에 적용됩니다.
[test-expr]
test-expr의 결과가 cond 폼의 결과로 반환됩니다. test-expr는 꼬리 위치에 있지 않습니다.
예시:
> (cond)
> (cond
[else 5])
5
> (cond
[(positive? -5) (error "doesn't get here")]
[(zero? -5) (error "doesn't get here, either")]
[(positive? 5) 'here])
'here
> (cond
[(member 2 '(1 2 3)) => (lambda (l) (map - l))])
'(-2 -3)
> (cond
[(member 2 '(1 2 3))])
'(2 3)
else 구문
syntax
else
cond와 같은 폼 안에서 특별하게 인식됩니다. 표현식으로서의 else 폼은 문법 오류(syntax error)입니다.
=> 구문
syntax
=>
cond와 같은 폼 안에서 특별하게 인식됩니다. 표현식으로서의 => 폼은 문법 오류입니다.
and 구문
syntax
(and expr ...)
and에 대한 소개는 The Racket Guide의 Combining Tests: and and or에서 다룹니다.
expr이 하나도 없으면 결과는 #t입니다.
expr이 하나만 있으면 그것은 꼬리 위치에 있으므로, and 표현식의 결과는 그 expr의 결과입니다.
그 외의 경우에는 첫 번째 expr이 평가됩니다. 그 결과가 #f라면 and 표현식의 결과는 #f입니다. 그 외의 경우 결과는 나머지 expr들을 꼬리 위치에 가진 and 표현식과 같습니다.
예시:
> (and)
#t
> (and 1)
1
> (and (values 1 2))
1
2
> (and #f (error "doesn't get here"))
#f
> (and #t 5)
5
or 구문
syntax
(or expr ...)
or에 대한 소개는 The Racket Guide의 Combining Tests: and and or에서 다룹니다.
expr이 하나도 없으면 결과는 #f입니다.
expr이 하나만 있으면 그것은 꼬리 위치에 있으므로, or 표현식의 결과는 그 expr의 결과입니다.
그 외의 경우에는 첫 번째 expr이 평가됩니다. 그 결과가 #f가 아닌 값이라면 그 결과가 or 표현식의 결과입니다. 그 외의 경우 결과는 나머지 expr들을 꼬리 위치에 가진 or 표현식과 같습니다.
예시:
> (or)
#f
> (or 1)
1
> (or (values 1 2))
1
2
> (or 5 (error "doesn't get here"))
5
> (or #f 5)
5