web-dev-qa-db-ja.com

「IF」引数の評価順序?

if(a && b)
{
  do something;
}

引数を右から左へ評価する可能性はありますか(b-> a)?

「はい」の場合、評価順序に影響を与えるものは何ですか?

(私はVS2008を使用しています)

36
winnerrrr

評価順序は標準で指定されており、left-to-rightです。左端の式は、常に&&句で最初に評価されます。

bを最初に評価する場合:

if(b && a)
{
  //do something
}

両方の引数がメソッドであり、結果に関係なく両方を評価したい場合:

bool rb = b();
bool ra = a();

if ( ra && rb )
{
  //do something
}
44
Luchian Grigore

C++では、評価順序を保証する演算子はわずかしかありません

  • _operator &&_は最初に左のオペランドを評価し、値が論理的にfalseの場合、右のオペランドの評価を回避します。典型的な用途は、ゼロ除算の問題を回避するif (x > 0 && k/x < limit) ...などです。

  • _operator ||_は最初に左のオペランドを評価し、値が論理的にtrueの場合、右のオペランドの評価を回避します。たとえば、if (overwrite_files || confirm("File existing, overwrite?")) ...は、フラグ_overwrite_files_が設定されている場合、確認を求めません。

  • _operator ,_は、最初に左オペランドを評価し、次に右オペランドを評価し、右オペランドの値を返します。この演算子はあまり使用されません。関数呼び出しのパラメーター間のコンマはnotコンマ演算子であり、評価の順序は保証されないことに注意してください。

  • 三項演算子_x?y:z_は最初にxを評価し、次に結果の論理値に応じてyのみまたはzのみを評価します。

他のすべての演算子では、評価の順序は指定されていません。

順序が指定されていないということではなく、式の「順序」さえまったくないため、状況は実際に悪化しています。たとえば、

_std::cout << f() << g() << x(k(), h());
_

関数は_h-g-k-x-f_の順序で呼び出される可能性があります(_<<_演算子のメンタルモデルは何らかの方法で連続性の概念を伝えますが、実際には順序は結果の順序でのみ順守されるため、これは少し厄介です結果が計算される順序ではなく、ストリームに配置されます)。

式の値の依存性により、順序保証が導入される可能性があることは明らかです。たとえば、上記の式では、xを呼び出すには両方からの戻り値が必要なので、k()h()の両方がx(...)の前に呼び出されることが保証されます。

_&&_、_||_、および_,_の保証は、事前定義された演算子に対してのみ有効であることにも注意してください。これらの演算子を型にオーバーロードすると、通常の関数呼び出しと同じようになり、オペランドの評価の順序は指定されません。

56
6502

この場合、&&を使用しているため、式を短絡するかどうかを判断するために結果が使用されるため、aが常に最初に評価されます。

aがfalseを返す場合、bはまったく評価できません。

7
Mysticial

組み込みの論理AND演算子&&および組み込みの論理OR演算子||の最初の(左)引数のすべての値計算および副作用は、すべての値計算および副作用の前にシーケンスされます。 2番目(右)の引数。

ルールセットのより包括的な説明については、こちらをお読みください。 注文評価

4
Pacheco

左から右に評価し、可能な場合は評価を省略します(たとえば、aがfalseと評価された場合、bは評価されません)。

それらが評価される順序を気にする場合は、ifステートメントで評価の望ましい順序でそれらを指定する必要があります。

2
Dylan Smith

組み込みの&&演算子は、常に左オペランドを最初に評価します。例えば:

if (a && b)
{
   //block of code
}

afalseの場合、bは評価されません。

bを最初に評価し、aが真の場合にのみbを評価する場合は、逆の方法で式を記述します。

if (b && a)
{
   //block of code
}
1
sameer