Hatena::ブログ(Diary)

みずぴー日記 Twitter

2009-07-21(火)

いまだに継承を使うタイミングが分からない

いまだに継承を使うタイミングが分からないを含むブックマーク

いまだに継承を使うタイミングが分からない。もうちょっと正確にいうと実装継承を使うべきタイミングが分からない。

インタフェース継承するのは理解できるよ。型をそろえたり、同一視したいんでしょ。

よくあるコードだとこんな感じ。ちゃんと動くかどうかは知らない。

interface Foo { ... }
class Bar implements Foo { ... }
class Baz implements Foo { ... }

List<Foo> foo = new List<Foo>();
foo.push(new Bar());
foo.push(new Baz());

でも、クラスを継承するのがよく分かんない。メソッドとかを再利用したいんなら、委譲を使ったほうが安心じゃん。不用意なメソッドを公開したりしないし。

class Foo {
  public void f() { ... }
}

// class Bar extends Foo {}のかわりに
class Bar {
  private Foo foo = new Foo();
  public void f() { foo.f(); }
}

GUIの世界で実装継承が盛んに用いられていて、便利なのもなんとなく分かるんだけど、ほかにどんな場面で用いたらいいのかがいまいち分かんない。

keigoikeigoi 2009/07/22 08:59 GoFのテンプレートメソッドなんかは実装継承の一例ぽいよね

osiireosiire 2009/07/22 11:35 >いまだに継承を使うタイミングが分からない。
それぐらいの感覚の方がいいんでない?あるクラスをどうしてもまるっと全体委譲したくなって、メソッド再定義ウゼーと思ったら継承、くらいの奥の手にしとけば。

mzpmzp 2009/07/22 21:43 > keigoi
テンプレートメソッドは確かに実装継承使うパターンですけど、ボクだったらStrategyパターンを使って委譲で済ましちゃうと思います。

> osiire
裏技!確かにそれなら納得できますね。

t2y-1979t2y-1979 2009/07/22 23:57 私もパッと思い付かないですが、
クラス例外とかどうでしょうか?趣旨が違う?
http://d.hatena.ne.jp/t2y-1979/20090705/1246772990

keigoikeigoi 2009/07/23 01:55 > ボクだったらStrategyパターンを使って委譲で済ましちゃうと思います。
それって果たしてStrategyなのかよくわからんけど、確かにtemplate methodパターンを使う強い動機はあまりないねぇ

mzpmzp 2009/07/23 07:17 > t2y-1979
おお、確かにExceptionクラスを継承するのはよくやりますね!
あれは何で継承を使うんでしょう? Exceptionクラスがmessageぐらいしか公開してないからですかね?

t2y-1979t2y-1979 2009/07/23 13:26 私自身、技術的に深いところは分からないのですが、
「初めての Python」の "25章 文字列例外とクラス例外"を読むと、
以下のようなメリットがあるそうです。
- 例外の階層構造が構築できる
- 既存の例外処理に影響を与えずに後から追加できる
- インスタンス属性の値としてステート情報を保持できる

mzpmzp 2009/07/23 21:22 なるほど。例外クラスは継承ツリーにも組込みたいし、各クラスの実装も似たものから、実装継承が適してるんですね。
どっちか片方だけだったら、インタフェース継承や外部クラスへの委譲で済んじゃうけど、両方必要だから実装継承でハッピーになれるんですね、たぶん。

doloopdoloop 2009/07/25 06:01 はじめまして

Template Methodを使うのは、
クラス独自の機能追加が必要なときではないかと思います。
http://doloopwhile.blogspot.com/2009/07/blog-post_25.html

mzpmzp 2009/07/26 11:30 おおお、ありがとうございます。ブログのほうのエントリを読んでたら、びびっときました。
なんか分かった気がするので、あとでまとめエントリを書きます。