メイン

オブジェクト指向全般 アーカイブ

2006年08月11日

オブジェクト指向の世界 != 現実世界

「オブジェクト指向は現実世界における私たちの認識を、できるだけそのまま表現できるようにしたもの」と説明されています。
しかし、(ばば抜きプログラムの)手札クラスのように、現実にはありえない操作を持たせています。
オブジェクト指向で重要なのは、あくまでも役割を明確に分担することなので、現実世界でありうるかどうかは気にする必要がない。
「同じ数のカードを探すのは手札の役割」と決めたため、手札は「ただのカードの集まり」ではなく、「賢い手札」になっています。そのため、プレイヤーは「同じ数のカードを教えてください」と手札にお願いするだけでよいのです。

[ なぜ、あなたはJavaでオブジェクト指向開発ができないのか P145~146 ]

2007年04月12日

Rubyとオブジェクト指向についてアウトプットしてみる【メッセージ】

1.メッセージ ~オブジェクトは「問いかけたらきちんと返事をしてくれる」~

print var1
var1.class  #=> String

上記の例だと、var1 がオブジェクト "class" がメッセージ。
"class"というメッセージを送ることで、オブジェクトの素性(クラス)情報を得ることが出来る。

1.class  #=> Fixnum
Fixnum.class  #=> Class

"1.class"とは"1"のクラスを知るためのメッセージであり、その結果から"1"は"Fixnum"クラス出身の
オブジェクトであることがわかりました。
またここで言う「出身」のように、「あるクラスから生まれた(所属している)」ことを、
そのクラスの「インスタンス」であると表現します。


・"1"とは"Fixnum"クラスのインスタンスであるオブジェクト
・"Fixnum"とは"Class"クラスのインスタンスであるオブジェクト

オブジェクト指向 比喩 Ruby
クラス 出身地(村) String
インスタンス 出身
オブジェクト 人(モノ) "hello"


p "hello".class #=> String
"hello"がオブジェクト、"class"がメッセージ





○Rubyとオブジェクト指向についてアウトプットしてみる○
1.メッセージ ~オブジェクトは「問いかけたらきちんと返事をしてくれる」~
2.継承とは
3.メソッドの実行
4.特異メソッド
5.特異クラス
6.オーバーライド
7.Mixin(include)
8.Mixin(extend)
9.委譲

Rubyとオブジェクト指向についてアウトプットしてみる【継承とは】

2.継承とは
継承とは「別のクラスの特徴を受け継ぐこと」

○差分プログラミング
class Kamesennin
  def kamehameha
    print "かめはめ波!"
  end
end

class Goku < Kamesennin
  def shunkanidou
    print "瞬間移動!"
  end
end

goku = Goku.new
goku.kamehameha    #=>かめはめ波!


あの亀仙人(Kamesennin)の技「かめはめ波!」を引き継ぎ、
さらに「瞬間移動!」を身に着けた悟空(Goku)が現れた!
これが、差分プログラミング。
悟空は"かめはめ波!"、"瞬間移動!"が使える。


○Rubyとオブジェクト指向についてアウトプットしてみる○
1.メッセージ ~オブジェクトは「問いかけたらきちんと返事をしてくれる」~
2.継承とは
3.メソッドの実行
4.特異メソッド
5.特異クラス
6.オーバーライド
7.Mixin(include)
8.Mixin(extend)
9.委譲

Rubyとオブジェクト指向についてアウトプットしてみる【メソッドの実行】

3.メソッドの実行

亀仙人(Kamesennin)と悟空(Goku)達本人は実は技を使えません。

class Kamesennin
  def kamehameha
    print "かめはめ波!"
  end
end

class Goku < Kamesennin
  def shunkanidou
    print "瞬間移動!"
  end

  def kamehameha
    print "界王拳4倍かめはめ波"
  end
end

goku1 = Goku.new
goku1.shunkanidou      #=>瞬間移動!
newすることで、goku1という分身を作り、それが技(メソッド => 瞬間移動!とかめはめ波!)を使えます。


