Elytraflyer 的博客

Racket学习笔记1————变量,函数和条件判断语句

Racket学习笔记1————变量,函数和条件判断语句

变量

变量的定义:

(define id expr)

e.g

(define a 1)

函数

函数的定义:

(define (funcName arg1 arg2 ...) body)

e.g

(define (double x)
	(+ x x))

函数的调用:

(funcName arg1 arg2 ...)

e.g

(define (drink)
	(printf "drink a cup of water\n"))
(drink)

一个函数既可以被当作函数的参数,也可以作为返回值。

(define (twice func val)
	(func (func val)))
(define (make-lambda-test s2)
    (lambda (s1) (string-append s1 s2)))
(twice (make-lambda-test "!") "hello")    ; 返回 "hello!!"

在这个例子中,make-lambda-test把(lambda (s1) (string-append s1 s2)) 作为参数传入twice函数中,twice又把"hello"传入了这个匿名函数中。

在racket里,你还可以在一个函数中定义一个作用域在该函数内的函数。

e.g

(define (print-angrily s)
    (define (anger v) ; 作用域仅限于print-angrily
      (string-append v "!!!"))
    (printf "~a\n" (anger s)))
(print-angrily "what") ; what!!!
匿名函数

在racket中,匿名函数用lambda表示:

(lambda (arg1 arg2 ...) body)

e.g

(lambda (x) (println x))

(define (id arg1 arg2 ...) body) 与 (define id (lambda (arg1 arg2 ...) body)) 等价。

局部变量

要创建一个局部变量,使用

(let ([id1 expr1] ...) body)

其中定义的变量的作用域仅限于let语句内。e.g.

(let ([x 1]
      [y 2])
    (printf "~a ~a" x y)) ; 1 2

但是,在用let语句定义的变量不能在定义时使用对方。如下代码会报错:

(let ([x 1]
      [y x])
    (printf "~a ~a" x y))
x: undefined;
 cannot reference an identifier before its definition
  in module: top-level
 [,bt for context]

这时就要用到let* 语句:

(let* ([x 1]
       [y x])
     (printf "~a ~a" x y)) ; 1 1

条件语句

if条件语句(相当于其他语言里的if...else语句):

(if cond true-expr false-expr)

e.g

(if (equal? 3 "hello")
      (print true)
      (print false))

在racket里,还有逻辑与、逻辑或和逻辑非三种逻辑运算符:

(and (expr)) ; 逻辑与
(or (expr))  ; 逻辑或
(not (expr)) ; 逻辑非

cond语句(相当于多个if语句):

(cond [expr then-expr]
	  [expr => proc]
	  [else then-expr])

e.g

(define score 100)
(cond [(>= score 90) "A"]
	  [(>= score 80) "B"]
      [(>= score 70) "C"]
      [(>= score 60) "D"]
      [else "E"])

其中

[expr => proc]

可以把expr的结果作为参数传递给proc.

e.g

(cond [(member 1 '(1 2 3)) => (lambda (k) (map sqr k))])

注意:else语句只能放在cond语句的最后

#programming #racket