Cでの&&&操作とは


195
#include <stdio.h>

volatile int i;

int main()
{
    int c;

    for (i = 0; i < 3; i++) 
    {
         c = i &&& i;
         printf("%d\n", c);
    }

    return 0;
}

上記を使用してコンパイルされたプログラムの出力は次のとおりgccです。

0
1
1

-Wall-Waddressオプション、gcc警告を発行します。

warning: the address of i will always evaluate as true [-Waddress]

c上記のプログラムでどのように評価されていますか?


42
だと思いますi && (&i)か?興味深いことに、SOで重複する投稿を見つけることができません。
ゾウ

42
while (i &&& i <-- j) {}
kennytm


8
重複ではありませんが、同様の質問であり、それは良いリンクです
Nathan Cooper

回答:


272

それはだc = i && (&i);から、2番目の部分は冗長であることと、&iに評価することはありませんfalse

実際にunaryをオーバーロードできるユーザー定義型の場合、operator &異なる場合がありますが、それでも非常に悪い考えです。

警告オンにすると、次のようになります。

警告:「i」のアドレスは常に「true」と評価されます


1
なぜ:c = i & (&&i);iラベルはどこにありますか?
anishsane

4
@anishsane iはとして定義されてintおり、質問にラベルはありません。また、最大のムンク...
ルチアングリゴー

5
@anishsane:&&とにかく、ラベルのアドレスを取得する演算子は非標準のgcc拡張です。しかし、それが標準であったとしても、最大のムンチルールはそれがそのように解析されることを防ぎます(スペースを挿入しない限り)。
キース・トンプソン、

実際に&iは、に評価できfalseます。デフォルトで使用されることもあります。例:パラメータなしで呼び出された場合void fn(type& x = *reinterpret_cast<type*>(NULL));&xin の値は何ですか?それは0別名falseです。しかし、それを説明した方法で使用すると、それ以外の場合は常にtrue になります。fnfni == 0c = &i && i
エイドリアン

@LuchianGrigore:どのように?
エイドリアン

118

&&&Cには演算子またはトークンはありませんが、&&(論理「and」)および&(単項アドレスまたはビット単位「and」)演算子は存在します。

最大のムンク規則によって、これは:

c = i &&& i;

これと同等です:

c = i && & i;

これは、設定cの両方の場合は1にiし、&i真であり、それらのいずれかの場合は0にはfalseです。

intの場合、ゼロ以外の値はすべてtrueです。ポインターの場合、null以外の値はすべてtrueです(オブジェクトのアドレスは常にnull以外です)。そう:

これは、設定c1の場合にi非ゼロである、あるいはする0場合i、ISはゼロに等しいです。

これは、&&&が意図的な難読化のためだけにここで使用されていることを意味します。割り当ては次のいずれかである可能性があります。

c = i && 1;
c = !!i;
c = (bool)i;          // C++ or C with <stdbool.h>
c = i ? 1 : 0;        /* C */
c = i ? true : false; // C++
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.