1番目の要素 apple 2番目の要素 orange 3番目の要素 cake
1番目の要素 シンボル apple 2番目の要素 リスト (orange cake) 3番目の要素 シンボル banana
1番目の要素 シンボル apple 2番目の要素 リスト ((orange) (cake)) 3番目の要素 数 512
リストの長さ 3
リストの長さ 3 4ではない
gosh> 1 1 gosh> 3.13 3.13 gosh> -1/3 -1/3
gosh> apple *** ERROR: unbound variable: apple
gosh> apple *** ERROR: unbound variable: apple エラー: アンバウンド バリアブル: apple アンバウンド: バインドされていない バリアブル: 変数 バインドされていない変数を評価するとエラー
gosh> + #<subr (+ :rest args)>
gosh> (+ 1 2) 3
1と2を足した結果に3を足した結果を求めよ 算数ではこう書く (1 + 2) + 3
何と何を足すかを明確にするためにはカッコがあった方が良いよね 1と2を足した結果に3を足した結果を求めよ 忠実に書くなら、
((1 + 2) + 3)
(+ (+ 1 2) 3)
何と何を足すかを明確にするためにはカッコがあった方が良いよね 1に 2と3を足した結果を足した結果を求めよ なら 忠実に書くなら、
(1 + (2 + 3))
(+ 1 (+ 2 3))
普通の算数の足し算 (1 + (2 + 3)) ここで、+ は演算子(オペレーター)と呼ばれる 1や2や3は演算の対象のデータで被演算子(オぺランド)と呼ばれる 被演算子が2つ必要な演算は2項演算という 被演算子が1つ必要な演算は単項演算という 被演算子が0個の演算は無項演算という ( 1より大きいn個の被演算子が必要な演算はn項演算という あと被演算子の個数のことは アリティとも呼ばれる、2項演算ならアリティは2) で、被演算子の間に演算子を置くのが、普通の算数の記法で中置記法 Scheme では (+ 1 (+ 2 3)) で演算子を 最初に書く 前置記法 ポーランド人の論理学者ウカシェヴィチが考案したとされていて 前置記法はポーランド記法とも呼ばれる。演算子を最後に書くのは 後置記法 逆ポーランド記法ともいう(プログラミング言語Forthとかでググってみよ)
関数適用も リストで表す
(f 1)
と表す
f(x)は 1引数の関数だけれど 2引数の関数 g(x,y) でも
xに1,
yに2
を入れて関数の値を求めることを
リストを使って (g 1 2)
と表す
(+ 1 (+ 2 3))
これは3要素のリスト (長さ3のリスト)、評価する。 先頭要素の+が演算子 2番目の要素 1 , 3番目の要素 (+ 2 3) が被演算子 まず、先頭以外の要素を、それぞれ評価する
1を評価して1
(+ 2 3)を評価して5
もちろんこれも3要素のリストで
先頭の要素 + が演算子,
2番目の要素 2, 3番目の要素 3が被演算子
それぞれ評価して 2 ,3 を得て 2と3を足して5
(+ 1 5)
が評価されて 6が(+ 1 (+ 2 3))
の値
hoge が 1つ引数をとって2倍にして返す関数 hoge(x) = x * 2 : もちろんこれは scheme の式ではない fuga が 2つ引数をとって最初の引数の値から2番目の値を引いて返す関数 fuga(x,y) = x - y : もちろんこれも scheme の式ではない だったら (hoge 3) は 6を返す (fuga 4 3)は 1を返す (hoge (hoge 3)) は 12を返す (hoge (fuga 4 3))は 2を返す (fuga (hoge 2) 5) は -1を返す
hoge が 1つ引数をとって2倍にして返す関数 hoge(x) = x * 2 : もちろんこれも scheme の式ではない fuga が 2つ引数をとって最初の引数の値から2番目の値を引いて返す関数 fuga(x,y) = x - y : もちろんこれも scheme の式ではない schemeでは 関数の定義は スペシャルフォーム define , lambda を使う(define hoge (lambda (x) (* x 2)))
と書く(define fuga (lambda (x y) (- x y)))
と書く
これで(hoge (hoge 3))
は 12を返す(hoge (fuga 4 3))
は 2を返す(fuga (hoge 2) 5)
は -1を返す
実は lambda が関数(手続き)を作る特別な手続きなので 引数を2倍にして返す手続き(lambda (x) (* x 2))
を使えば((lambda (x) (* x 2)) ((lambda (x) (* x 2)) 3))
は 12を返す さらにdefine が シンボルに値を バインドする特別な手続きで(define hoge (lambda (x) (* x 2)))
とすることで((lambda (x) (* x 2)) ((lambda (x) (* x 2)) 3))
を(hoge (hoge 3))
と書ける
(+ (* (- 5 4) (- 3 1)) 10)
演算子 + 1つ目の引数 (* (- 5 4) (- 3 1)) 2つ目の引数 10
(* (- 5 4) (- 3 1))
演算子 * 1つ目の引数 (- 5 4) 2つ目の引数 (- 3 1)
(- 5 4)
演算子 - 1つ目の引数 5 これは評価すると値は5 2つ目の引数 4 これは評価すると値は4- に 5 4 が渡されて 1が計算されて返る
(- 3 1)
演算子 - 1つ目の引数 3 これは評価すると値は3 2つ目の引数 1 これは評価すると値は1- に 3 1 が渡されて 2が計算されて返る
(* 1 2)
演算子 * 1つ目の引数 1 2つ目の引数 2* に 1 2 が渡されて 2が計算されて返る
(+ (* (- 5 4) (- 3 1)) 10)
= (+ (* 1 2) 10)
= (+ 2 10)
= 12