C99中那些奇怪的数组大小[*]和[静态]是什么?

Ker*_* SB 29 c arrays c99 function-prototypes c11

显然,以下函数原型在C99和C11中有效:

void foo(int a[const *]);

void bar(int a[static volatile 10]);
Run Code Online (Sandbox Code Playgroud)

什么是那些奇怪的符号下标为目的*,static和CV预选赛?

它们有助于区分静态类型数组和可变长度数组吗?或者他们只是语法糖?

oua*_*uah 25

参数数组声明符中的static

 void f(int a[static 10]);
Run Code Online (Sandbox Code Playgroud)

static这是一个指示,参数a是一个指针,int但数组objet(其中a是指向其第一个元素的指针)至少有10元素.

然后编译器有权假设f参数不是NULL,因此它可以执行一些优化.gcc目前不执行任何优化(来源):

"参数数组声明符中的static提供的信息不用于优化.将来与预取工作结合使用可能是有意义的."

参数数组声明符中的限定符

void g(int a[cvr 10]);
Run Code Online (Sandbox Code Playgroud)

内部g a是一个CVR指针int(CVRconst,volatilerestrict限定符).例如,with constit表示指向(即,键入)aconst指针.intint * const

所以参数声明:

T param[cvr e] 
Run Code Online (Sandbox Code Playgroud)

与参数声明相同:

T * cvr param
Run Code Online (Sandbox Code Playgroud)

* 在参数数组声明符中

void h(int a[*]);
Run Code Online (Sandbox Code Playgroud)

[*]在函数声明的正式阵列参数声明(即不是一个函数定义的一部分),表示该正式阵列是可变长度的数组.

  • 这有用吗?当我用错误类型的数组(错误的大小或错误的VLAness)调用函数时,我似乎没有得到任何*有意义的诊断.你对`[*]`有"sizeof"支持吗? (2认同)
  • @KerrekSB,`[*]`的`sizeof`是不可能的,原因很简单,这只是**只允许在声明中而不是在定义中.对于VLA作为函数参数,大小表达式的计算方式就像放在函数体开头的位置一样.`[*]`是声明中表达式的占位符,用于那些不知道(或不希望)在接口中显示该表达式的情况.函数`sizeof`内部按预期工作,只有你没有第一个维度,就像数组参数一样. (2认同)