練習問題 1 (解答例)


1.1 二つの実数 a, b を受けとり、二乗和(つまりa*a+b*b)の平方根を返す関 数 sqsum を書け

素直にそのままかきましょう。
> (define (sqsum a b)
      (sqrt (+ (* a a)
               (* b b))))
> (sqsum 3.0 4.0)
5.0

問題

1.2 二つの実数a, b を受けとり、絶対値の大きい方の値をそのまま返す関数 absmax を書け。ただし、絶対値が等しい場合はaを優先するものとする。

これも素直にかけばよい。 つまり、 a, b それぞれの絶対値を比較し、 a の絶対値の方が大きいか等しければ a を返し、 さもなくば b を返す。 >= を知らない場合でも、 < を使うか =, > を使えば書けるはずです。
> (define (absmax a b)
    (if (>= (abs a) (abs b))
        a
        b))
> (absmax 2.4 (/ -5 2))
-5/2

問題

1.3 a, bをうけとり、a, b ともに数字の場合はその和を返し、 ともに文字列の場合は文字列を繋げたものを返し、 それ以外のときは 0 を返す関数 num-str-add を書け。
まず、値が数字であるか、文字であるかを調べるには、 number?, string? をもちいればよいです。この場合、条件文が三つに分かれていたので、 cond を使っていますが、他のもので代用しても構いません。
> (define (num-str-add a b)
      (cond ((and (number? a) (number? b))
             (+ a b))
            ((and (string? a) (string? b))
	     (string-append a b))
	    (else 0)))
> (num-str-add (/ 2 3) (/ 1 3))
1
> (num-str-add "Work " "Hard!")
"Work Hard!"
> (num-str-add "strange pair" (* 2 4))
0

問題

1.4 西暦の年号を与えられた時、うるう年かどうかの真偽値を返す関数 leap を書け。ただし、うるう年とは、原則としては4で割り切れる年であるが、100 でも割り切れるならば、400でも割り切れなくてはならない。(つまり、西暦 2000年は、100で割り切れるが、400でも割り切れるのでうるう年である)。

表現の仕方はいくらでもあるので、どれがいいとはいわない。 leap, leap2 の様に一つの論理式として記述する方法が考えられる (論理式の書き方は他にもいろいろある)。 また、 leap3,leap4 の様に記述することもできるであろう。 発想は leap1,leap2 と同じであるが、 cond をもちいて場合分けという形で表現している。
> (define (leap1 year)
      (and (= (remainder year 4) 0)
           (or (not (= (remainder year 100) 0))
	           (= (remainder year 400) 0))))
> (define (leap2 year)
      (or (= (remainder year 400) 0)
          (and (not (= (remainder year 100) 0))
               (= (remainder year 4) 0))))
> (define (leap3 year)
      (cond ((not (= (remainder year 4) 0)) #f)
            ((not (= (remainder year 100) 0)) #t)
            ((not (= (remainder year 400) 0)) #f)
            (else #t)))
> (define (leap4 year)
      (cond ((= (remainder year 400) 0) #t)
            ((= (remainder year 100) 0) #f)
            ((= (remainder year 3) 0)   #t)
	    (else #f)))
> (leap 2000)
#t
> (leap 1999)
#f
> (leap 1996)
#f
> (leap 2100)
#f

問題


99.9.29/ Tomio KAMADA: kamada@cs.kobe-u.ac.jp