Silverlight をインストールするには、ここをクリックします*
Japan変更|サイトマップ
MSDN
|MSDN ライブラリ|デベロッパー センター|ダウンロード情報|開発ツール製品|コミュニティ|ご意見・ご要望|サイトマップ
MSDN Home > Student > プログラミング チャレンジ スクエア > 第 5 章 単語帳を作ろう VB 編

第 5 章 単語帳を作ろう


サンプルプログラムのダウンロード (chap5_vb.msi, 235 KB)

※ また、サンプルプログラムは、あらかじめ Visual Basic 2005 Express Edition と同じパソコンにインストールしておいてください。
   設定方法は こちら


この章でやること
・ 単語帳プログラムを完成させます。
・ 文字列を変数として扱う方法と、複雑な条件分岐について体験します。

第 5 章 単語帳を作ろう
問題ファイルを読み込ませよう
問題と解答を表示する準備をしよう
問題と解答を実際に表示しよう





第 4 章で時間を計るプログラムを作った翔太君と美咲さんですが、翔太君はそろそろ宿題が気になっているようです。


翔太:なんとか第 3 章まで終わったね。でも、そろそろ宿題の方もやらないと。
健一:宿題? あ、そういえば、僕も明日までに報告書を作って社に出さないといけないんだった。
美咲:健一さんも宿題があるのね。じゃあ、とりあえずプログラムの勉強は一休みして、みんなで宿題を片付けましょうか。
健一:今日はこの辺で家に帰ることにするよ。今度はいつこられるか分からないけど、もしなにかプログラミングで分からないことがあったら電話してきて。
翔太:うん、分かった。今日はどうもありがとう。
美咲:健一さん、ありがとう。
健一:それじゃ、また。


健一さんが帰った後、二人は宿題に取り掛かりましたが、二人で相談しながら進めたおかげで、あっという間に片付いてしまいました。


翔太:なんだ、こんなに簡単に終わっちゃうんなら、もっと早くやっておけばよかったな。
美咲:ほとんど私に聞いてばっかりいたじゃない。でも、そんなに量が多くなくてよかったわね。・・・あら? これは何?
翔太:しまった! 明日小テストがあるんだ。それはその予習用のプリントだよ。すっかり忘れてた。
美咲:どれどれ・・・ 英単語のテストか。暗記すればいいのね。
翔太:仕方ない、これから朝までじっくり覚えるよ。
美咲:ちょっと待って。そういえば、入門マニュアルに単語帳の話が出てた気がするわ。
翔太:単語帳?
美咲:さっき、少し先までページをめくって読んでたときに、そんな名前が出てきたような・・・ あ、あったわ。第 5 章って、次の章だったのね。
翔太:へぇー、次の章で単語帳を作るのか。うーん、健一さんは帰っちゃったしなぁ・・・
美咲:やってみる? もし作れたら、それを使って単語を覚えるのも面白そうよ。
翔太:ちょっと様子を見て、できそうだったらやってみようか。
美咲:じゃ、始めましょう!


翔太君は、美咲さんにうながされて再びパソコンに向かいました。


翔太:まずはサンプルを開くところからだね。


プログラムメニューから Visual Basic 2005 Express Edition を立ち上げて、サンプルファイルフォルダの中の Part5_VB\Part5_Base フォルダにある Part5.sln を開きます。そして、[ソリューション エクスプローラ] から、[Form1.vb] を開きます。





翔太:「問題」と「正解」か。クイズみたいで面白そうだな。まず問題が表示されて、解答欄に解答を入力するのかな。デバッグ ボタンを押して確かめてみよう。


デバッグ ボタンをクリックして、プログラムを実行します。[進む] ボタンをクリックしても、特に何も起こりません。





翔太:[進む] ボタンを押すと、何かが起こるんだろうな、きっと。それをプログラミングするのがこの章のテーマなのかもしれないね。
美咲:デザインは単語帳みたいだけど、実際の単語帳とは少し違うわね。やっぱりプログラムだとある程度は仕方ないのかしら。
翔太:そうだね。まさか実際に単語帳を持っているようにはできないし。
でも、これはこれで楽しそうだから、とりあえずやってみようか。
美咲:うん。そういえば、ソリューション エクスプローラに見たことのない名前が増えているわ。章を追うごとにだんだん増えていくような気がするけど、他の項目は見なくて平気なのかしら。





