There are situations in C++ where a statement can be parsed as both a declaration and as an expression. Specifically, a declaration can look like a function call in certain cases. The compiler resolves these ambiguities by applying the following rules to the whole statement:
f();
int (x);
In some cases, C++ syntax does not disambiguate between expression statements and declaration statements. The ambiguity arises when an expression statement has a function-style cast as its leftmost subexpression . (Note that, because C does not support function-style casts, this ambiguity does not occur in C programs.) If the statement can be interpreted both as a declaration and as an expression, the statement is interpreted as a declaration statement.
Note: The ambiguity is resolved only on a syntactic level. The disambiguation does not use the meaning of the names, except to assess whether or not they are type names.
The following expressions disambiguate into expression
statements because the ambiguous subexpression is followed by an
assignment or an operator. type_spec in the expressions can be
any type specifier:
type_spec(i)++; // expression statement type_spec(i,3)<<d; // expression statement type_spec(i)->l=24; // expression statement
In the following examples, the ambiguity cannot be resolved
syntactically, and the statements are interpreted as
declarations. type _spec is any type specifier:
type_spec(*i)(int); // declaration type_spec(j)[5]; // declaration type_spec(m) = { 1, 2 }; // declaration type_spec(*k) (float(3)); // declaration
The last statement above causes a compile-time error because you cannot initialize a pointer with a float value.
Any ambiguous statement that is not resolved by the above
rules is by default a declaration statement. All of the following
are declaration statements:
type_spec(a); // declaration type_spec(*b)(); // declaration type_spec(c)=23; // declaration type_spec(d),e,f,g=0; // declaration type_spec(h)(e,3); // declaration
Another C++ ambiguity between expression statements and
declaration statements is resolved by requiring an explicit
return type for function declarations within a block:
a(); // declaration of a function returning int // and taking no arguments void func() { int a(); // declaration of a function int b; // declaration of a variable a(); // expression-statement calling function a() b; // expression-statement referring to a variable }
The last statement above does not produce any action. It is semantically equivalent to a null statement. However, it is a valid C++ statement.