○Rubyとオブジェクト指向についてアウトプットしてみる○
1.メッセージ ~オブジェクトは「問いかけたらきちんと返事をしてくれる」~
2.継承とは
3.メソッドの実行
4.特異メソッド
5.特異クラス
6.オーバーライド
7.Mixin(include)
8.Mixin(extend)
9.委譲

Rubyとオブジェクト指向についてアウトプットしてみる【特異メソッド】

4.特異メソッド

#特異メソッド
class Foo
  def Foo.test
    print "this is foo\n"
  end
end

Foo.test   #=>this is foo

#通常
class Foo
  def test
    print "this is foo\n"
  end
end

o = Foo.new
o.test   #=>this is foo
クラスの特異メソッドをクラスメソッドと呼びます。


○Rubyとオブジェクト指向についてアウトプットしてみる○
1.メッセージ ~オブジェクトは「問いかけたらきちんと返事をしてくれる」~
2.継承とは
3.メソッドの実行
4.特異メソッド
5.特異クラス
6.オーバーライド
7.Mixin(include)
8.Mixin(extend)
9.委譲

Rubyとオブジェクト指向についてアウトプットしてみる【特異クラス】

5.特異クラス

class Foo
  def hello
    print "hello.\n"
  end
end

foo = Foo.new
foo.hello     #=>hello.

class << foo
  attr :name, true
  def hello
    print "hello. I'm ", @name, ".\n"
  end
end

foo.name = "Tom"
foo.hello     #=>hello. I'm Tom.
参考


○Rubyとオブジェクト指向についてアウトプットしてみる○
1.メッセージ ~オブジェクトは「問いかけたらきちんと返事をしてくれる」~
2.継承とは
3.メソッドの実行
4.特異メソッド
5.特異クラス
6.オーバーライド
7.Mixin(include)
8.Mixin(extend)
9.委譲

Rubyとオブジェクト指向についてアウトプットしてみる【オーバーライド】

6.オーバーライド

class Kamesennin
  def kamehameha
    print "かめはめ波!"
  end
end

class Goku < Kamesennin
  def shunkanidou
    print "瞬間移動!"
  end

  def kamehameha
    print "界王拳4倍かめはめ波"
  end
end

goku1 = Goku.new
goku1.kamehameha   #=> 界王拳4倍かめはめ波


悟空(Goku)は亀仙人(kamesennin)から教わったかめはめ波を進化させ「界王拳4倍かめはめ波」
にしました。Gokuの分身(インスタンス)がkamehamehaを使うと「界王拳4倍かめはめ波」になります。


○Rubyとオブジェクト指向についてアウトプットしてみる○
1.メッセージ ~オブジェクトは「問いかけたらきちんと返事をしてくれる」~
2.継承とは
3.メソッドの実行
4.特異メソッド
5.特異クラス
6.オーバーライド
7.Mixin(include)
8.Mixin(extend)
9.委譲

Rubyとオブジェクト指向についてアウトプットしてみる【Mixin(include)】

7.Mixin(include)

module Hiden_of_Kuririn
  def kienzan
    print "気円斬!"
  end
end

class Kamesennin
  include Hiden_of_Kuririn
  def kamehameha
    print "かめはめ波!"
  end
end

class Goku < Kamesennin
  def shunkanidou
    print "瞬間移動!"
  end

  def kamehameha
    print "界王拳4倍かめはめ波"
  end
end


goku1 = Goku.new
goku1.kienzan   #=> 気円斬!


亀仙人(Kamesennin)は昔、クリリンの書(Hiden_of_Kuririn)を取得して技を習得してました。
それは、悟空(Goku)も使うことが出来ます。

これが、Mixin(include)です。


○Rubyとオブジェクト指向についてアウトプットしてみる○
1.メッセージ ~オブジェクトは「問いかけたらきちんと返事をしてくれる」~
2.継承とは
3.メソッドの実行
4.特異メソッド
5.特異クラス
6.オーバーライド
7.Mixin(include)
8.Mixin(extend)
9.委譲

Rubyとオブジェクト指向についてアウトプットしてみる【Mixin(extend)】

8.Mixin(extend)

module Hiden_of_Kuririn
  def kienzan
    print "気円斬!"
  end
end

class Kamesennin
  def kamehameha
    print "かめはめ波!"
  end
