使えない理由&&a
&
変数のアドレスを提供し&a
、変数ではないためです。
C 11 ドラフトでは、次のように指定されています。
6.5.3.2 アドレスおよび間接演算子
制約
1 単項 & 演算子のオペランドは、関数指定子、[] または単項 * 演算子の結果、またはビットフィールドではなく、レジスタ ストレージ クラスで宣言されていないオブジェクトを指定する左辺値のいずれかでなければなりません。指定子。
[...]
セマンティクス
3 単項 & 演算子は、そのオペランドのアドレスを生成します。[...]
この「制限」を回避するには、次のような複合リテラルを使用して一時ストレージを導入できます (少なくとも C99 を想定)。
int a = 42;
int ** ppa = &((int *){&a});
以下のエラーメッセージを参照する補足として:
test.c:5:3: error: label ‘a’ used but not defined
int * * dp2 = &&a; // NG
^
&&
gcc (およびおそらく他のもの) は、オペラントがラベルを識別する場合に単一のオペラントで演算子を使用できるようにする C 標準の拡張機能を定義します。(詳細はこちら: https://gcc.gnu.org/onlinedocs/gcc/Labels-as-Values.html )
例:
void * pv = &&lbl;
goto *pv;
/* some dead code */
lbl:;
/* living code again here */