翔太:今までも必要な項目は入門マニュアルに出ていたから、今回も必要なら説明があるんじゃないかな。だから、特に何も言われなければ触らない方が無難だと思うよ。
美咲:そうね。どうしても分からなくなったら、健一さんに電話しましょう。


二人は入門マニュアルを見ながら先に進めることにしました。




<問題ファイルを読み込ませよう>

翔太:まず、デバッグ ボタンで実行していた画面を閉じて、と。
美咲:最初にやるのは「問題ファイルを読み込ませよう」ってところね。
翔太:ファイルを読み込ませる? 読み込むのはプログラム、だよね・・・ どこかに置いてあるファイルをプログラムが読み込むにはどうすればいいか、ってことか。
美咲:ということは、そもそも問題ファイルっていうものがどこかに保存されていないといけないわね。


サンプルプログラムが保存されているフォルダを開くと、同じフォルダの中に単語帳.txtというファイルが入っていることが分かります。


翔太:これを使うのか。中身は、簡単な英単語みたいだね。
美咲:そうか! 問題はテキストファイルに保存していて、それをプログラムが利用して出題してくれるんだわ。よかったじゃない、翔太君。
翔太:よかった、ってどうして?
美咲:だって、問題文のテキストファイルを作れば、このプログラムを使って暗記ができるかもしれないじゃない。プログラムの中に英単語を書き込むよりも簡単にできるわよね。
翔太:あっ、そうか。・・・でも、問題文を作るのは自分なんだよね・・・
美咲:何か言った?
翔太:なんでもない! とりあえずやるだけやってみるかな・・・


美咲:まず、やるのは、フォームのプロパティ ウィンドウを開く、だって。フォームって言うのは、さっき開いた Form1 のことよね。
翔太:そのプロパティ ウィドウを開くってことは、画面のどこかを右クリックしてプロパティを選べばいいのかな。


今回使うサンプルでは、画面のほとんどがコントロールなどで埋まっていて、Form1 のプロパティ ウィンドウを表示できる場所があまり見当たりません。難しければ、プロパティ ウィンドウを開いてから、タイトルバーの「単語帳」と書かれている部分をクリックしてみてください。





翔太:それで、ここで何をやればいいの?
美咲:[イベント] アイコン でイベント一覧を表示して、一覧にある [Load] を見て。その右側のコンボ ボックスに「Form1_Load」と入力して [Enter] キーを押すの。





翔太:コードを書く画面が開いたよ。





美咲:リスト 5-1-1 のコードが追加されてるのを確認してみて。


リスト 5-1-1 は、後で読み返すときに分かりやすいようにコメント文を追加した形で紹介しています。実際に上記の手順でコードを追加した場合、コメントは追加されていませんので、必要に応じて自分で書き加えてください。以後のリストについても同様です。


リスト 5-1-1

    ' Form をロードしたときの処理
    Private Sub Form1_Load(ByVal sender As Object, ByVal e As System.EventArgs) 
    Handles Me.Load

    End Sub


翔太:この Load っていうのは何のイベントなんだろう?
美咲:入門マニュアルによると、プログラムを実行したときに一番最初に行うイベントなんだそうよ。イベント自体は表には出てこないから、実行結果によってはユーザーの目には見えないで終わることもあるらしいわ。
翔太:なるほど。ここで問題文を読み込むようにすれば、プログラムを実行したときに最初から使えるようになってるってわけか。
美咲:この「Private Sub Form1_Load〜」と「End Sub」の間の行にリスト 5-1-2 のコードを追加するんだって。


リスト 5-1-2

       ' Wordbook に問題と解答データを読み込む
        Wordbook.Read("../../../../単語帳.txt")


翔太:新しい名前が出てきたね。Wordbook? Read?
美咲:Wordbook って、さっきのソリューション エクスプローラにも出てきてたし、よく見たらこのコード エディタの上から 2 行目にも「Private Wordbook As New Wordbook」って書いてあるわね。えーっと、入門マニュアルによると・・・


Wordbook というのは、テキストファイルから問題と解答のデータを読み取るためのプログラムです。第 4 章では DigitalTimer という特別なコントロールをあらかじめ用意して、翔太君たちや皆さんにはそれをそのまま使ってもらいましたが、この章では、Wordbook がそれにあたります。


