短絡評価短絡評価(たんらくひょうか、英: short-circuit evaluation)または最小評価(さいしょうひょうか、英: minimal evaluation)とは、多くのコンピュータプログラミング言語の論理演算子における左辺(第一引数)と右辺(第二引数)の式の評価法のひとつである。 概要「≪左辺≫ ≪論理演算子≫ ≪右辺≫」というような、論理演算子による式(論理演算子式)があるとする。左辺(第一引数)を評価した段階で式全体の値が定まらない場合のみ右辺(第二引数)を評価する、というのが短絡評価である。例えば、論理積 (論理AND) の第一引数を評価した結果が 前述のように多くの言語の論理演算子は短絡評価だが、Pascalでは「処理系依存」[1]である。Adaでは両方を評価する演算子と短絡評価の演算子とが用意されている。Javaでは、短絡評価の論理演算子の他に、ビット演算の演算子のうち 短絡評価の演算子には単なる演算子としての役割だけでなく、制御構造としての役割を負わせることができる。(なお、ALGOL 68 は "proceduring" という機能を使ってユーザー定義の短絡評価の演算子やプロシージャを実現できる) 短絡評価では、
例例として次のC言語のコードを見てみよう。 int a = 0;
if (a && myfunc(b)) {
do_something();
}
この例では、短絡評価によって int is_three_chars_long(const char *p) {
return (p != NULL) && (strlen(p) == 3);
}
短絡評価を利用することで、コードブロックの入れ子がいたずらに深くなることを防ぐこともできる。 このような利点はあるが、短絡評価であることを忘れていると問題が発生することがある[11]。例えば、次のコードを見てみよう。 if (expressionA && myfunc(b)) {
do_something();
}
ここで、myfunc(b) は副作用のある式だとする。myfunc(b) が常に実行されることを期待していると、expressionA が false だった場合に実行されないことになり、問題が発生する。必ず実行されるようにするには、2つの式の評価順序を変えるか、あるいはまず両方の式を評価し、いったん結果を変数に格納してから論理演算するなどの対処が必要となる。 if (myfunc(b) && expressionA) {
do_something();
}
Javaなどの言語では短絡評価する演算子と短絡評価しない演算子を用意して、このような問題に対処している。 if文の条件式で使われる論理積や論理和の演算子は、if文の入れ子をコンパクトに表したものと見ることもできる。例えば、次の擬似コードの中で、 if (CONDITION_A && CONDITION_B) {
TRUE_BRANCH
} else {
FALSE_BRANCH
}
これは、論理積を展開することで次のようにも表せる。 if (CONDITION_A) {
if (CONDITION_B) {
BOTH_TRUE
} else {
B_FALSE
}
} else {
A_FALSE
}
ブール論理の性質から、A_FALSE と B_FALSE というコード部分が、最初の例では FALSE_BRANCH という部分に集約されていることに注意されたい。後者の例の方が条件によって異なる処理を記述できるため、必要に応じて使い分けることになる。両者が結局同じことをするコードであれば、共通式削除や定数伝播といったコンパイラ最適化によって、どちらも同じコードを生成する可能性がある。 短絡評価を使ってコードの一部の条件付実行を実現することもできる。以下は Perl の例である。 some_condition or die; # some_condition が false なら実行を停止
some_condition and die; # some_condition が true なら実行を停止
ALGOL 681968 Final Report での仕様と 1973 Revised Report での仕様は異なる。本来の ALGOL 68 には proceduring という機能があった。これは、項の値をその項を評価するプロシージャに合わせるようにすることである。proceduring は実質的には評価を「遅延」させることができる。その最も便利な利用法として、論理演算の短絡評価がある。 以下はユーザー定義演算子の例である。 op andf = (bool a, proc bool b)bool: if a then b() else a fi; ¢ b は a が true の場合のみ評価される。 ¢ op orf = (bool a, proc bool b)bool: if a then a else b() fi; ¢ b は a が false の場合のみ評価される。 ¢
ただし、これは予定通りには機能しなかった。多くの実装では andf/orf や andth/orel といった拡張を特別に扱って短絡評価をエミュレートしていた。 文献・脚注
関連項目 |
Portal di Ensiklopedia Dunia