トップページ⇒tech
1001コメント385KB

オブジェクト指向の概念を教えれ

■ このスレッドは過去ログ倉庫に格納されています
0001デフォルトの名無しさんNGNG
優秀なお前らに質問です。
JavaScriptで document.write("Hello!"); がやっと書けるようになったオイラに、
オブジェクト指向の何たるかを、わかりやすく、華麗に、スマートに教えてください。
これは、主に自然言語において発揮される高い言語能力が、
プログラマの優秀さの必要条件でもあるという想定を検証するためにも、
チャレンジしがいのある課題であるゴルァ
0153デフォルトの名無しさんNGNG
>>150
もうちょっと問題を絞ったほうが議論しやすいのでは。

主張:
オブジェクトの比較は、比較対象であるところのオブジェクトで定義すべきでない。
なぜならば、比較を行うのは第三者だし、文脈によって方法が変わってくるから。
0154デフォルトの名無しさんNGNG
>>150
問題が解決できないものを捨てたら、何も残りません。
代替案が無い以上最善の方法を使うしかないと思うが。
0155デフォルトの名無しさんNGNG
この人に言わせると「私の知る限りでは日本でオブジェクト指向を
理解している人には3人くらいしかいない」そうだ。

http://village.infoweb.ne.jp/~fwgf2942/
0156150NGNG
>>152
javaでもC++(STL)でもComparatorつうのがあってカスタムな比較を
したいときには一応指定できるようになってる。オレが思うに、
どちらの言語でもこのComparatorを唯一の標準にするべきだった。

で、おっしゃるとおり、比較対象となるオブジェクトに外部から
アクセスすることはOOの急所の一つであるカプセル化を壊すことに
なってしまう。オレは第三者が比較を行うのが自然な設計であると
考えてるから、現在のOOは良い設計を行う妨げになってるのでは
ないかと思うわけ。

代替案としては、明示的に宣言した場合にはオブジェクトのprivate
な部分にアクセスすることを許可するような仕組みが考えられる。
こうゆう仕組みをサポートする言語があるのかどうかは知らんけど。
0157 NGNG
どういうときにprivateな部分にアクセスしたいわけ?
0158150NGNG
>>153
まあ、その通りなんだけど、設計自体を問題視してるのではなくて、
そのような設計をさせてしまうOOという手法のあり方を問題にしてる
のよ。

オブジェクトの比較云々はその具体例だと思ってちょ
0159WILLNGNG
あんま関係ないかもしれないけど・・・。

>> 146さんと150さん

オブジェクト指向自体のってーのが良くわからないんだが、
オグジェクト指向の利点てのは
オブジェクト指向設計が徹底されると、複数のプログラムからできてるシステムでも

 「どのプログラムもある種類のデータには同じアクセスをしている」

ちゅ-ことを保証できることにあるとおもうんだわ。

例えば、

「 期間の開始日と終了日には常に 開始日 ≦ 終了日 の関係が成り立たなければならない」

っちゅ-事の管理を構造体と関数でやろうとすると、
ファイルとかデータ-ベースとか引数から期間のデータをもらう度に、
開始日と終了日のチェックをする関数を呼び出す羽目になると思うんだわ。

でも、期間をオブジェクトにしてそのオブジェクトの
開始日と終了日に値をセットするメソッドでチェックするようにして置けば
一々、期間読み込み → チェック関数呼び出し をしなくても良くなるわけさ。




0160デフォルトの名無しさんNGNG
>>155
そりゃ大変だ。外国に勝てないぜ。

つーか彼が知っている日本人は何人なのか気になる。
0161WILLNGNG
>>158

あ〜、なるほど・・・。
もしかして、下手な設計者がオブジェクト指向もどきをしようとすると
公開されなきゃならないはずのデータまで隠蔽されてしまって、
痒いところに手が届かないクラス乃至オブジェクトができるといってます?

そーれはそのとおりかもしれない。
0162デフォルトの名無しさんNGNG
>公開されなきゃならないはずのデータまで隠蔽

これはまだいい方。
「隠蔽しなきゃならないはずのデータまで公開」されちまった日にゃぁ...
0163デフォルトの名無しさんNGNG
少なくともWILL君は「3人」の中には入ってないみたいだねぇ。
0164150NGNG
説明が下手でスマン。javaとオブジェクトの比較の例で捕捉してみる。

- 本来オブジェクトの比較は第三者(Comparatorのような)が行うべきだ。
 理由は、前に書いたので分かって貰えると思う。

- ところがjava言語では、Objectクラスに比較メソッド equals(Object)
 が定義されていて、任意のオブジェクトの比較にこのメソッドを使う
 のが標準的、ということになってる。これはおかしい。