翔太:わざわざこうして作ってくれてるっていうことは、かなり複雑なことをやってくれてるんだろうね。
美咲:この Wordbook みたいなプログラムのことをクラスっていうらしいわ。
翔太:コントロールとはどう違うの?
美咲:ほとんど同じような物だって書いてあるわ。プログラム全体の中でどのように使うのか、使い方が異なるのが一番大きな違いみたい。コントロールだと、デジタル時計の画面のような表示部分があるけど、クラスはない、とか。また、コンポーネントとも違って、画面に貼り付けるんじゃなくて、コードの中で呼び出すだけみたいね。
翔太:ふーん。クラスとコントロールとコンポーネントか。要するにこれらに共通してるのは、あらかじめ特定の機能についてそれぞれの形で作っておけば、使い回しができる、ってことなのかな。
美咲:今までの話を総合すると、そうらしいわね。
翔太:よし、それじゃここはあまり深く考えずに、Wordbook という機能を使って、問題を読み込む、ということにしておこう。コード エディタの上から 2 行目の行も、そのために必要な行なんだろうね。それで、Read の方は?
美咲:これは前回出てきたメソッドってものらしいわ。これによって指定したファイルを読み込むということなのね。
翔太:なるほど。ファイル名の前についている「../../../../」はなんだろう?
美咲:ファイルの保存場所を表わす記号だって。普通にドライブ名を書いて、"c:\単語帳.txt" のように指定してもいいそうよ。
翔太:問題文のファイルをどこに置くかで設定を変えないとだめってことだね。




<問題と解答を表示する準備をしよう>

翔太:今度は、問題文と解答を表示するための準備か。
美咲:今回は、自分で「Private」から始まる部分を書き込むみたいよ。


リスト 5-1-1 で出てきたコードの「End Sub」の次の行に、リスト 5-2-1 を追加してください。


リスト 5-2-1

    ' ページの表示処理
    Private Sub PageView()

    End Sub


翔太:これって、自動的に作られるだけじゃないんだ。
美咲:今まではイベントやコントロールのコードを書くときに自動的に作られてたわね。そのときは、「Private Sub」の後にイベントやコントロールの名前みたいなものが出ていたけど、これは何の名前かしら。
翔太:「PageView」か・・・。もう少し先まで進むと何か分かるかもしれないな。
美咲:そうね。それじゃ、次は、この「PageView」と書いてある行の次の行に、リスト 5-2-2 を追加するんだって。


リスト 5-2-2

        ' === [問題]ページの表示 ===
        ' 問題を表示する
        lblQuestion.Text = Wordbook.Question


美咲:lblQuestion はどこかにありそうね。
翔太:画面デザインの「問題」と書いてあるところだ。ちょうど今は、Text プロパティに「問題」と入力されているけど、そこに Wordbook の Question の値を代入しようとしてる、ってことみたいだね。
美咲:ということは、Question というのは問題文に当たるデータということなんだわ。
翔太:そうなると、次は、解答の設定かな。
美咲:えーっと・・・その前に問題番号を設定するみたい。
翔太:問題番号?
美咲:lblQNo っていうコントロールがあるそうよ。
翔太:どこだろう・・・。あ、これか。





この画面では、分かりやすく表示させていますが、通常は目立つ存在ではないので、すぐには見つけられないかもしれません。すぐに見つけるには、プロパティ ウィンドウの一番上の名前が出ているところで右端の▼ボタンをクリックします。すると、次に紹介する画面のように、「プロパティを表示可能な項目のリスト」が表示されるので、この中から、lblQNo を探してください。





lblQNo のプロパティを表示すると、デザイナ 画面上で lblQNo コントロールが選択された状態で表示されます。


美咲:Text プロパティのところが空欄になっていて、何も設定されてない状態だから画面上でも一見何もないように見えるのね。
翔太:それで、これをどうするの?
美咲:リスト 5-2-3 のコードをさっきのリスト 5-2-2 のコードに続けて入力するの。


リスト 5-2-3

        ' 問題が存在するか判断する
        If Wordbook.Question <> "" Then
            ' 問題が存在したら問題番号を表示する
            lblQNo.Text = "Q" + Wordbook.No.ToString()
        Else
            ' 問題が存在しなかったら問題番号の表示欄を空白にする
            lblQNo.Text = ""
        End If


翔太:前回やった条件なんとかってやつだね。
美咲:条件 “分岐“ でしょ。
翔太:そうそう。でも、最初に出てくる <> "" ってなんだ?
美咲:うーん、ここはよく分からないわね。
翔太:これは僕らでは無理かな。健一さんに相談してみようか。
美咲:そうしましょうよ。


二人は健一さんに電話して相談することにしました。


