C中有const吗?

问题描述 投票:49回答:10

这个问题可能很幼稚,但是:

  • C中有const关键字吗?
  • 从哪个版本?
  • C和C ++中的const之间是否存在语义和/或语法差异?
c++ c const language-comparisons
10个回答
54
投票

关于const关键字,C和C ++之间没有语法差异,除了相当模糊的一个:在C(从C99开始)你可以将函数参数声明为

void foo(int a[const]);

这相当于

void foo(int *const a);

宣言。 C ++不支持这种语法。

也存在语义差异。正如@Ben Voigt已经指出的那样,在C const声明中不产生常量表达式,即在C中你不能在const int标签中使用case对象,作为位字段宽度或非VLA数组声明中的数组大小(这一切都可以在C ++中实现)。此外,const对象默认在C中具有外部链接(C ++中的内部链接)。

还有至少一个语义上的差异,Ben没有提及。 C ++语言的Const-correctness规则支持以下标准转换

int **pp = 0;
const int *const *cpp = pp; // OK in C++

int ***ppp = 0;
int *const *const *cppp = ppp; // OK in C++

这些初始化在C中是非法的。

int **pp = 0;
const int *const *cpp = pp; /* ERROR in C */

int ***ppp = 0;
int *const *const *cppp = ppp; /* ERROR in C */

通常,在处理多级指针时,C ++表示您可以在任何间接深度添加const-qualification,只要您还将const-qualification一直添加到顶级。

在C中,您只能将const-qualification添加到顶级指针指向的类型,但不能更深。

int **pp = 0;
int *const *cpp = pp; /* OK in C */

int ***ppp = 0;
int **const *cppp = ppp; /* OK in C */

同一基本一般原则的另一个表现形式是const-correctness规则在C和C ++中使用数组的方式。在C ++中你可以做到

int a[10];
const int (*p)[10] = &a; // OK in C++

尝试在C中执行相同操作将导致错误

int a[10];
const int (*p)[10] = &a; /* ERROR in C */

1
投票

C中有一个“const”关键字,并且持续时间很长。如果变量被指定为“const”,则禁止写入。此外,在某些环境中,声明为“const”的变量可能位于与其他变量不同的数据段中。这个数据段可以提供硬件写保护,对于嵌入式系统,可以存储在ROM或闪存中,而不是存储在RAM中(在一些处理器上有一个非常重要的区别,这些处理器比RAM有更多的ROM或闪存 - 例如128K闪存和3.5K RAM,或2K ROM和96字节RAM)。

请注意,编译器通常不会对“const”值或涉及它们的表达式进行任何推断。如果我说“const char foo [] =”Hello“;”然后引用foo [1],编译器将从存储foo []的地方加载值(很可能是'e')并使用加载的值。有时,这有用地允许在已编译的代码映像中修补值,但有时它只会浪费代码。

如果要将数字定义为编译时“可替换”常量,最好的方法,至少对于整数常量,可能是使用“枚举”。例如,“enum {woozle = 19;}”将导致19代替整个代码中的“woozle”。请注意,与文本替换不同;枚举声明遵守适当的范围规则。


13
投票

前两个问题在这里得到解答:Const in C

是的,在C和C ++中const之间的语义有很多不同。

  • 在C ++中,适当类型的const变量是整数常量表达式(如果它们的初始化器是编译时常量表达式),并且可以在需要它的上下文中使用,例如数组边界和枚举定义。在C中,它们不是也不可能。
  • 在C ++中,const全局变量自动具有static链接,因此您可以将它们放在头文件中。在C中,此类变量具有外部链接,并且会在链接时生成重复的定义错误。

8
投票

是的,有一个const关键字。它是1989年标准的一部分。

至于兼容性,这里是Harbison&Steele的第5版:

A top-level declaration that has the type qualifier const but no explicit storage class is considered to be static in C++ but extern in C. To remain compatible, examine top-level const declarations and provide an explicit storage class. In C++, string constants are implicitly const; they are not in C.

5
投票

是的,至少自ANSI C(又名C89)以来,const一直在那里。

它肯定出现在我的"The C Programming Language (2nd Edition)", Kernighan & Ritchie(1988年出版)中。

相关提取物:

constvolatile属性是ANSI标准的新特性。 const的目的是宣布可能放在只读内存中的对象,并可能增加优化的机会。


5
投票

另外两个区别:


2
投票

C中的语义与C ++中的语义不同,例如

unsigned const a = 10;
unsigned A[a];

在文件范围内在C ++中有效但在C中不有效。


2
投票

是。 const在C中,来自C89。

这是一个很好的阅读是关于behaviour of const keyword in C


1
投票

是的,C中有一个const关键字。自C90以来一直存在。

从语法上讲,它可以出现在与C ++相同的位置。在语义上,它有点松懈,IIRC。


1
投票

根据ESRconst被添加到ANSI C草案提案标准中。 1987年的Eric Giguere's summary of ANSI C证实了这一点。

编辑:This looks like the draft itself - 搜索“3.5.3类型限定符”。

© www.soinside.com 2019 - 2024. All rights reserved.