728x90
728x90
2020/05/21 - [컴퓨터 전공 공부/프로그래밍언어론] - [프로그래밍 언어/Racket] Racket introduction - 컴도리돌이-(1)
2020/06/04 - [컴퓨터 전공 공부/프로그래밍언어론] - [프로그래밍언어/Racket] Macros - 컴도리돌이-(3)
Racket의 기본 구조
(연산자 피연산자1 피연산자2)
(- 5 2)
(+ 3 4)
(* 2 3)
Racket에서는 전위 표기법을 사용한다.
<example>
#lang racket
(define x 3)
(define y (+ x 2))
(define cube ; function
(lambda (x)
(* x (* x x))))
(define pow ; recursive function
(lambda (x y)
(if (= y 0)
1
(* x (pow x (- y 1))))))
Racket의 함수 구조
(define (함수명 매개변수) 함수 표현식)
(define (f w h) (* w h))
(define (g w h)
(+ (* 2 w)
(* 2 h)))
#;;test case
#(f 1 1) ;1
#(g 1 1) ;4
#(f 1 2) ;2
#(g 1 2) ;6
#(f 2 1) ;2
#(g 2 1) ;6
#(f 2 2) ;4
#(g 2 2) ;8
set! 함수
<example>
(set! x e)
(define b 3)
(define f (lambda (x) (* 1 (+ x b))))
(define c (+ b 4)) ; 7
(set! b 5)
(define z (f 4)) ; 9
(define w c) ; 7
3이라는 데이터 값으로 정의된 b가 set! 함수로 인해서 5라는 데이터 값으로 변경되었다.
cond 함수 (조건 표현)
조건 표현(conditional function) 사용법. 대괄호를 소괄호로 해도 되나, 대괄호로 사용하는 게 가독성 측면에서 더 좋다.
else는 위의 질문들이 모두 false일 때 결과 값을 반환하며 없어도 상관없다. 위에서 아래로 차례대로 조건을 검사한다.
(cond
[질문 답]
...
[질문 답]
[else 답])
(define (sum xs)
(cond
[(null? xs) 0]
[(number? (car xs))(+ (car xs) (sum (cdr xs)))]
[#t (+ (sum (car xs)) (sum (cdr xs)))]))
커링(curring)
다중 인수를 가진 함수를 단일 인수를 갖는 함수들의 함수열로 바꾸는 것을 말한다.
(define (sum xs)
(if (null? xs) 0
(+ (car xs) (sum (cdr xs)))))
(define (my-append xs ys)
(if (null? xs) ys
(cons (car xs) (my-append (cdr xs) ys))))
(define (my-map f xs)
(if (null? xs) null
(cons (f (car xs)) (my-map f (cdr xs)))))
List processing
비어있는 리스트 : null
cons constructor : cons
리스트의 첫 인자 : car
리스트의 첫 인자를 제외한 값들 : cdr
리스트가 비어있는지 검사 : null?
(cons null null) ; null
(cons 인자1 인자2)
(car 인자 리스트-인자)
(cdr 인자 리스트-인자)
(null? 리스트)
(define xs (list 인자1, 인자2, 인자3 ...))
(define xs '(인자1 인자2 인자3 ...))
<example>
(define (sum xs)
(if (null? xs)
0
(+ (car xs) (sum (cdr xs)))))
(define (my-append xs ys)
(if (null? xs)
ys
(cons (car xs) (my-append (cdr xs) ys))))
(define (my-map f xs)
(if (null? xs)
null
(cons (f (car xs)) (my-map f (cdr xs)))))
Local bindings : let, let*, letrect, define (중요!)
<example>
(define x 3)
(define y (+ x 2))
(define (silly-double x)
(let ([x (+ x 3)][y (+ x 2)]) (+ x y -5))) ; 6
; x=3, y=5이기 때문에 let함수로 x를 다시 6,
; y는 x+2이기 때문에 5의 지역변수로 두어서 x+y-5를 하였다.
(define (silly-double x)
(let* ([x (+ x 3)][y (+ x 2)]) (+ x y -8))) ; 6
;let*에서는 마지막 결과 값이 x+y-8 임에 불구하고 똑같은 결과 값이 나왔다.
;이것은 y = x+2에서 x가 let* 함수 앞에 있는 지역변수 x= x+3의 결과 값을 가지고 사용하였다.
;(가장 최근의 전에 있는 x값을 받아왔다.)
(define (silly-triple x)
(letrec ([y (+ x 2)][f (lambda(z) (+ z y w x))][w (+ x 7)]) (f -9)))
; y = x(3) + 2, w = x(3) + 7, f (-9) = z + 5 + 10 + 3
; letrec에서 이상한점을 확인을 해야한다.
; f함수에서 w값을 사용하였다. 하지만 w의 지역변수 값은 f함수 후에 나온다.?
; 즉 letrec은 all the binding으로 binding된 인자들은 순서 상관없이 값을 받아온다.
; + letrec대신 let 또는 let*을 대신 사용하면 당연히 오류난다.
728x90
728x90