健一:やあ、どうしたんだい?
翔太:健一さん、お仕事があるのにごめんなさい。実は宿題が終わって、入門マニュアルの第 5 章を見てるんだけど。
健一:おやおや、すっかり気に入ったみたいだね。
翔太:それでどうしても分からないところが出てきたんだ。
健一:今どこまで進んだの?
翔太:問題番号を設定するところなんだけど、条件分岐ってやつがまた出てきて、その最初の行の意味が分からなくて。
健一:なんて書いてあるところ?
翔太:「If Wordbook.Question <> "" Then」の <> "" という部分が分からないんだ。
健一:ああ、なるほど。えーと・・・第 4 章の時に話した条件分岐は覚えてる?
翔太:うん。タイマーの設定時間が 0 秒だったら、とか、設定時間と経過時間が同じだったら、ってやつだったよね、確か。
健一:そうそう。条件分岐で出てくる条件というのは、条件式といって、= や >、< といった記号を使うんだよ。= は、左に書いてある項目と右に書いてある項目が同じだったら、って言う意味なのは第 4 章でやったとおり。> や < というのは・・・
翔太:それって、確か大きいとか小さいっていう意味の記号だよね。
健一:そのとおり。だから、この記号を使うときは、例えば左に書いてある項目が右に書いてある項目よりも大きくなったら、とか、小さくなったら、という条件を設定するときに使うんだよ。
翔太:それじゃ、この <> っていうのは?
健一:これはね、この記号の左側に書いてある項目と右側に書いてある項目が同じではない、という意味なんだ。この記号の右側には何が書いてある?
翔太:右側って言っても、"" しかないよ。"" と同じではないってどういう意味?
健一:"" というのは、本来 " と " の間に文字列を書くための記号なんだ。それが今は記号だけで文字列が何も書いてないから・・・
翔太:つまり・・・?
健一:右側の項目は「文字が何もない」ってことをあらわしてるんだ。文字が何もない状態、と同じではない、ということは・・・?
翔太:何でもいいから文字が入っていればいいってこと・・・?
健一:正解! 第 5 章は単語帳だったよね。だから、この場合は問題にあたる文章が入っていればその次の行を処理しなさい、ってことなんだ。
翔太:数値じゃなくても式は成り立つんだね。
健一:そう、それがプログラミングの世界の特徴の一つでもあるんだよ。
翔太:なるほど。


ここまでの話を、翔太君に伝えてもらいながら聞いていた美咲さんは、あることに気がつきました。


美咲:翔太君、この Else ってどういう意味かしら。
翔太:え・・・? 健一さん、条件分岐の中に Else って出てくるけど、これはどういう意味があるの?
健一:If で始まる条件式の文があって、命令文があって、その次に出てくる Else だよね。
翔太:そうだけど。
健一:さっきも言ったように、If で始まる条件式を満たしていれば、その次の行の命令文を処理するんだ。では、条件式を満たしていなければ?
翔太:条件分岐の作業が終了して次に進むんじゃないの? あ、でも、なにか代入してるな・・・
健一:それじゃ、命令文で何をやっているか順番に考えてみようか。


翔太:えーっと。まず、lblQNo っていうコントロールの Text プロパティに・・・、なんだこれは。文字に足し算があるの?
健一:うん。まず、Q という文字が書いてあるよね。それは "" で囲ってあるはずだ。
翔太:うん、そうだよ。
健一:次に、それに + して、Wordbook .クラスの No のデータを持ってきてる。
翔太:ToString となってるのは、数値を文字列に置き換えてるんだよね、確か。
健一:よく覚えてたね。そう、No は問題番号が数値として収められていて、それをここで文字列に変えて出してるんだ。そして、+ というのは複数の文字列を結合して 1 つにするときに使う記号なんだよ。だから、例えば No に 1 という数値が入っていたとしたら、ここで Q と 1 を結合させて Q1 とし、さらにそれを lblQNo コントロールの Text プロパティに代入していることになる。
翔太:つまり、問題番号が設定されたってことだね。
健一:そういうこと。さて、これで条件が満たされた場合の処理は終わった。でも条件が満たされてない場合はどうすればいい?
翔太:え?
健一:条件が満たされてないってことはどういうこと?
翔太:えーと。


そばで聞いていた美咲さんが助け舟を出しました。


