«前の日記(2003-07-28) 最新 次の日記(2003-07-30)» 編集

Matzにっき


2003-07-29 [長年日記]

_ [OOP]オブジェクト指向は難しい

昨日、オブジェクト指向の部分でつまづいていますというツッコミをいただきました。 人によって「オブジェクト指向」のつまづき方はそれぞれだと思うので、 誰にでも分かるという説明は実は困難なのですが、最初のきっかけになる解説を試みようと思います。 これより先は書籍なりを参照してください。

Rubyで最小限覚えないといけないオブジェクト指向の基本概念は以下の通りだと思います。

  • 「値」はすべて「オブジェクト」と呼ぶ
  • 「オブジェクト」の「メソッド」を呼べる。「オブジェクト」は「メソッド」が呼ばれると自分に合わせた処理を行う。
  • 「オブジェクト」は「クラス」に所属する。
  • 「オブジェクト」が持つ「メソッド」は(原則的に)その所属する「クラス」で決まる。

ね、そんなに難しくないでしょ。

あと、ドキュメントを読むために「継承」を理解した方が良いかもしれません。

  • 「クラス」は親となるクラスである「スーパークラス」を持つ。
  • ある「クラス」に所属する「オブジェクト」が持つ「メソッド」は、そのクラスで定義されたものと、スーパークラスで定義されたものを(先祖までさかのぼって)合わせたものだ。

それからRubyにはMix-inがありますから、これも押さえておきましょう。

  • 「メソッド」などをまとめる単位として「モジュール」がある
  • 「クラス」は「モジュール」をincludeできる(これをMix-inと呼ぶ)
  • includeされた「モジュール」の「メソッド」は「スーパークラス」同様、「クラス」に受け継がれる

ですから、文字列のクラスであるStringクラスには、長さを求めるsizeメソッドなどが定義されており、 スーパークラスであるObjectクラスから引き継いだobject_idメソッドなども持ちます。

さて、ではオブジェクト指向のメリットはなにか、ということですが、大きく分けると

  • オブジェクトが自分に合わせた処理を選ぶので、プログラマが選択する必要がない。つまり、 自分で値と処理の適切な組み合わせを選ぶ

    str = "abc"
    string_size(str) #=>3
    ary = [1, 2, 3, 4]
    array_size(ary)  #=>4
    string_size(ary) #=> error!!

    という「非オブジェクト指向」と、言語が勝手に選択してくれる

    str = "abc"
    str.size         #=>3
    ary = [1, 2, 3, 4]
    ary.size         #=>4

    という「オブジェクト指向」の嬉しさの違いです。

  • 機能がクラス単位で整理されるので理解しやすい。 つまり、Perlのリファレンスマニュアルのように数百の関数がフラットに並ぶのと比べると、 Rubyのリファレンスマニュアルのように文字列の機能はStringクラスに、 すべてのオブジェクトに共通の機能はObjectクラスに分類されている方が、 整理されていると感じられます。
  • 継承によって機能の拡張が行いやすい(時がある)。 つまり、既存のクラスとほとんど機能が同じだが微妙に違うクラスを作りたい時には、 既存のクラスを継承して、微妙に違う部分だけ追加したり、書き換えたりするだけで、 新しいクラスを作れるというもの。これを「差分プログラミング」と呼ぶ。

「差分プログラミング」はさほど重要ではないのですが、 オブジェクト指向を解説した書籍では必要以上に強調される傾向があります。

まあ、最初の一歩としてはこんなもんでしょうか。

本日のツッコミ(全9件) [ツッコミを入れる]
_ とおりすがり (2003-07-29 21:19)

上のオブジェクト指向の嬉しさの例のところ、例が不適切ではないかと思います。非オブジェクト指向の例で、ary というオブジェクトに string_size というメソッドを適用するのは現実的では無いから。オブジェクト指向の例でも、str と ary に同じ size というメソッドを呼んでも size の意味が異なるので、混乱するだけで、良くわからないのではないでしょうか?<br>多態性の例として挙げるなら、to_s メソッドなんて適切ではないかと思います。

