メールの詳細(トピック表示)
about Sample in Mediator Pattern
投稿者:阿部 将典さん 2002/05/11 17:35 MLNo.1507 [メール表示]
阿部です。
結城さん、A23-1 の件における素早い対応ありがとうございました
。ついでと言っては何ですが、もう一つお願いします。
『Java言語で学ぶデザインパターン入門』の中のMediator パター
ンのサンプルプログラムですが、プログラム起動直後は Guest に
チェックが入っているのに OK ボタンが押せなくなります。
プログラムを読んでいる限りでは、とてもそんな事は起こり得ない
ように思えるのですが、println デバッグをしてみると、
LoginFrame.java のコンストラクタ内における pack() の途中で、
textUserと textPass が textValueChanged()を(何回も)呼び出し
ているようです(なぜそんな事が起きるかはさっぱり分かりません
が…)。
それゆえ、この問題はコンストラクタ内のcolleagueChanged() と
pack() の順番を入れ換えれば一応解決します。ただ個人的には
colleagueChanged() メッソドの中身を変えた方がいい気はします
が…
例えば以下のようにしてみたらどうでしょうか?
public void colleagueChanged(Colleague c){
if(checkGuest.getState()){
textUser.setColleagueEnabled(false);
textPass.setColleagueEnabled(false);
buttonOk.setColleagueEnabled(true);
}else{
textUser.setColleagueEnabled(true);
userpassChanged();
}
}
それでは失礼します。
--
阿部 将典
mabe@…
__________________________________________________
Do You Yahoo!?
Yahoo! BB is Broadband by Yahoo! http://bb.yahoo.co.jp/
読み込み中...-
MLNo.1508
結城浩さん
(0) 2002/05/11 21:12 [メール表示する]

阿部さん、結城です。
ご指摘ありがとうございます。
よければ、ご投稿くださった、以下の修正の「ココロ」を
教えていただけますか。
> public void colleagueChanged(Colleague c){
> if(checkGuest.getState()){
> textUser.setColleagueEnabled(false);
> textPass.setColleagueEnabled(false);
> buttonOk.setColleagueEnabled(true);
> }else{
> textUser.setColleagueEnabled(true);
> userpassChanged();
> }
> }
修正前は以下のようになっています。
public void colleagueChanged(Colleague c) {
if (c == checkGuest || c == checkLogin) {
if (checkGuest.getState()) { // Guest mode
textUser.setColleagueEnabled(false);
textPass.setColleagueEnabled(false);
buttonOk.setColleagueEnabled(true);
} else { // Login mode
textUser.setColleagueEnabled(true);
userpassChanged();
}
} else if (c == textUser || c == textPass) {
userpassChanged();
} else {
System.out.println("colleagueChanged:unknown colleague = " + c);
}
}
----
結城浩 http://www.hyuki.com/
http://www.textfile.org/
For the word of God is living and active ... (Hebrews 4:12)

-
MLNo.1509
阿部 将典さん
(0) 2002/05/12 20:32 [メール表示する]

阿部です。
> よければ、ご投稿くださった、以下の修正の「ココロ」を
> 教えていただけますか。
単純に p239 のロジックをそのまま実装しただけで、それほど深い
意味があるわけではないのですが…
修正前のコードでは changeColleague() の引数が checkGuest or
checkLogin でない場合、Login モードになっているという仮定が
入り込んでいます(引数が textUser or textPass の時実行される
userpassChanged() がbuttonOK.setColleague(false) を含んでい
るので)。しかしこの仮定は成立しません。
修正コードではその仮定が入っていません(引数を使っていないの
で)。そもそも必要のない仮定を前提にしてコードを書くのは危険
だと思います。
「現在の状況がどうなっているのか」ということが重要で、「どの
Colleague から通知が来たか」ということは重要ではないので、
colleagueChanged() の最初の if 文が引数によっているというの
は直観的ではない気もしますし…
それでは、失礼します。
--
阿部 将典
mabe@…
__________________________________________________
Do You Yahoo!?
Yahoo! BB is Broadband by Yahoo! http://bb.yahoo.co.jp/

-
MLNo.1510
結城浩さん
(0) 2002/05/13 00:32 [メール表示する]

結城です。
ご説明ありがとうございます。
> 単純に p239 のロジックをそのまま実装しただけで、それほど深い
> 意味があるわけではないのですが…
>
> 修正前のコードでは changeColleague() の引数が checkGuest or
> checkLogin でない場合、Login モードになっているという仮定が
> 入り込んでいます(引数が textUser or textPass の時実行される
> userpassChanged() がbuttonOK.setColleague(false) を含んでい
> るので)。しかしこの仮定は成立しません。
なるほど! いや、よく理解しました。
恥ずかしながら、上のご説明を読んでから、
コードを読み直しても、どこで余計な仮定が含まれているのか、
すぐにはわからず、しばらく悩んでしまいました。
思い込みから抜け出すのは難しかったです。
自分が日本語で書いた仕様のとおり、
きちんとcheckGuest.getState()の値でGuestモードかどうかを
判断していればよかったのですね。
> 修正コードではその仮定が入っていません(引数を使っていないの
> で)。そもそも必要のない仮定を前提にしてコードを書くのは危険
> だと思います。
おっしゃる通りです。
Mediatorのソースの修正版はそのうちWebに出しておきます。
正直、勉強になりました。感謝します。
----
結城浩 http://www.hyuki.com/
http://www.textfile.org/
For the word of God is living and active ... (Hebrews 4:12)

-
MLNo.1511
結城浩さん
(0) 2002/05/13 00:53 [メール表示する]

> Mediatorのソースの修正版はそのうちWebに出しておきます。
> 正直、勉強になりました。感謝します。
Mediatorサンプルの修正版を以下で公開しました。
◆サンプルプログラムのダウンロードとライセンス
http://www.hyuki.com/dp/index.html#download
◆誤りと訂正
http://www.hyuki.com/dp/index.html#error
----
結城浩 http://www.hyuki.com/
http://www.textfile.org/
Perlはみだし情報募集中! http://www.hyuki.com/pq/pqhami.html