美咲:Wordbook.Question、つまり問題文のデータに何か入っている、の反対だから、問題文のデータが空っぽ、要するになにもないってことじゃないかしら。
翔太:あ、そうか。問題文のデータがない場合ってこと?
健一:そう。そして、問題文がない場合には、問題番号を表示する必要はないよね。
翔太:ということは、Text プロパティに何も代入しない、ってことだよね。あ、そうか、だから Else の次の行で "" を代入してるのか。"" は何もない、つまり空白ってことなんだよね。
健一:そのとおり! これでもう Else の役割は分かったよね。
翔太:条件式を満たさない場合は、Else の次の行を処理しなさいっていうこと?
健一:そう! Else がなければ、End If まで進んでその次の行を処理するんだ。かなり翔太君も分かるのが早くなってきたねー。美咲ちゃんのおかげもかなりありそうだけど。
翔太:でも、まだまだ大変だよ。この章だって、そんなに難しくなさそうだから軽い気持ちで始めたのに、いきなりまたクラスとか出てきちゃって。
健一:そうか、クラスを使ってるんだっけ。でもこの条件分岐まで進んでるってことは、なんとなく理解できてるってところかな?
翔太:コントロールやコンポーネントのように、あらかじめ特定の機能を作りこんでおけるもので、コントロールなどと違って、画面に貼り付けたりしないもの、っていうくらいに考えてるけど。
健一:そうだね、今はまだそういう理解でかまわないよ。もっとプログラミングの勉強が進んでくると、もっと詳しいクラスの働きや種類が分かるようになるけど、今はそんなことを知らなくてもサンプルを作れるからね。
翔太:うん、分かった。それじゃ、忙しいところをごめんなさい。また何かあったら電話するかもしれないけど、そのときはよろしくお願いします。
健一:そうだ、あまり悩みすぎないようにね。分からないままずっと悩んでいると、プログラミングのことが嫌いになりがちだから。まずは楽しく体験することが重要なので、どうしてもわからなかったら、いつでも質問していいから。
翔太:ありがとう。それじゃ、またね。


美咲:条件分岐もいろいろなことができるのね。
翔太:本当に、プログラミングって奥が深いんだなぁ。でも、逆の見方をすれば、今くらいの程度でもいろんなプログラムが作れちゃうんだね。もちろん、ある程度クラスやコントロールの準備はしてもらわないといけないけど。
美咲:必要なパーツさえあれば、それを組み合わせるのはそれほど難しくないってことね。
翔太:よし、それじゃがんばって先に進もうか。
美咲:今度は、正解の表示よ。リスト 5-2-3 の次に、リスト 5-2-4 のコードを追加してみて。


リスト 5-2-4

        ' === [正解]ページの表示 ===
        ' 解答を表示する
        lblAnswer.Text = Wordbook.Answer


翔太:あれ? これは Wordbook の Answer というところから解答を取り出して代入してるんだろうけど、このコードの順番だと、問題文が表示されたら、問題番号が表示されて、そこで条件分岐が終わってこの行が処理されるってことだよね。そのまま解答を表示しちゃまずいんじゃない? 
美咲:入門マニュアルによると、Wordbook.Answer に入っているのは一つ前の問題の解答なんだそうよ。
翔太:なるほど、問題と解答がずらしてあるんだ。
美咲:さらに、答え合わせをしたときの表示を設定するようね。


続けて、リスト 5-2-5 の内容を書き込んでください。


リスト 5-2-5

        ' 解答が存在するか判断する
        If Wordbook.Answer <> "" Then
            ' 正解、不正解の文字列を格納する変数を用意する
            Dim strCheck As String
            ' 入力した答えと解答が同じか判断する
            If txtAnswer.Text = Wordbook.Answer Then
                strCheck = "正解です!"
            Else
                strCheck = "間違っています!"
            End If
            ' 解答が存在したら解答番号と、正解、不正解の文字列を表示する
            lblANo.Text = "A" + (Wordbook.No - 1).ToString() + strCheck
        Else
            ' 解答が存在しなかったら解答番号の表示欄を空白にする
            lblANo.Text = ""
        End If


