TL; DR 哪些const
可以出现在C99程序中而不被忽略?或者相反:在C99程序中const
添加非平凡约束的位置?
我的理解是const
限定符仅适用于允许限定类型的少数几个地方。 “有用”在这里用于语义,意思是“添加非平凡约束”。我const
有用的地方列表包括:
int const *
int const x = 1
struct
/ union
中某些字段的可变性。例如。 struct Foo { int baz; int const quux; }
typedef
中,当在上述案例之一中使用我很难找到这些详尽的清单。我已经略过了C99规范,但这几乎不是轻读。 :)
非常感谢!
以下是AFAICT const
不“有用”的一些案例:
const int foo() { return 2; }
(int const) bar()
sizeof
(限定/非限定类型的对齐和大小相同)。例如。 sizeof(const int)
答案 0 :(得分:3)
根据语言语法 type-qualifier 可以作为 type-name 的一部分出现。如果您查看 type-name 的语言语法,您将找到可以使用它的所有上下文。那将是:声明,演员表,复合文字,泛型,sizeof
,_Atomic
,_Alignas
,_Alignof
。
可以肯定地说,在过去四年的背景下 - sizeof
,_Atomic
,_Alignas
,_Alignof
- const
在任何间接层面都没有区别。
_Generic
似乎仍然没有明确规定,但可以安全地假设顶级const
没有任何区别。更深层次的间接const
问题在_Generic
。
至于其他人,管理规则是:顶级const
仅对 lvalues 有意义。应用于 rvalues 时没有任何区别。这意味着将顶级const限定应用于函数返回类型或转换中的目标类型没有意义。
在更深层次的间接使用的限定词显然很重要。
请注意,复合文字是左值,意味着复合文字中的顶级const
很重要
int *p = (const struct { int a[10]; }) { 0 }.a; // Error: discards `const`
还有一些奇怪的例子,例如
const struct S { int a[10]; } foo(void)
{
return (struct S) { 0 };
}
int main()
{
int *p = foo().a;
}
它在GCC中编译,但是,如果我没有弄错的话,无论如何行为都是未定义的。