Let us look at each of the cases.
Case 1
Here we have the statement
int a[]; //this is a definition so size must be known
This is not valid.
Case 2
Here we have the statement:
extern int b[];//this is a declaration that is not a definition
This is valid. Here the type of b
is incomplete. Also, b
has external linkage.
Case 3
Here we have:
int (*ptrB)[];
This is valid. We say that ptrB
is a pointer to an incomplete type.
Case 4
Here we have:
struct Name
{
int k[]; //NOT VALID
};
This is not valid as from cppreference:
Any of the following contexts requires type T to be complete:
- declaration of a non-static class data member of type T;
Case 5
Here we have:
void func()
{
ptrB++; //NOT VALID
}
This is not valid as from postfix increment’s documentation:
The operand expr of a built-in postfix increment or decrement operator must be a modifiable (non-const) lvalue of non-boolean (since C++17) arithmetic type or pointer to completely-defined object type.
Case 6
Here we have:
void bar()
{
ptrB = &b;//NOT VALID
}
This is not valid as from cppreference:
The declared type of an array object might be an array of unknown bound and therefore be incomplete at one point in a translation unit and complete later on; the array types at those two points (“array of unknown bound of T” and “array of N T”) are different types.
Case 7
Here we have:
void bar()
{
ptrB++; //NOT VALID
This is not valid as from cppreferene:
The type of a pointer to array of unknown bound, or to a type defined by a typedef declaration to be an array of unknown bound, cannot be completed.
So we will get the same error as in case 5.
Case 8
Here we have:
int main()
{
int c[];
}
This is not valid since this is a definition and so size must be known.
Case 9
Here we have:
int main()
{
extern int d[]; non-defining declaration
}
This is valid. d
has external linkage.