#pragma twice

KAB-studio > プログラミング > #pragma twice > 171 Version 9.10 ショートサーキット

#pragma twice 171 Version 9.10 ショートサーキット

前のページへ 表紙・目次へ 次のページへ

 Version 9.10
ショートサーキット

さて、まずは前回の続きから

    if  ( 
            !m_wndToolBar.CreateEx() 
            ||
            !m_wndToolBar.LoadToolBar()
        )
    {
        TRACE0("Failed to create toolbar\n");
        return -1;      // 作成に失敗
    }

なに? よくわかんないんだけど、つまり上のがエラーになると下のが呼
ばれないってこと?
そういうこと。まず、このふたつの結果と if との関係をまとめると

               上の結果  下の結果   || の結果    if
両方とも成功:     0         0           0      入らない
上のだけ成功:     0       0 以外      0 以外   入る
下のだけ成功:   0 以外      0         0 以外   入る
両方とも失敗:   0 以外    0 以外      0 以外   入る

っていう関係になります
もちろん ! のあとのだよね
もちろん。 ! が掛かってない時には成功した時は 0 以外だからね
で、上がエラーになるってことは

下のだけ成功:   0 以外      0         0 以外   入る
両方とも失敗:   0 以外    0 以外      0 以外   入る

の時だよね
そう。で、これを〈上のだけ呼んだ状態〉の表に書き換えると

上のまず失敗:   0 以外      ?        0 以外   入る

??? 下の結果が?なのは分かるけど、なんで || の結果とか?じゃな
いの?
だって、ほら。もう一度見て

下のだけ成功:   0 以外      0         0 以外   入る
両方とも失敗:   0 以外    0 以外      0 以外   入る

あ! ?のとこが成功でも失敗でも、結果変わらないんだ!
そゆこと。こういう理由で、 || 演算子は〈左側が 0 以外だと、右側は
無視する〉っていう仕様になってるんです
だから下の方が呼ばれない!
これを【ショートサーキット】って言います
ショートサーキット? 短い……コース?
ショートサーキットっていうのは電気の用語で、プラスとマイナスを直に
くっつけちゃうこと。ほら、〈電気回路がショートした〉とか言うでしょ
あのショートと同じなんだ
用語的にはね。つまり、呼ぶ必要のない || の右側は飛ばしちゃおうって
こと
へー、便利っていえば便利ね
うまく使えばね。たとえば……

    // int *pi; 
    // ってしてあって、どこかの int 変数を指してると思ってください。
    if  ( 
            ( pi == NULL )
        ||
            ( *pi != 100 )
        )
    {
        // pi が指す変数の値は 100 じゃないです。
    }

むむ、ちょっと難しいかも
ここでは本当は

    if( *pi != 100 )
    {
        // pi が指す変数の値は 100 じゃないです。
    }

だけしたいんです
これならわかるよ。 pi ってポインタが指す変数が 100 じゃなかったら 
if の中に入るんだね
そういうこと。ところが、もし pi が NULL だと

    if( *pi != 100 )

のとこがエラーになっちゃうね
だから、実際には

    if( pi != NULL )
    {
        if( *pi != 100 )
        {
            // pi が指す変数の値は 100 じゃないです。
        }
    }
    else
    {
        // pi が NULL ってのはおかしくない?
    }

って書きます
 NULL かどうかチェックしてからってわけね
で、これを一緒にしちゃったのが

    if  ( 
            ( pi == NULL )
        ||
            ( *pi != 100 )
        )
    {
        // pi が指す変数の値は 100 じゃないです。
    }

えーっと、 pi が NULL なら 0 以外になって、それだと || の右側に関
係なく 0 以外になるから *pi != 100 が呼ばれない、と
そゆこと。ま、厳密には同じじゃなくて、2重に if してるのの else の
場合、つまり

    else
    {
        // pi が NULL ってのはおかしくない?
    }

の場合も if の中に入っちゃうけどね
 NULL の場合もってことね
それに、このショートサーキットだと || の右側が呼ばれない場合があ
るって事が分かりにくいから、僕はあまり勧めないかな
分かりにくいとまずい?
たとえば最初の例の場合だと

    {
        TRACE0("Failed to create toolbar\n");
        return -1;      // 作成に失敗
    }

って感じに if の中にはいると return() するけど、プログラムによって
はしないこともあるでしょ
うん、あるだろーね
その場合、ショートサーキットが機能すると、 || の右側が処理されない
から、あとあと影響するような関数を呼んでたりすると
その関数が呼ばれないで次へ行っちゃう……げ、それちょっとヤバそ
う!
そういうのを気を付けることが重要なんだけど、ショートサーキットを使
うと分かりにくいから、バグの温床になりかねないかな
だったらどうするの?
さっきの2重の if にするの
あー
見栄えは良くないけど、この方が分かりやすいよ。 NULL の場合に別の処
理をさせることもできるし
見栄えよりも分かりやすさ?
そゆこと。と、最後に、ショートサーキットの機能を持つ演算子が || の
他にあるから紹介しておきます
 && のこと?
げ、なんで分かったの?
だって || と && ってペアじゃん
まぁそうだけど……当てずっぽう?
もちろん
もちろんって……じゃあ火美ちゃん、どういう時にショートサーキットす
るか考えてみて
げ! それってかなりむつかしくない??
ま、できなくてもいいからとりあえずやってみて
……えーっとぉ、 && って Version 6.10 ( No.110 ) で出てきたよね。
そんときは……

    TRACE
        ( "%d, %d, %d, %d\n"
        ,  0 && 0, 0 && 1, 1 && 0, 1 && 1 );
    // 0, 0, 0, 1

この条件を縦に並べると……

0 && 0 : 0
0 && 1 : 0
1 && 0 : 0
1 && 1 : 1

あ、判った。 && の左側が 0 になったら右側飛ばすでしょ
げげ!!
げげってなによげげって
あ、いや……うん、合ってるよ。よく分かったね
だって、左側が 0 の時は、右側が 0 でも 0 以外でも、結果 0 だもん。
だから右側は飛ばせちゃうんだよね
そのとおり……
ってことは、 && を使う時もショートサーキットに注意しなきゃいけない
わけね
そゆこと。ま、特に面倒じゃなかったり、すると見にくくならないんな
ら、 if を2重にするとかした方がいいかな

/*
    Preview Next Story!
*/
こういうプログラミングの話って……どう?
つまんない

面白いって思わないとダメ?
うーん、今の段階ではそれも困るかも
ならいーじゃん
うーん
というわけで次回
< Version 9.11 ツールバーリソース >
につづく!
そう、こういうのの方が面白そう!
それが普通なのかもしれないけど……
 
del.icio.us 登録する
Yahoo!ブックマーク 詳細を表示 users
livedoorクリップ 詳細を表示 livedoorクリップ ブックマーク数
はてなブックマーク 詳細を表示 はてなブックマーク ブックマーク数
RSSに登録
del.icio.us 登録する
Yahoo!ブックマーク 詳細を表示 users
livedoorクリップ 詳細を表示 livedoorクリップ ブックマーク数
はてなブックマーク 詳細を表示 はてなブックマーク ブックマーク数
 
このページは、Visual C++ 6.0を用いた C++ 言語プログラミングの解説を行う#pragma twiceの一コンテンツです。
詳しい説明は#pragma twiceのトップページをご覧ください。