【问题标题】:What is the standard to declare constant variables in ANSI C?在 ANSI C 中声明常量变量的标准是什么?
【发布时间】:2011-06-30 23:47:01
【问题描述】:

我正在通过阅读我的 C++ 书籍并用 C 重新编写问题来自学 C。我想知道在 C 中声明变量为常量的正确行业标准方法。你还在使用 #define main 之外的指令,或者您可以在 main 内部使用 C++ 样式 const int

【问题讨论】:

  • “常数变量”是矛盾的:)
  • 它可能是矛盾的,但这正是 const 关键字在 C 中创建的 - 不是 常量,而是不可修改的变量。
  • C 的正确术语是const-qualified object,也就是说这不是变量的属性,而是它所引用的对象的属性。

标签: c


【解决方案1】:

C 中的const 与 C++ 中的const 非常不同。

在 C 中,这意味着不会通过该标识符修改对象:

int a = 42;
const int *b = &a;

*b = 12; /* invalid, the contents of `b` are const */
a = 12; /* ok, even though *b changed */

此外,与 C++ 不同,const 对象不能用于例如开关标签中:

const int k = 0;
switch (x) {
    case k: break; /* invalid use of const object */
}

所以...这真的取决于你需要什么。

你的选择是

  • #define: 真的是 const 但使用了预处理器
  • const: 不是真的 const
  • enum:限int

更大的例子

#define CONST 42
const int konst = 42;
enum /*unnamed*/ { fixed = 42 };

printf("%d %d %d\n", CONST, konst, fixed);

/* &CONST makes no sense */
&konst; /* can be used */
/* &fixed makes no sense */

【讨论】:

    【解决方案2】:

    现代 C 支持 #defines 和 const 全局变量。但是,#defines 通常更适合真正的常量;这是因为#defines 可以内联到使用它们的位置,而const 全局变量通常需要内存读取,特别是如果它们是在不同的翻译单元中定义的。

    也就是说,复杂的常量结构非常适合 const 全局变量 - 字符串、structs、数组等。

    【讨论】:

    • 我完全不同意#defines 通常比真正的常量更受欢迎。 enum 避免了您提到的问题并提供了一个符号名称。或者更确切地说:我不同意它们通常应该优于真正的常量。
    • 枚举仅限于int 的范围,请注意。这在嵌入式平台上工作时很重要...
    • 在现代系统上,consts 被放置在实际保护它们的 .rodata 部分中
    【解决方案3】:

    在大多数现代实现中,编译器试图通过将全局const 变量放在只读部分中来做更多的事情,以通过符号进行访问。它实际上在许多系统上保护它们免受更改。 一些示例:Linux 系统上的段错误和 Windows 上的错误或在使用微控制器时将代码放入 FLASH 中。

    这当然是 100% 实现,但很高兴知道具有内存保护硬件和现代编译器的现代机器不仅仅遵循标准

    【讨论】:

      【解决方案4】:

      const 限定的变量不被视为编译时常量,它们有一个明显的限制:const int 不能用于定义数组的大小。(历史原因但不是编译器的限制,但 C++ 纠正了这种疏忽)

      您可以选择:

      #define SIZE 5   /* preprocessor */
      enum { SIZE=5 }; /* compiler */
      

      【讨论】:

        【解决方案5】:

        大多数 C 程序遵循的标准是将所有常量作为宏 (#define) 放在单独的头文件中。

        【讨论】:

          猜你喜欢
          • 2012-08-09
          • 2020-03-19
          • 2011-09-17
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2010-09-19
          • 2011-10-13
          相关资源
          最近更新 更多