翔太:今度の条件分岐はまたさらに複雑だね。
美咲:まず 1 行目はさっきの条件分岐と似てるわね。最初に、Wordbook.Answer の内容を確認して、空白でなければ次の行からElseまでを処理する、と。Else が二つあるわ。End If もふたつあるし、どちらを見ればいいのかしら。
翔太:コードを見てると、所々行の頭が下がってるよね。今までもそうだったけど、これって実はそれぞれ一つのブロックなんじゃないかな。
美咲:ブロック?
翔太:つまり、1 行目の If で始まる条件式は、この条件分岐全体のスタートなんだ。これとペアを組む End If は当然、条件分岐の最後の行だと思うんだよ。
美咲:すると、その手前の Else もセットってことね。たしかに、この三つの行は、行頭の位置がそろってるわ。
翔太:そして、1 行目の If の条件式が満たされた場合は 2 行目に行くんだけど、2 行目は行頭が少し右に下がってるだろう? そしてこの行と同じ位置に行頭が来る行が「lblANo.Text = 〜」まで続いて、さっきの Else で行頭が上がるんだ。
美咲:ということは、「Dim〜」から始まって、「lblANo.Text = 〜」で終わる行までが、1 行目の条件式が満たされた場合の処理内容ということね。
翔太:それで考えていくと・・・、1 行目は strCheck という変数を定義してるんだね。 String ってなんだっけ。
美咲:たしか文字を扱う変数の型じゃなかったかしら。
翔太:そういえばそんな話を第 3 章あたりでしてたね。
美咲:それで 2 行目でまた条件分岐が始まって、ここでの条件は txtAnswer というサンプル画面では「正解」と書いてあるコントロールの Text プロパティと、Wordbook の Answer、つまり正解のデータが一致しているかどうか、ということのようね。一致していれば条件を満たすということで次の行に行く、と。
翔太:次の行でやってるのは、strCheck 変数に正解のメッセージを代入することか。ここではまだ表示まではやらないんだね。
美咲:条件を満たさない、つまり正解と解答が一致しない場合は、Else の次の行を処理するので・・・
翔太:strCheck 変数に不正解のメッセージを代入する、と。これで解答を判断するこの条件式が終わるんだね。
美咲:そうして、次に出てくるのが解答番号の表示になるのね。
翔太:lblANo という最初はテキストが入ってなくて見えないコントロールに番号を表示するところまでは一緒だけど、さらに strCheck 変数が + で結合されてるようだよ。
美咲:本当だ。つまり、解答番号と判定結果が表示されることになるわけね。解答番号が Wordbook.No から 1 引かれているのは、今表示している問題の番号より一つ前の番号の解答だから、ってことなんだわ。
翔太:もう一つの Else の次の処理は、解答が空白だったら解答番号も空白にする、っていうことで問題番号の処理と同じだな。
美咲:ここまででまた一区切りね。次は、いよいよボタンの処理に入るみたい。
翔太:あと少しか。この調子なら最後までできちゃいそうだな。がんばろう!




<問題と解答を実際に表示しよう>

美咲:問題と解答を表示するための準備が整ったので、これからいよいよ実際に表示させる作業に入るようよ。
翔太:それじゃ、ボタンのコントロールを・・・
美咲:待って。その前にやることがあるみたい。
翔太:なんだろう?


次にあげるリスト 5-3-1 を、リスト 5-1-2 で追加した「Wordbook.Read("../../../../単語帳.txt")」の次の行に書き込んでください。


リスト 5-3-1

        ' PageView を呼出してページの表示処理を行う
        PageView()


美咲:この行を書くことで、プログラムを実行したときに、自動的に問題文を表示するようになるそうよ。
翔太:リスト 5-1-2 は、プログラムを実行したときに、問題文と解答のデータをテキストファイルから自動的に読み込むっていう作業だったよね。その次の行だから、同じように自動的に作業する、っていうのは分かるな。でも、この単語って・・・
美咲:リスト 5-2-1 で書いたコードの 1 行目「Private Sub PageView()」に出てくる名前と同じだわ。
翔太:ここは、今まで問題文と解答を表示させる条件分岐などを書いてたところだね。
美咲:そこの名前をただ書くだけ・・・?
翔太:もしかして、この 1 行目に出てくるのは、呼び出し用の名前なんじゃないかな。ここに書いておけば、他のところから名前で中身を呼び出して実行できる、とか。
美咲:なるほど。そうかもしれないわね。
翔太:後で健一さんにも聞いてみることにして、とりあえず先に進めようか。
美咲:今度はお待ちかねのボタンの処理よ。[進む] ボタンのプロパティ ウィンドウを表示して、イベントの一覧を表示させるの。そこで、[Click] の右にあるコンボ ボックスに「NextPage」と入力して [Enter] キーを押してみて。





翔太:リスト 5-3-2 のコードが追加されたよ。


