6

私は私の友人 (C を学んでいる) に、複数の変数を一度に比較することはできないと話していました。

int main(){
    int a[4];

    scanf("%d %d %d %d", &a[0], &a[1], &a[2], &a[3]);

    if(a[0] < a[1] < a[2] < a[3]){
        printf("OK!\n");

    }

    else{
        printf("I've told ya\n");

    }

}

したがって、私が正しかったことを証明するために、上記のプログラムをコーディングし、それを で実行しました1 2 3 4。驚いたことに、それは印刷されOK!ました。だから、彼に何を話せばいいのかわからなかった。それは間違いだと確信していたからだ。

最後に、それは未定義の動作ですか、それともそうではありませんか?

4

7 に答える 7

12

いいえ、それは明確に定義されています。それは単にあなたが期待しているものとは異なるセマンティクスを持っています.

式は次のように評価されます。

if (((a[0] < a[1]) < a[2]) < a[3]) {

各比較は、ブール (0または1) の結果を生成します。

の (ブール) 結果はa[0] < a[1]と比較されa[2]、その比較の (ブール) 結果は と比較されa[3]ます。

正当なユースケースがいくつかあると確信していますが、せいぜいまれです。

表現しようとしているものを表現する正しい方法は、

if (a[0] < a[1] && a[1] < a[2] && a[2] < a[3]) {
于 2013-01-30T20:32:28.233 に答える
4

それは未定義の動作ではなく、あなたが思っていることをしないだけです。と同等です

(((a[0] < a[1]) < a[2]) < a[3])

1真の場合、0偽の場合。したがって、a[0] が a[1] より小さい場合は a[2] を 1 と比較し、そうでない場合は 0 と比較します。等々。

于 2013-01-30T20:32:42.737 に答える
4

これは未定義の動作ではなく、予期しない動作です。

C および C++ では、そのような数学のような比較を行うことはできません。一度に 2 つのことを比較できます。したがって、必要な場合はa < b < c < d、次のように記述する必要があります。

if (a < b && b < c && c < d)
    ...
于 2013-01-30T20:34:26.217 に答える
3

C++ をミックスに取り入れたので、非常に簡単に実行できます。

if ( std::is_sorted(a, a+4) )
    puts("OK!");
于 2013-01-30T20:49:12.683 に答える
2

これは定義された動作ですが、期待どおりの動作をしないため、実行しないでください。

あなたの式は次のようになります。

((a[0] < a[1]) < a[2]) < a[3]

ここで、各 x < y は 1 または 0 に変換されます。つまり、a[3] が 1 より大きい場合は常に true であり、a[3] が 0 より大きい場合は true になる可能性があります。

于 2013-01-30T20:33:56.317 に答える
2

それは未定義の動作ではありませんが、彼が考えていることを実行しません。< は左から右への結合であるため、最初a[0] < a[1]に評価され、結果はtrue. 次にtrue < a[2](と同等1 < a[2]) が評価され、結果は になりtrueます。等々。たまたま正しい結果が得られただけです。たとえば、「2 1 0 1」も true になります。どちらかを使用

a[0] < a[1] && a[1] < a[2] && a[2] < a[3]

またはより一般的には、配列が長い場合:

for(i=1,ok=1;i<n&&ok;i++)ok &= a[i-1] < a[i];
于 2013-01-30T20:36:03.257 に答える
1

このように表示される場合、< 演算子の評価の順序は明確に定義されています。作成したコードは次と同等です。

bool x;

x = a[0] < a[1];

if(x == true)
{
  x = true < a[2]; 
}
else
{
  x = false < a[2]; 
}

if(x == true)
{
  x = true < a[3]; 
}
else
{
  x = false < a[3]; 
}

if(x == true)
{
  printf("OK!\n");
}
else
{
  printf("I've told ya\n");
}

true は常に整数 1 に評価され、false は 0 に評価されます。おわかりのように、このコードはまったく意味がありません。

于 2013-01-30T20:43:54.943 に答える