Hatena::ブログ(Diary)

暗号、数学、時々プログラミング このページをアンテナに追加 RSSフィード

2009-06-25

【第5話】もっとプログラムっぽく!(後編)

| 03:41 | 【第5話】もっとプログラムっぽく!(後編)を含むブックマーク


「じゃあ、まずは『組』の定義からいってみようか?あ、そうそう。『組』は英語だと"Tuples"って表現するみたいだから、そのままカタカナ読みして"タプル"って言う人もいるみたいね」

と僕の顔を見るリンダさん。

「はい。複数のデータを1つにまとめることで、それ自身に何か意味を持たせたデータの事を『組』と呼びます。 XY 平面上の座標とか、国数英理社の点数とか、セットになって初めて意味があるものを上手く取り扱うための概念ということだと思います」

という僕の説明に

「『組』の中の1つの要素としてさらに『組』を使うようなケースがあるってトコロが面白いよね。例えば、、」

(( 10, 47 ), "Aの座標");;
val it : (int * int) * string = ((10, 47), "Aの座標")

「みたいな感じで実際にデータを考えてみると分かりやすいと思う」

と横からミラっちが付け加える。

うっ。なかなかやるな。

「あと、実際に動作を見た限り OCaml との差分は無かったと思います」

僕には特に付け足すことがないので、ここで締めてみた。

「うん。そうみたいだね」

と頷くリンダさん。

「それじゃ、早速この『組』を実際に使う話、つまりパターンマッチングの話にうつろうか?」

「はい!」


・・・・・・

溶けかけたアイスを1口食べた後、リンダさんが口を開いた。

「じゃあ、恒例の質問。パターンマッチって何かしら?」

「今度は私が!」

おっ、ミラっち。なんか今日はえらいノリ気だなぁー。

「どうぞ」

ニコニコと先を促すリンダさん。

「えっと。 複数のデータから成るデータから、意図したデータを取り出す為に使う技術ってところかな。具体的には、、、」

ここでパソコンに向かうミラっち。

matchwith
 パターン ->

「match の後に指定された式、まぁデータよね。これについて with 以下でどういう操作をするか記述するようになってるわ」

と、ここまで言ってリンダさんの顔を見るミラっち。

「『パターン』ってところには match の後で指定されてる式を抽象化したもの、つまり"パターン変数"を使って書き直した式が書かれ、矢印の先に、そのパターン変数を使って具体的にどんな処理をするのか?が書いてある、ってイメージになるよね。あ、関数定義なんかの場合とか考えると match の後に来るのが具体的なデータになるとは限らないけど」

と、そこにすかさず僕が付け加える。

「うん。うん」

満足そうに頷くリンダさん。へへへっ。

あれ、でもなんかミラっちが不機嫌そうに僕を見てるぞ。うう、余計なフォローだったかな?

「それじゃ、何か気になったところはあるかな?」

とリンダさん。マイペースな人で助かるなぁ。

引数の部分に直接パターンを書けてしまう、って部分も含めて OCaml と動作は共通だったと思う」

首を振りつつミラっちが答え、「そっちはどう?」とばかりに僕を見る。

「基本的にはミラっちと同じなんですけど、、」

言いながら僕は次のファイルを読み込む。

(* 目的:組で表された平面座標をふたつ受け取ったら、その中点の座標を返す *) 
(* chuten : float * float -> float * float -> float * float *) 
let chuten point1 point2 = match point1 with 
  ((x1: float), (y1: float)) -> (match point2 with 
    ((x2: float), (y2: float)) -> ((x1 + x2) / 2.0, (y1 + y2) / 2.0)) 
 
(* テスト *) 
let test1 = chuten (0.0, 0.0) (1.0, 2.0) = (0.5, 1.0) 
let test2 = chuten (2.3, 5.1) (7.6, 1.7) = (4.95, 3.4) 
let test3 = chuten (-3.8, -2.4) (3.4, -1.2) = (-0.2, -1.8) 

printfn "test1: %b"  test1
printfn "test2: %b"  test2
printfn "test3: %b"  test3

「この問題7.4の為に作ったコードを実際に実行してみると・・・」

> [Loading C:\Program Files\SharpDevelop\3.0\bin\test9.fs]
test1: true
test2: false
test3: false

namespace FSI_0025
  val chuten : float * float -> float * float -> float * float
  val test1 : bool
  val test2 : bool
  val test3 : bool

「って感じで、一部上手くいかないんですよね。。回答例見ても、、」

(* ただし test2, test3 の場合など、小数を2進数で表すときの *) 
(* 誤差のため true にならないことがある *) 

「ってなってるんで、『この動作は変だ!』って騒ぐ話じゃなさそうだとは思うんですけど、、、」

「そうね。プログラム自身が間違ってるってコトはないと思うから、少なくともこの段階で理解しておくべき事は身についてると思って大丈夫だと思うよ」

と、リンダさん。リンダさんが言うには、これをスッキリと説明するのは難しいみたい。後でこういうところが足を引っ張ったりするんじゃないかとちょっと心配ではあるんだけど、ここはまぁ敢えて深入りしないようにしておこうかな。。

「まずは大枠を押さえる、ってコトよね」

ミラっちも少し難しい顔をしてたけど、一応は自分の中で納得したみたい。

「ごめんねー。もっと上手く説明できれば良いんだけど、、」

少し申し訳なさそうな顔をするリンダさん。

「あ、いえいえ。ミラっちの言う通り、今は基本を身に付ける為の勉強ですから」

リンダさんの真似をして親指を立ててみる僕。

プッと吹き出すリンダさん。よしよし、空気が軽くなったぞ。

「それじゃ、今日はここまで。次回は8章のレコードと、9章のリストをやるよ」

言い終わるとリンダさんは残りのクリームソーダを飲み始める。

「了解でーす」

うーん、ちょっとずつだけど面白くなってきたなー、プログラミング。そういえば予習してても義務感みたいなのが全然ないぞ。もしかして、僕、結構ハマってる??


・・・・・・

「良い人だったね」

リンダさんが去った後、ポツリとミラっちが呟く。

「え? ああ、リンダさんの事?」

と聞き返す僕。

「うん。。」

ん? ミラっちは何か考え事してるのかな?

「もうちょっと・・・」

「え?」

「もうちょっと、ココに居ても良い?」

僕を見るミラっち。

「あ、うん。いいよ。別にこの後に予定があるワケじゃないし。」

そう言って僕はコーヒーのお替りを取りに行く為に席を立った。

どうせなら次回の予習をここでしちゃおうかな。うん。


【本日使った本】

プログラミングの基礎 (Computer Science Library)

プログラミングの基礎 (Computer Science Library)



次回につづく。

osiireosiire 2009/06/26 02:53 decimalですか。確かにこーゆーのが独学の障害になるんですよね。オッカムル少年がんばれー。

hamatsu1974hamatsu1974 2009/06/26 08:26 はい。どのタイミングでどこまで深くやるか?ってサジ加減が難しいんですよねー。