リスト 5-3-2

    ' [次へ] ボタンを押したときの処理
    Private Sub NextPage(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btnNext.Click

    End Sub


美咲:この「Private Sub NextPage〜」と「End Sub」の間の行にリスト 5-3-3 のコードを書き込むの。


リスト 5-3-3

       ' 次の問題へ進む
        Wordbook.GoToNextNo()
        ' PageView を呼出してページの表示処理を行う
        PageView()


翔太:なんだい、これは?
美咲:入門マニュアルによると、Wordbook の中の GoToNextNo という命令を実行するらしいわ。これで、今まで表示していた問題から、次の問題に切り替わるみたいね。単語帳でいえば、ページをめくるようなものかしら。それで、2 行目でそのページを表示するために「PageView()」を使って、さっきまで書いてきた問題と解答を表示するコードを呼び出しているようよ。
翔太:なるほど。なんだかこんがらがってきたなぁ。一度動きを整理しようか。


プログラムの流れを改めて整理するとこうなります。

1) プログラムを起動すると、最初の問題が問題番号と一緒に表示される。この時点では解答が入力されていないので、正解欄には何も表示されない。

2) ユーザーが解答欄に解答を入力して、[進む] ボタンをクリックすると、ページが変わる。

3) 問題のところに新しい問題と問題番号が表示され、正解欄には、前回の問題の正解が表示される。そして、解答欄には解答を判定した結果が表示される。


美咲:それじゃ、実際にプログラムを動かして確認してみましょう。


デバッグ ボタンを押して、動きを確認してみてください。





プログラムを実行すると、コードを入力する前と違って、問題文と問題番号が読み込まれていることが分かります。そして解答を入力して [進む] ボタンをクリックすると、





ページが替わって、正解か不正解かの判別が行われ、新しい問題が表示されます。

もし、うまく行かない場合は、デバッグを終了してコードを確認し、イベントの名前や変数の名前などが間違っていないかよく確認してみてください。コードが正しければ、次のリスト 5-3-4 のようになっているはずです。なお、ここまでやってきた作業には、すべて意味があります。ただ単にこのコードをそのままコピーして貼り付けても、正常に動作しない場合がありますので、分からなくなったら、最初からやり直してみてください。


リスト 5-3-4