- じゃ、なんでこうしてるのか?と考えてみると、OOの考え方が悪い方向
 に影響を与えてるのではないかと推測できる。つまり、

1 オブジェクトの内部データに確実にアクセスできるのはそのオブジェクト
 自身だけである、というカプセル化の考え方があるから。したがって、
 第三者であるところのComparatorは潜在的に、オブジェクトを比較する
 のに十分なデータにアクセスできるとは限らない。

2 「オブジェクトは自分自身について知っているとよい」という考え方が
 あるから。

こんな感じ。
0165WILLNGNG
>>163

うむ。
おいらはリンク先のやつの知人でもないし、
そんなに有名でもないからね。(w
0166デフォルトの名無しさんNGNG
oriented であって one とか only じゃないんだから

そんな必死になるようなもんじゃないと思う。
 逆にOOP言語を効率的に使いこなす技術程度でいいんじゃないかと
0167150NGNG
>>166
どうも。確かに固執してるかもしれない。かれこれ1ヶ月も気になってる(w

ただ、この問題に気づいたのは過去にjavaでコレクションやってて躓いた
ときだったし、今日もC++でplacement newやってて同じ問題にぶち当たった。
なんつうか、不必要に遠回りさせられてるような気がして、もっと柔軟な
言語なりパラダイムなりが必要なのではないかと思うのよ。
0168WILLNGNG
>>164
うーん・・・。
つーか、equals()メソッドと150氏のおっしゃってる
Comparatorではどうも役割が違う気がするんだが・・・。

A.equals(B)

は、主体Aが渡されたオブジェクト"Bと自分自身とが等しいか?"
を判断しているのに対して、

C.compare(A , B)

では、主体Cが"AとBが等しいか?"を判断している
という差があるはず。
で、この二つの答えは必ずしも一致する必要がないし、
どちらが標準ってことも言えないとおいらは考える。

ただ、後者型の比較の仕方はとりあえず
ライブラリの実装としてはあまり適切じゃないんじゃないかな?

150氏がOOの考えが悪い方向に影響を与えていると感じているのは、
何でもかんでもカプセル化しなきゃならないっちゅーような考え方
なんじゃないかなぁ。

もし、>>163の1にあるように第3者であるComparatorが潜在的に
比較するのに必要な情報にアクセスできないのであるとすれば、
それは比較対照となるオブジェクトとComparatorのどちらかの
設計ミスである可能性が高いと考えられる。
可能性としては次の二つ。

1.比較対照となるオブジェクトさんが人に見せなきゃならないデータを見せてない。
(夏休みの宿題とか)
2.こんぺれーたさんはもうちょっと比較対照となるオブジェクトと
仲良くならなければならない。
「(赤の他人のてめぇがおいらの口座の暗証番号を盗み見るなよ。
(おいらの嫁さんなら教えるかも知らんがな〜)」

と、言った感じ?

まぁ、どちらにしろ"わかりやすい設計"をするためのオブジェクト指向
なんであって、"正しいオブジェクト指向"するための設計をしていたんじゃ
本末転倒も良い所だと思う今日この頃。

・・・答えになってるかどうかはわからんけど。
0169デフォルトの名無しさんNGNG
>>150
まず、比較は第三者がすべきだという根拠を説明するところからはじめてみては?
0170デフォルトの名無しさんNGNG
>>169
ダブルディスパッチがしにくいとか?
0171デフォルトの名無しさんNGNG
150氏ではないし、理屈よりも感覚なんだが、

オブジェクトを中心に考えると、比較の実装は
"そのオブジェクトが別のオブジェクトと等しいかどうか調べる"
となるんだろうけど、二つが等しいかどうかどっちがどうとか考えず、
単純に比較できたほうがやりやすい、って思ってしまう。

けど、これはデータ中心で考えてるんだろうなぁ。
0172150NGNG
>>169
オブジェクトが提供する機能と、そのオブジェクトを比較する
機能は異なるもので、また異なると見なした方が便利だから、
って感じかな。

例えば文字列オブジェクトを例にとると、文字列の比較方法は
大文字・小文字を区別しないとか最初の何文字だけを比較するとか
千差万別に存在するわけだけど、どの方法で比較したいのかを
知っているのは文字列オブジェクトの使用者だけで、文字列
オブジェクト自身ではないでしょ。だから比較方法は文字列とは
切り離して第三者が行うべきだと思う。
0173169NGNG
たとえば150さんも>>172で
「文字列の比較方法は」
と言っている通り、
比較という概念には比較対象となる各オブジェクトに帰結するものが多い
と思うんだけど。

これを無理にComparatorという第三者に持っていってもいいけど、
そのComparatorは何でも知ってる神様的存在でなければいけない。
文字列比較、文字と数値の比較、整数と分数の比較、…
例えば整数と分数の比較はどうやって行うのか?
結局「分母と分子」という分数の構造と「通分」という分数の知識を
要求されるよね。
するとこのComparatorは分数の中身を知ってる超越的存在でなければならない。
0174デフォルトの名無しさんNGNG
>>172
オブジェクトが公開してないデータを用いて比較する場合は
どうすればいい?
結局は第三者がカプセル化を破る手段(friendとか)
が必要になる?うーん
って言ってる事が>>168と同じになってきた
0175150NGNG
>>168
A.equals(B)とC.compare(A, B)の意味的な違いは同意なんだけど、
どちらが標準として扱われているかと言えば、明らかに前者でしょ。
オレは後者を標準にするべき(つまるところ、AがBをどう思っていよう
が知ったことではない)だと考えているから、

> ライブラリの実装としてはあまり適切じゃないんじゃないかな?

には同意できん。もうちょっと詳しく教えて。

で、後半部分で指摘されてるような設計ミスは、Comparatorを使うと
往々にして起こり得そうなんだけど、>>156で提案してるのが、これを
カバーするための案なのよ。動的分類をサポートするならともかく、
そうでないOO言語では「私もあなたのお嫁さんになりたいのよ」も柔軟に
対応できたらいいなと。
0176 NGNG
単に設計の問題じゃねーのか?
0177150NGNG
>>173
別にComparatorが全てを知っている必要はないでしょ。
Comparatorは、比較するべきオブジェクトの種類を判別
できて、使用者が望む方法で比較できればそれでいい。
そしてこれはあらかじめ定義されてる必要性は全くなくて、
必要なときに使用者が定義してやればそれで済む。
0178デフォルトの名無しさんNGNG
オブジェクト指向ってワカッテル人が、ワカッテナイ人が使えるものをつくるためのもの?
0179169NGNG
>>177
つまり分数と整数の比較をしたい人はそれぞれ自分で
比較するための処理を書かないといけないわけ?
その手の「車輪の再発明」はバグの温床になりそうな…

それよりも例えばSmalltalkみたく全ての比較をメソッドで定義して
使用者がどの比較基準を使うか選んだほうがよくない?
0180150NGNG
>>179
まだ起きてたのか、オレもだけど(w
うーっとComparatorの使い方を説明すれば解って貰える思う。

ComparatorはSet(Smalltalkにもあったよね)のコンストラクタの引数に
与えたりして使う。使用者が意図するオブジェクトの比較方法をSetは
知らないので、知ってるComparatorをこちらで定義して与えてやる。
すると、Setは要素となるオブジェクトの比較方法を知らなくても、
boolを返すComparatorのcompare(Object, Object)メソッドという共通
インターフェイスを呼び出すだけでオブジェクトを比較できる、と
いうような具合。

文字列の比較で、通常は大文字・小文字を区別して比較が行われる
のを区別しないようにしたい場合には、使用者が定義するComparator
の比較メソッドは文字列クラスのEqualsIgnoreCase(String)を呼び出
すだけで終わる。
もちろん、EqualsIgnoreCaseに相当するメソッドがなかったら、自前の
奴を実装するわけだけど。

どのインターフェイスに統一するかの話。
0181169NGNG
ああ、何となくわかってきた。

例えばSmalltalkでソートする時には
SortedCollection withAll: aCollection sortBlock: [:less :more | less < more]
とかするけど、この[:less :more | less < more] は引数を2つ取る無名関数みたいなもの。
これを無名関数という汎用なものではなくて比較に特化したクラスにしたい
って話ね。

各種比較の実装は各クラスの責任で行なうけど、
もう1つ高い抽象化をしたい、って事ね。
それって別にオブジェクト指向が邪魔になってるわけでも
オブジェクト指向に反してるわけでもないような気がするけど。
0182150NGNG
そ。Smalltalkは静的な型チェックが入らなかったと思うんで、
無名関数のままでもいっこうに構わない。いろいろな比較メソッド
を要素となるクラスの側で定義するのも全然構わない。

問題なのは、そのような比較メソッドがなくてもう一段レベルの低い
ところまで行って自前のものを実装しようというときに、カプセル化
(アクセス制御)が邪魔して思うようにできない可能性があって、それが
javaやC++でComparatorを大々的に使用することの歯止めになってるん
じゃないか?てこと。>>164
0183デフォルトの名無しさんNGNG
結局、150がオブジェクト指向の表面しか理解していないだけなんじゃないの?
カプセル化を隠蔽と捉えているようじゃ駄目だよ。
0184デフォルトの名無しさんNGNG
150に限ったことではないが、いろんなOOPLで、同じ問題がどういうふうに
解決されてるか、もうすこし調べれ、って感じな。

それから、文字列比較の問題は、ビットパターンが同じかどうか比較
するのと、「同じ」っていうのを、あるクラスがどう定義してるかっていう
のがごっちゃになってるみたいだし、同じクラスのインスタンス同士の
比較と、違うクラスのインスタンスの比較も分けてないみたいだ。

「大文字と小文字を区別しない比較」なんて、文字列クラス以外のどこ
で定義しろというんだ?
どうしても「第3者が比較」したいならクラスメソッドでええやん。

それから、、、つっこみドコロ多いから以下略
0185150NGNG
>>183
それは、「カプセル化の恩恵は隠蔽の不利益を補って余りある
ものだから、目を瞑るべきだ」ってこと?

---
オブジェクトの比較について整理してみる。
比較は第三者が行うべきだというオレの意見は、これは統一的な
インターフェイスとしてA.equals(B)ではなくC.compare(A, B)を
採用するべきだ、ということを言ってるのよ。

前者の問題点は、比較方法を変えるためにAに手を入れなければ
ならないこと(それ以外にも手が無いわけじゃないけど、後者の
解決法に較べたらスマートじゃない。>>184氏の言うように、オレ
の知らない言語ではもっといい方法があるかもしれないけど)。
後者の場合は、使用者が意図する比較方法をその度に定義してやれば
いいのでこの問題を解決できる。オブジェクト比較のStrategy
パターンと言ってもいいかもしれない。
0186デフォルトの名無しさんNGNG
>比較方法を変えるためにAに手を入れなければ
使用者の都合で「別の比較方法を追加」したい時にC.compare(A, B)っていう
選択もあるだろうが、A.equals(B)や A sameAs:B を否定する理由にはならん
だろう…
0187John ◆0z.4Is5E NGNG
>>150
>後者の解決法に較べたらスマートじゃない。
これおかしいと思うよ。
簡単に書ける=スマートではない事は明らかだよね。
Comparatorなんて物を作ったときのデメリットは
オブジェクトが自分の挙動を知らない事になる。
これが意味するところは、クラス単位での管理が困難になる。
つまり、コードの保守という点でリスクを背負う事になる。

念のため聞いておくと、外部から見てリードオンリーなメンバを作る事って
何か問題があるかな?
問題なければ、あらゆる比較は可能だけどね。
0188デフォルトの名無しさんNGNG
>>164
>オブジェクトの内部データに確実にアクセスできるのはそのオブジェクト
>自身だけである、というカプセル化の考え方があるから。したがって、
>第三者であるところのComparatorは潜在的に、オブジェクトを比較する
>のに十分なデータにアクセスできるとは限らない。

オブジェクトを比較するのに十分なデータを読み出せないというのは
クラスの設計がおかしい。

クラスを利用する方が間違ってる場合もあるけど。
0189デフォルトの名無しさんNGNG
Johnがふつーな事書いてる…
0190デフォルトの名無しさんNGNG
>>189
はあ?>>187はツッコミ所満載だが、何か?
0191デフォルトの名無しさんNGNG
150の一知半解ぶりといい、粘着気質といい、見れば見るほど

■翻訳者が仕事するように駄目な奴をさらす■
http://pc.2ch.net/test/read.cgi/tech/1008165139/-100

の58にそっくりだな。
もしかして同一人物か?
0192150NGNG
>>187
Comparatorという別のクラスを作るのは、管理面でちょっとは
不利かもしれないけど、他の方法で同じことを実現するのは
難しいと思う。おかしいと言うのなら、これ以外の方法で実現
できる統一的なインターフェイスを提案してほしい。

後半部分に関しては、OO的な観点から言えば、公開する必要のない
内部情報をアクセス可能にするのは危険だ、ということになる。
個人的には、アクセスする側・公開する側の両者が、自分が何を
しているのかを理解しているなら構わないと思うけど。
0193150NGNG
>>191
違う。そのスレに書き込んだことはないよ。

あなたみたいな、きちんと理解した人がオレの間違いを
指摘してくれると嬉しい。ちょっくら遊んでかない?
0194189NGNG
>>190
ごめん、「Johnにしては」くらいで、大目に見てくれ。
0195John ◆0z.4Is5E NGNG
>これ以外の方法で実現,できる統一的なインターフェイスを提案してほしい。
equalとか
equalIn***とか(equal_in_***)

>内部情報をアクセス可能にするのは危険だ
だから、リードオンリーって書いたんだけど。
それともリードオンリーのメンバが存在するケースのデメリットがあるんですか?

>自分が何をしているのかを理解している
具体的に書いてくれないと、ちょっとよくわからないんだけど。
0196デフォルトの名無しさんNGNG
>>150は>>184を見て何も感じないんだろうか…
0197デフォルトの名無しさんNGNG
>>196=>>184
150呼んでるぞー
0198デフォルトの名無しさんNGNG
190 vs John
が見たいのは俺だけ?

190が登場したら、190とJohn以外の書き込みは禁止の方向で
0199150NGNG
>>195
>equalとかequalIn***とか(equal_in_***)
「統一」と言ってるんだから一つにしてくれよ。
例えば、あなたがハッシュテーブルをコーディングしていて、
出所のわからない二つのオブジェクトをハッシュテーブルの
使用者のために比較しなければならないときに、いったい
どうやってこの二つを比較するんだ?

>それともリードオンリーのメンバが存在するケースのデメリットがあるんですか?
>具体的に書いてくれないと、ちょっとよくわからないんだけど。
アクセスされる側のクラスをAと呼ぶことにすると、Aの公開インターフェイス
は将来に渡ってある程度互換性が保証されるんだろうけど、Aのリードオンリー
のメンバを含む内部実装は、保証されない。だから、Aがバージョンアップしたり、
Aを他の実装に切り替えたりしたときに、アクセスしてる側のオブジェクトが
動作しなくなるかもしれない。アクセスする側はそのリスクを承知した上で
アクセスしなくちゃいけない、ってこと。
0200184=196NGNG
放置されて、ちょっとくやしい。
0201デフォルトの名無しさんNGNG
150は神!
0202150NGNG
>>196 >>197
>>184氏の発言は、何というか、ビットパターンとか
クラスメソッドとか言ってて微妙にはずしてるような
気がするのよ。「もしかして何か重要なヒントが隠さ
れてるのか?」とも考えてみたんだけど、今のところ
理解できないのでレスできない(w
0203John ◆0z.4Is5E NGNG
>「統一」と言ってるんだから一つにしてくれよ。
そんなのどうやったって無理だけど。

>どうやってこの二つを比較するんだ?
HashObject#equalInHashValue()
みたいな感じかな。

>将来に渡ってある程度互換性が保証されるんだろうけど
そんなんだったら、Javaのライブラリーは将来使い物にならなくなるって
事なんだよね(w
まあ、オブジェクト指向理解度88%に認定かな。
0204デフォルトの名無しさんNGNG
( ゚д゚)ポカーン
0205デフォルトの名無しさんNGNG
なんだなんだ?マルチメソッドの話題か?
0206John ◆0z.4Is5E NGNG
ヒントって言うか、直球だと思うけど、
さらに分かりやすく書くと

>出所のわからない二つのオブジェクトをハッシュテーブルの
>使用者のために比較しなければならない
さらに、オブジェクトへのポインタの値が同じかどうか調べる必要もでてきました。
さあ、どうする?みたいな・・・・・
0207デフォルトの名無しさんNGNG
>205
いや、たまに出てくる俺的感覚の押し売り。
Johnが絡んでるんだから、おして知るべし。
0208デフォルトの名無しさんNGNG
(゜д゜)<ついに馬脚をあらわたしったら
0209150NGNG
>>205
お、なんか面白そうね。勉強してみるよ、ありがと。
そういえば昨日「マルチディスパッチ」って言った人が
いたと思うけど、知らなかったんで無視した。スマン。
0210John ◆0z.4Is5E NGNG
無視?
それとも言ってる意味がわからなかったのかな。

前半は、第三者が比較しても比較の方法分だけメソッド名が必要。

後半は
継承がわかってないか、あるいは継承の使い方をわかっていないのどちらか。

>アクセスしてる側のオブジェクトが動作しなくなるかもしれない。
こんなケースはありえないと言うか、
「リードオンリー」って書くのは4回目くらいなんだけどね。
0211デフォルトの名無しさんNGNG
電波は無視、気違いは放置
0212John ◆0z.4Is5E NGNG
まあ、これでわかんないなら
説得は不可能って言うか、
分からない事に目をつぶるスタイルじゃ
何を言っても無駄な気がしてきたので、もうやめた。

ちなみにレイトバインディングくらいはわかってるんだよな?
0213デフォルトの名無しさんNGNG
#211.equal(150)?
#Yes!!
0214169NGNG
>>209
いや、マルチメソッドは共通した名前と意味を持つメソッドの実装を
引数の型に応じて複数用意する仕組み。あんまり直接的な関係はないと思う。
ただ、マルチメソッドの実装として、型を指定した引数の情報隠蔽を破る仕組みも
用意している場合があるという点では参考になるかもしれん。

俺的には、この議論はどっちかというとデザインパターン的な所にいくんじゃないか
と思うのだが、どうよ?
0215デフォルトの名無しさんNGNG
オブジェクトとオブジェクトの実装コードは別のもの、とか書いてみるテスト。
0216デフォルトの名無しさんNGNG
John君、煽るのも結構だが、
せめてvisibilityとstatic(dynamic) typingぐらい理解してからにしとけよ。
こっちが恥ずかしくなる。
0217John ◆0z.4Is5E NGNG
可視性ってアクセス修飾子とかの話?

typingって型の事言ってるのか?
静的型付言語とかの事?

だとしたら、ちょっとかわいそう。
がんばって勉強してくれ。
0218John ◆0z.4Is5E NGNG
216=150だったらかわいそうなので
アクセサメソッドを使えばリードオンリーなメンバは作れる。
って書くほど大げさじゃないけど。

equal(A , A)
equal(A , B)
B extends Aのケースを考えれば。

じゃ、おやすみ
0219デフォルトの名無しさんNGNG
さすがの>>150も、Johnを相手にするのは、意味が無い事を悟ったらしい。
0220デフォルトの名無しさんNGNG
a.equal(b)でもClassObj.equal(a,b)のどっちでもいいじゃん。
使い分ければ?
どっちかが絶対的に優れているわけではないし。
時と場合によるのでは?
0221デフォルトの名無しさんNGNG
>>220
>>150はClassObj.equal(a,b)が、
>クラスメソッドとか言ってて微妙にはずしてるような気がするのよ。
だと>>202で言ってるんだよ。
0222150NGNG
マルチメソッドちょっと勉強した。引数で多態するような
感じであってるよね? Visitorパターンと関連が深そう。

で、>>169氏の言う通り、直接関係があるわけではなさそう。
0223デフォルトの名無しさんNGNG
>>222

>>181や>>182で言ってることは Eiffel ならできると思う。
はっきりしたことは分からないれど。
0224訂正 223NGNG
>>181や>>182で言ってることは Eiffel ならできるかもしれない。
はっきりしたことは分からないけど。
0225デフォルトの名無しさんNGNG
>>224
Javaなら俺もprivate/protected変数に
public getXXX()をつけるけど
これで解決じゃない?
0226224NGNG
>>225
150はちがうことを言ってるような気がする。
0227デフォルトの名無しさんNGNG
ココ初めてきたが、お前等キモイなマジで。
気に障ったらすまん・・・が、しんで
0228デフォルトの名無しさんNGNG
なんか比較と等値の話が混ざっているような……

(等値の話だとすると)オブジェクトは自分自身について詳しいので,
自分と相手が等しいかどうかを判定するのはオブジェクトに任せちまって
いいんじゃない?わざわざ第3者を連れてくるのは,独立していない
オブジェクトをこしらえることになるのでスマートじゃない.

せいぜい>>202の言うとおりクラスメソッドでやるべきだねぇ.
0229228NGNG
ごめん.>>202じゃなくて>>184……
逝ってきます
0230228NGNG
ちょっと自己レス

これが等値じゃなくて比較の話になると150の逝っていることに意味が出てくる
オブジェクト同士を比較する方法は「オブジェクトのどの特性に注目するか」
によって複数存在するからねぇ.

「ドラッグカーとラリーカー,どっちが速い?」
そんなもん条件によって全然違う.

「F1と野球,どっちがすごい?」
……何を比較すりゃいいんだ?

こういうときは,150の言うとおり,プログラマが審判となるオブジェクト
をでっち上げて判定させる C.compare(A, B)の形式のほうが柔軟性が高い.

でも,いちいち作るのは面倒だから,オブジェクトA, Bの性質から比較される
「だろう」基準をあらかじめ用意して,自分自身で判断させるA.compare(B)の
方法もあっていいとおもう.

結論としては結局ケースバイケースでやれやっつうことに……
何回も出てきてるじゃん,この結論.




0231150NGNG
>>228
とりあえず、同値性判断や順序判断の操作を総称して「比較」
と呼んでる感じ。その辺はなんとなくで解ってちょ。

オブジェクトは自分自身について詳しいけど、bool equals(Object)
という単一のインターフェイスで判断できるのは、オブジェクトが
主観的に最も適切だと思っている方法でだけででしょ。
で、それがオブジェクトの使用者が意図している方法と一致するとは
限らない。だから、客観的な判断が出来て、使用者の意図を知っている
第三者を連れてこなきゃいけない場合がある。
そして、この第三者を連れてくる方法が今のところ最も汎用性の高い
やり方なんじゃないかと思うのよ。

で、まあこのように考えた場合、それはOO的観点からは、

>独立していない オブジェクトをこしらえることになるのでスマートじゃない

ことになってしまうので、OOに問題があるんじゃないか?
と言ってるのよ。>>164の2
0232仕様書無しさんNGNG
クラス開発者と利用者が別れている場合を想定してるわけだ。
0233デフォルトの名無しさんNGNG
>>231
話をわかりやすくすると、
例えばある人間が「同じ」と判断する基準があって、

  if (ある人間.equal(a, b))

のequalの判定基準はa,bそれ自身では特定できないってこと?
0234224NGNG
>>231
Eiffelには Javaの Objectに相当するクラスに
オーバーライドできない
standard_equal (shallow_equal) と
deep_equal と
オーバーライドできる equal というメソッドがあるんだけどどう思う?
0235150NGNG
>>233
そうです。

>>234
standard_equalとdeep_equalは全てのオブジェクトに共通する比較
方法を定義してるんだよね。equalの方は、これが汎用インターフェイス
であるのなら、前述の理由で設計が悪いと思う。
0236デフォルトの名無しさんNGNG
そういうクラス横断的な考えは AOP を参照するといいと思う。
0237224NGNG
>>235
比較にはクロージャを使うべきだということですか?
0238デフォルトの名無しさんNGNG
>>237
それは>>181-182で既出です。
0239デフォルトの名無しさんNGNG
sort = a.sort{|a,b| a.hoge <=> b.hoge }
@sort = sort { $a.hoge <=> $b.hoge } @hogehoge;
sort := SortedCollection sortBlock: [:a :b| a >= b].

適切な getter があれば良いということか
0240150NGNG
>>236
うん、個人的にはアスペクト指向を拡大解釈してOOに組み込みたい感じ。
アスペクト指向はまだ勉強すら始めてないんでビクビクもんなんだけど、
副作用的な部分だけでなく本筋の部分もアスペクト指向的に織り込めたら
いいね(確証なし)。

>>237
重要なのはインターフェイスなので、実装方法はどうでもいいのでは?
0241169NGNG
>>239
150が欲っしてるのは比較方法を適宜選択できるようなインターフェイスでしょう。
あるCollectionではequal、別のCollectionではdeep_equal、
また別のCollectionではidentity_equal、さらに別のCollectionでは名前の比較とか。
SmalltalkではこれをBlockClosureでやりくりするけど、
これを静的型でやるにはどうする?って話で,、Comparatorが一番近いだろう、と。

その時に比較対象となるオブジェクトが十分なインターフェースを提供していない場合には
情報隠蔽が邪魔だというのが150の主張だと思うんだけど、
俺的には、それはその比較対象となるオブジェクトの設計の問題だろうと思う。
比較に限らず、常にその問題はあるわけで、そこで必要十分なインターフェースを
洗い出すのが設計ってもんだろうと思うのだが。
0242224NGNG
>>241
>その時に比較対象となるオブジェクトが十分なインターフェースを提供していない場合には
>情報隠蔽が邪魔だというのが150の主張だと思うんだけど、
>俺的には、それはその比較対象となるオブジェクトの設計の問題だろうと思う。

同意。
0243224NGNG
>>241
>これを静的型でやるにはどうする?って話で,、Comparatorが一番近いだろう、と。

Eiffel では比較用のメソッドを定義して
メソッドを引数として渡すと思う。
0244召還師NGNG
うまく説明しにくいが…
比較について、例えば
型A,B,C3で、比較方法も3つだと…

(1)比較方法を全部、被比較オブジェクトのメソッドとして持たせる場合
  a.hikaku1(b) <- 比較法1
  a.hikaku2(c) <- 比較法2
  a.hikaku3(b) <- 比較法3

(2)第三者の審判オブジェクトを作る場合
  judge1.hikaku(a, b) <- 比較法1
  judge2.hikaku(b, c) <- 比較法2
  judge3.hikaku(a, c) <- 比較法3

型が増える可能性が高い場合、(1)有利。
比較法が増える可能性が高い場合、(2)有利。

一般的に(という言い方をすると突っ込まれるがw)、
比較法の方が増える可能性が少ないので、
(1)の方がよく用いられる。

…ってだけじゃないの?ここでの議論って。
なんか、もっと根深いことを議論してるの?良く分からないが。
0245150NGNG
>>241
そこまで同意。設計に問題があるから云々っていうのは別にOOに固有
の問題でもないとも思う(ただ、情報隠蔽を前面に出してるので相対的
に問題になりやすいはず)。

で、問題が発生したときに、比較対象となるオブジェクトのソース
コードを変更できる立場にあるのであれば、修正すればそれで済む。

でも、そうでなくて修正することができない場合に、Comparator
を使う戦術は使えなくなってしまう。だから、Comparatorは戦術と
しては申し分ないのに、オプションという不当な扱いを受けてるの
ではないかと考えたわけ。
0246228NGNG
>>231
ふむふむ,「等値」じゃなくて「ある特徴が同じ」ぐらいの意味かな?
#等価ってやつ?

確かにそれだったらオブジェクト自身にやらせるよりは判定オブジェクトを
でっち上げてそいつにやらせたほうがいいかも.
まあ,特徴ごとにA.equalSize(B)とかA.equalData(B)とかメソッドを作って
やってもいいような気もするけど,それはそれで(使う側も作る側も)
めんどくさそう.

>>241
同意.
隠蔽しているということは,その部分が変更される可能性があるということ
なので,その部分に依存するのはリスク高いね.ちゃんと契約された内容を
使うようにする必要があると思う.

0247169NGNG
>>243
なるほど。つまり、Eiffelでは
「比較が問題になるようなCollectionを*利用する*クラスでは
その比較自体がそのクラスである程度の重要度を持っているわけだから
その比較をメソッドとして提供するよう契約するだけの価値がある。」
という考え方なんでしょうか?
俺的にはEiffelのそういうマジメな所に好感を持っています。

Smalltalkでは「比較基準を作りたい?じゃ作ればぁ〜」って感じかな(藁
ループなども全てBlockClosureで実装するから、
「ある処理」をBlockClosureとしてオブジェクト化する事には
何の抵抗もないんだよね。
0248デフォルトの名無しさんNGNG
>>150 の主張は
1、A.equal(B) では解決できない場合 C.compare(A,B) が必要だ。
2、だったら「比較」はすべて、 C.compare(A,B) で統一すべきで、A.equal(B)無いほうがよい。

というふうにずっと見てるんだが。
この 2 が、場合によって適切なシンタックスを選べばいい、っていう意見と対立してるんだろ?

で、 C.compare(A,B) で統一できないのは、OOPLの欠点だとまで言ってるようだ。
0249228NGNG
>>244
確かに比較についてはそれでおしまいだね.
そういやSTLの連想コンテナは両方の方法をやってるや.
#デフォルトはOperator<を使って,ユーザー定義の関数(オブジェクト)が
#指定された場合はそちらを利用して「等値」を判定
#この辺の話は"Effective STL"が詳しくてよかったなぁ

実はこの先にもう一つ話があって,
 >>164
 あるオブジェクトが他のオブジェクトの詳細を必要に応じて知ることが
 できないのはOOの悪い癖じゃないの?
というのが150の意見.
0250150NGNG
本題に入ったところで止まってしまってはもったいないので、
今までの話をまとめてOOの弱点を挙げてみる。こんな感じだろうか

- 機能そのものよりも、その機能プラスその機能を自己完結させる
 ために必要なものまでを含めてモジュールとする傾向が強い。

- カプセル化を前面に押し出しておきながら、それを柔軟に扱うの
 に必要な機能を提供していない(これは言語依存かも)。
0251デフォルトの名無しさんNGNG
具体例をあげてほしいプリーズ
0252169NGNG
>>250
> - 機能そのものよりも、その機能プラスその機能を自己完結させる
>  ために必要なものまでを含めてモジュールとする傾向が強い。

で、何が困るんでしょ?

> - カプセル化を前面に押し出しておきながら、それを柔軟に扱うの
>  に必要な機能を提供していない(これは言語依存かも)。

カプセル化がオブジェクト単位でしかできないという事?
それでも大抵のオブジェクト指向言語は
オブジェクトとして扱う粒度をユーザー(プログラマ)の判断に委ねているし、
そうして生み出されたオブジェクトを使ってより粒度の粗いオブジェクトを
合成するための仕組みを提供していると思いますが。

オブジェクトの粒度に言語(環境)によって強い制約が課せられているOOといえば
COMがとりあえず思い当たる例なんだけど、そういう話をしてるんじゃないよね?
■ このスレッドは過去ログ倉庫に格納されています