end

class Goku < Kamesennin
  def shunkanidou
    print "瞬間移動!"
  end

  def kamehameha
    print "界王拳4倍かめはめ波"
  end
end


goku1 = Goku.new
goku1.extend Hiden_of_Kuririn
goku1.kienzan   #=> 気円斬!


今回の亀仙人(Kamesennin)は昔、クリリンの書(Hiden_of_Kuririn)を取得していませんでした。
しかし悟空(Goku)の分身は使わなければいけませんでした。
そこで、登場したのが extend です。
extend を利用して、悟空の分身(Gokuのインスタンス)は
クリリンの書(Hiden_of_Kuririn)を手に入れ、"気円斬!"を利用できるようになれるのです。
これが、Mixin(extend)です。


○Rubyとオブジェクト指向についてアウトプットしてみる○
1.メッセージ ~オブジェクトは「問いかけたらきちんと返事をしてくれる」~
2.継承とは
3.メソッドの実行
4.特異メソッド
5.特異クラス
6.オーバーライド
7.Mixin(include)
8.Mixin(extend)
9.委譲

Rubyとオブジェクト指向についてアウトプットしてみる【委譲】

9.委譲

require 'forwardable'

class Kuririn
  def kienzan
    print "気円斬!"
  end
  def mekuramashi
    print "目くらまし!"
  end
end

class Gohan
  extend Forwardable

  def initialize
    @q = Kuririn.new
  end

  #気円斬を Kuririnに委譲(任せる)
  def_delegator :@q, :kienzan
end

gohan1 = Gohan.new
gohan1.kienzan   #=>気円斬


悟飯(Gohan)は、クリリンではないので、気円斬を使えない。
しかし、悟飯(Gohan)に気円斬を使う依頼が来た!
悟飯は気円斬を使え!と言われたが、クリリンに任せた。
これが委譲。



詳しく説明すると・・・

オブジェクトの機能を再利用する手法の一つとして、Ruby では言語仕様としてクラスの継承とモジュールの Mix-in を提供しています。これらは、元になるクラスやモジュールの実装までもをそのまま取り込んでしまいますが、他の手段で機能の再利用を実現する手法として、委譲があります。

委譲では、再利用したい機能を自分に取り込むのではなく、その機能を持つオブジェクトに処理を依頼します。

Ruby では特に言語仕様として委譲がサポートされているわけではありませんが、委譲を実現するためのライブラリとして forwardable と delegate が用意されています。具体的には、これらのライブラリを使用することによって、あるメソッド呼び出しを他のオブジェクトのメソッドに「たらい回す」ということを簡単に記述することができます。

参考


○Rubyとオブジェクト指向についてアウトプットしてみる○
1.メッセージ ~オブジェクトは「問いかけたらきちんと返事をしてくれる」~
2.継承とは
3.メソッドの実行
4.特異メソッド
5.特異クラス
6.オーバーライド
7.Mixin(include)
8.Mixin(extend)
9.委譲

2007年06月13日

Duck Typing

http://0xcc.net/blog/archives/000053.html
class Duck
  def quack
    puts "hogehoge"
  end
end

class Foo
  def quack
    puts "foofoo"
  end
end

def func(ducky)
  ducky.quack
end

duck = Duck.new
foo = Foo.new

func(duck)  #=> hogehoge
func(foo)    #=> foofoo


「Foo もquack と鳴くのでDuck みたいなもんだろう」っていうのがDuck Typing(たぶん)

カレンダー


2007年06月
Su Mo Tu We Th Fr Sa
          1 2
3 4 5 6 7 8 9
10 11 12 13 14 15 16
17 18 19 20 21 22 23
24 25 26 27 28 29 30

Map

About オブジェクト指向全般

ブログ「プログラマ 福重 伸太朗 ~基本へ帰ろう~」のカテゴリ「オブジェクト指向全般」に投稿されたすべてのエントリーのアーカイブのページです。過去のものから新しいものへ順番に並んでいます。

前のカテゴリはアセンブラーです。

次のカテゴリはサーバーです。

他にも多くのエントリーがあります。メインページアーカイブページも見てください。