Public Class Form1

    ' Wordbook クラスを使うための準備をする(インスタンス化する)
    Private Wordbook As New Wordbook

    ' Form をロードしたときの処理
    Private Sub Form1_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load

        ' Wordbook に問題と解答データを読み込む
        Wordbook.Read("../../../../単語帳.txt")
        ' PageView を呼出してページの表示処理を行う
        PageView()

    End Sub

    ' ページの表示処理
    Private Sub PageView()

        ' === [問題]ページの表示 ===
        ' 問題を表示する
        lblQuestion.Text = Wordbook.Question
        ' 問題が存在するか判断する
        If Wordbook.Question <> "" Then
            ' 問題が存在したら問題番号を表示する
            lblQNo.Text = "Q" + Wordbook.No.ToString()
        Else
            ' 問題が存在しなかったら問題番号の表示欄を空白にする
            lblQNo.Text = ""
        End If

        ' === [正解]ページの表示 ===
        ' 解答を表示する
        lblAnswer.Text = Wordbook.Answer
        ' 解答が存在するか判断する
        If Wordbook.Answer <> "" Then
            ' 正解、不正解の文字列を格納する変数を用意する
            Dim strCheck As String
            ' 入力した答えと解答が同じか判断する
            If txtAnswer.Text = Wordbook.Answer Then
                strCheck = "正解です!"
            Else
                strCheck = "間違っています!"
            End If
            ' 解答が存在したら解答番号と、正解、不正解の文字列を表示する
            lblANo.Text = "A" + (Wordbook.No - 1).ToString() + strCheck
        Else
            ' 解答が存在しなかったら解答番号の表示欄を空白にする
            lblANo.Text = ""
        End If

    End Sub

    ' [次へ] ボタンを押したときの処理
    Private Sub NextPage(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btnNext.Click

        ' 次の問題へ進む
        Wordbook.GoToNextNo()
        ' PageView を呼出してページの表示処理を行う
        PageView()

    End Sub

End Class


翔太:何とかうまく行ったみたいだ。
美咲:問題文が最後まで行くと、最初に戻るみたいね。ずっと練習を続けられるからいいかも。
翔太:それじゃ、健一さんに電話して報告しておこう。
美咲:さっきの PageView の件も確認しておかないとね。


翔太君は健一さんに電話しました。


健一:もしもし、どう? うまくできた?
翔太:うん、何とか最後までできたよ。それで、健一さんに質問がいくつかあるんだけど。
健一:いいよ。なんだい?
翔太:まず、あの電話の後で「Private Sub PageView()」という文を自分で書いたんだけど、これってどういう意味があるの?
健一:そうか。プロシージャを自分で書くところまで入ってたっけ。
翔太:プロシージャ?
健一:そうだなぁ。これもプログラムを書く上で大事なことではあるんだけど、今はまだあまりそこを深く掘り下げる必要はないよ。ただ、今までやってきたコントロールのイベントなどと同じように、ある特定の機能を持ったコードを、名前を付けて管理しているんだということは覚えておいて欲しい。「PageView()」という部分は他のコードでもでてくるだろう?
翔太:そうなんだ。だから、他で呼び出すための名前を付けてるのかな、って話してたんだけど。
健一:なかなか鋭いね。厳密な定義はともかく、そういう認識で今のところは問題ないよ。その呼び出す対象のことをプロシージャって呼んでるんだ。
翔太:なるほど。あと、条件分岐がまた出てきたんだけど、今度は条件分岐の中にさらに条件分岐が入ってて驚いちゃった。ああいう使い方もできるんだね。
健一:ごめん、ごめん。それもちゃんと説明しておけばよかったね。
翔太:でも何とか理解できたよ。それで、そのときに思ったんだけど、コードを書くときに行の頭を下げることがあるよね。Visual Basic 2005 Express Edition は、行の途中から書いてもある程度自動的に位置を調整してくれるみたいだし。あれって、行の頭が同じもの同士が一つのブロックになってるって考えていいのかな。
健一:よく分かったね。そのとおりだよ。例えばさっきの条件分岐が組み合わさる場合だと、どこからどこまでが同じ条件の範囲なのかを判別するときに便利なんだ。
翔太:やっぱりそうなんだ。僕たちもそれでなんとなく分かったんだよ。
健一:コメントを書き込んだり、変数に分かりやすい名前を付けたりといったことを今までの章でもやってきたけど、これらは他の人がコードを読んだときに分かりやすくするための配慮なんだ。プログラムというのは、大掛かりなものになればなるほど、一人じゃ作れなくなるので、グループで作業する場合にはとても重要なことなんだよ。
翔太:なるほど。そうだ、あともう一つ。単語帳のテキストファイルなんだけど。
健一:ファイルがどうかしたの?
翔太:中身を見ると、「犬,dog」というように「問題,正解」って書いてるんだけど、同じように書いていけば問題を増やせるんだよね。
健一:そうだよ。ただし、その書き方は、このサンプルプログラムで使うための書き方だから、他のプログラムで通用するとは限らないからね。
翔太:他で使いたいわけじゃないんだ。実は、明日テストがあって、暗記しなきゃいけないことがあるから・・・
健一:それで、今回のサンプルを利用したいってことか。でも、プログラムを使わなくても、テキストファイルを作ってる間に覚えちゃうんじゃない? それでも勉強しないよりは良さそうだけど。
翔太:とにかくやってみるよ。いろいろありがとう。
健一:うん、今日はもうテスト勉強に集中して、プログラミングの続きはまた今度にした方がいいよ。
翔太:分かった。それじゃ、またね。


美咲:行頭を下げるのは他の人への配慮でもあるのね。もちろん、自分自身も見やすいから、後で修正するときに便利そうだわ。それを手助けしてくれる Visual Basic 2005 Express Edition もたいしたものね。
翔太:そうだね。さて、ひと段落着いたところで、明日の試験に備えてテキストファイルを作らなきゃ。
美咲:ファイルを作るだけ作って満足しないようにね。ちゃんとこのプログラムを使って覚える練習もしないと。
翔太:分かってるって。


さて、みなさん、いかがでしたか? 今回は、健一さんが帰ってしまって、電話でポイントだけ教えてもらいながら、翔太君と美咲さんが二人でサンプルを完成させました。かなりむずかしい話も出てきましたが、なんとか二人は理解できたようです。

さあ、次回は今までとは違って、簡単なゲームを作ることにします。今回取り上げた条件分岐に加えて、今度は乱数というものを使う方法を紹介しますので、ぜひ挑戦してみてください。


Top of Page Top of Page Top Page プログラミング チャレンジ スクエアへ戻る


Microsoft