Array initialization [c/c++]
Why this is not allowed?
#include <cstdio>
struct Foo {
int fooId;
char arr[ ];
} fooList[] =
{ {1, {'a', 'b'}},
{2, {'c', 'd'}}
};
int main()
{
for (int i = 0; i < 2; i++)
printf("%d %c\n", fooList[i].fooId, fooList[i].arr[0]);
}
whereas, this is allowed:
struct Foo {
int fooId;
char arr[2]; // this l开发者_开发知识库ine modified
} fooList[] =
{ {1, {'a', 'b'}},
{2, {'c', 'd'}}
};
Only the last member of a C struct can be flexible as in arr[]
.
Shamelessly copying from paragraph 6.7.2.1, sub-paragraph 16 of the ISO C99 standard:
16 As a special case, the last element of a structure with more than one named member may have an incomplete array type; this is called a flexible array member. With two exceptions, the flexible array member is ignored. First, the size of the structure shall be equal to the offset of the last element of an otherwise identical structure that replaces the flexible array member with an array of unspecified length.106)...
EDIT:
As for C++, see this. Bottom-line: flexible array members are not allowed in C++ at all - at least for the time being.
In C++ all members of an user defined type must have complete types, and the member arr
does not have a complete type unless you give it a size.
In C, the struct definition would compile, but you might not get what you want. The problem is that an array without size is allowed at the end of a struct to be used as a proxy to access the contiguous block of memory after the instance. This allows a dumb vector implementation as:
typedef struct vector {
int size;
char buffer[];
} vector;
vector* create_vector( int size ) {
vector* p = (vector*) malloc( sizeof *p + size ); // manually allocate "size" extra
p->size = size;
};
int main() {
vector* v = create_vector(10);
for ( int i = 0; i < v->size; ++i )
printf("%d\n", v->buffer[i] );
free(v);
}
But the language does not allow you to initialize with the curly braces as the compiler does not know how much memory has to be held (in general, in some circumstances it can know). The size-less member of the struct is only a way of accessing beyond the end of the object, it does not hold memory in itself:
printf( "sizeof(vector)=%d\n", sizeof(vector) ); // == sizeof(int)
In C++03, this is not allowed in struct or class!
Comeau C++ compiler gives this error:
"ComeauTest.c", line 3: error: incomplete type is not allowed char arr[ ]; ^
Exactly simlar question yesterday : Difference between int* and int[] in C++
精彩评论