Вот грамматика для описателя, как взято из standard (§ 6.7.5):
declarator:
pointeropt direct-declarator
direct-declarator:
identifier
(
declarator)
direct-declarator[
type-qualifier-listopt assignment-expressionopt]
direct-declarator[ static
type-qualifier-listopt assignment-expression]
direct-declarator[
type-qualifier-liststatic
assignment-expression]
direct-declarator[
type-qualifier-listopt* ]
direct-declarator(
parameter-type-list)
direct-declarator(
identifier-listopt)
pointer:
*
type-qualifier-listopt
*
type-qualifier-listopt pointer
type-qualifier-list:
type-qualifier
type-qualifier-list type-qualifier
parameter-type-list:
parameter-list
parameter-list, ...
parameter-list:
parameter-declaration
parameter-list,
parameter-declaration
parameter-declaration:
declaration-specifiers declarator
declaration-specifiers abstract-declaratoropt
identifier-list:
identifier
identifier-list,
identifier
Как вы можете видеть, как []
и ()
связывается с описателем перед тем *
. Возьмем декларацию
int *a[N];
описатель является *a[N]
, который приспосабливает указатель отказа прямой описатель рисунок выше, и, таким образом, как разобранную *(a[N])
, поэтому a
представляет собой N-элемент массива указателей.
Подводя итог:
T *a[N] -- declares an N-element array of pointer to T
T (*a)[N] -- declares a pointer to an N-element array of T
T *f() -- declares a function returning pointer to T
T (*f)() -- declares a pointer to a function returning T
Объявления = выражения. – delnan
Похожа: http://stackoverflow.com/questions/859634/c-pointer-to-array-array-of-pointers-disambiguation В частности, см. Ответ на вопрос 'cdecl' –