_ D (2003-07-29 23:52)

「プログラミングだけ」憶えればいいのか、「プログラミングとオブジェクト指向」を憶えなければいけないのかということではないでしょうか。「プログラミングだけ」していても躓くところはたくさんありますが、プログラミングが目的なので乗り越える気になります。一方、オブジェクト指向しなくてもプログラミングはできますので、憶えることが少ない道を選びたくなる気持ちになるのではないでしょうか。また、コード(=書けば動く)から離れて概念を知ることを要求されるのが辛い人もいるみたいです。個人的には、前者を選んで自己流の開発手法を編み出すよりも、既存の手法を使った方が楽だと思うのですけども。

_ ksaito (2003-07-30 01:27)

思い切った提案ですが、差分プログラミングについては触れない方が、必要以上に強調されている背景から見ても安全かと思います。整理されている(==Dさんの言う、概念から見る)こととクラスが理解できれば理屈は自然に導かれるはずですし、「要するに各々好き勝手にパッチ当ててるだけじゃん」という古典的で不毛な議論に落ちなくて済むように、特にRubyの場合は思います。これを言ったのは誰だったか思い出せませんが、この勘違いがかなり大きな問題なんじゃないかとずっと思っているものですから。

_ haruki (2003-07-30 10:40)

「オブジェクト指向のメリット」の例ですが、<br>言語に組み込みのデータ型であれば、<br>言語によっては、関数が値と処理の適切な組み合わせを選んでくれたりしますし、<br>組み込み関数も、グループ分けしてして整理して理解すれば済むことです。言語によっては、プレフィックスがついて、整理されていたりもします。<br><br>「ユーザ定義のもの」に関して、それらのメリットが生かされるときに、<br>おっしゃる利点が出てくるのだと思います。

_ aaaa (2003-07-30 13:22)

オブジェクト指定でも大抵はクラスとしてプレフィックスが付いてる。<br>結局プレフィックスがあったほうがわかりやすいという理屈の点ではそれは関数型言語の利点ともオブジェクト指向言語の利点とも言えない。<br>グループ分けして整理してというところも同じく整理したほうが良いのなら、私は結局オブジェクト指向でいいと思う。<br>オブジェクト指向でも、あるべきでないところにメソッドが定義されてると頭を抱えてしまうわけで。<br>まつもとさんが言うところの「値」自身がメソッドを持つのも利点だと思うんですが。<br>あと変数のスコープがわかりやすい気がするのは私だけでしょうか。<br>とりあえず自分が書くソースはオブジェクト指向のほうがすっきりしてる感じです。<br>曖昧ですみません。

_ たかはし (2003-07-31 03:12)

「オブジェクト」「クラス」「メソッド」と、いきなり新しい単語が三つも出てきて相互に定義に使われている時点で、すでに難しいんじゃないかとおもいます。

_ AC (2003-08-01 03:05)

新しい単語がでてきて難しそうだから嫌なんならプログラミングせんでもええと思うんやがどうか。

_ たかはし (2003-08-02 01:55)

別に「嫌」じゃないですよん。「ね、そんなに難しくないでしょ。」とは思わない、というだけです。 <br>また、まつもとさんがここに書かれたオブジェクト指向の説明が難しいからといって、もっとかんたんなオブジェクト指向の説明もありうるかもしれないですし、まつもとさんの書かれているオブジェクト指向のコードそのものが難しいわけでもありません。事実、わたしはRubyのプログラムのおかげでオブジェクト指向が理解できたといっても過言ではないのです。

_ ゆあい (2003-08-09 03:56)

「オブジェクト指向が難しい」ということではなく「オブジェクト思考できるようにパラダイムチェンジすることが難しい」ということではないでしょうか?<br>手続き型言語のパラダイムは学習しやすいというのは、人間が普段何気なくおこなっている動作が手続きだからではないでしょうか?

お名前:
E-mail:
コメント:
[]

«前の日記(2003-07-28) 最新 次の日記(2003-07-30)» 編集

track feed Matzにっき Creative Commons License This work is licensed under a Creative Commons License.