字面数字是否被视为常量?

时间:2010-08-07 23:37:54

标签: c++ c

对于诸如PI之类的内容总是更好地#define它们或将它们声明为const,这样编译器就可以进行优化,并且它变得不那么容易出错。然而,我想知道,如何对待陈述中的字面数字?例如:

float x;
const int y = 60;
x = y / 3.0f;

在这个例子中,如何处理3.0f?它会继承常量的优化吗?

4 个答案:

答案 0 :(得分:10)

将进行哪些优化取决于编译器。在您的情况下,C和C ++编译器通常都有足够的信息来将源代码优化为相同的机器代码。换句话说,它并不真正依赖于 literal 以及此代码中常量的内容。

话虽如此,术语 literal 常量的含义在C和C ++中有显着差异(并且您同时标记了问题C和C ++)

  • 在C 603.0f常量,但y不是常量。如果您愿意,可以调用y一个 const限定变量,但在C术语中它不是常量,从某种意义上说是{{1}在C中不是常量表达式

对于 literals ,在C语言中,术语 literal 仅适用于字符串文字(以及C99中的复合文字),即在你的代码中根本没有文字。

  • 在C ++中,y60文字,它们分别形成常量表达式(整数和浮点)。 3.0.f也是y类型的常量,在某种意义上,单个int是C ++中的常量表达式。< / LI>

您可能会注意到差异的情况与优化无关,而是与语言的定义方式无关。例如,在文件范围数组类型声明中使用上述y在C ++中是合法的,但在C

中则不合法
y

答案 1 :(得分:1)

由于使用#define,您要求预处理器进行文本替换,因此您的代码与以下内容相同:

#define VAL 3.0f

float x;
const int y = 60;
x = y / VAL;

如何优化直接const值显然取决于编译器。但是,如果你观察汇编代码(例如gcc生成的汇编代码),你会注意到编译器直接在浮点标准中写入编码值为3.0的二进制序列。

答案 2 :(得分:0)

在某些体系结构中,可以直接使用的字符串文字大小有限制。当字符串文字的大小太大时,编译器需要将常量存储在只读数据存储器中的某个位置,然后在需要时从内存中加载该值。

如果将值存储在常量变量中,编译器很可能只存储常量的一个值并适当地使用。但是,如果一个#defines常量,这只会使预处理器将文字值放入代码中,因此编译器可能没有意识到您使用相同的值并多次存储常量。因此,const变量优于#defines。

答案 3 :(得分:0)

答案取决于你是使用C还是C ++,所以你需要选择一个并停止假装它们是同一个东西。在C中,const关键字未声明常量;它声明了一个变量,试图修改该变量调用未定义的行为。在C中,除非它是静态/全局的,否则不应声明const int y;,并且旨在将内部信息从一个模块传递到另一个模块,而您不希望在另一个模块的编译时将其修复(例如,{{1}在共享库中可能很有用,尽管函数调用返回值会更清晰。)

至于优化,我所知道的C编译器不会优化你的例子中的除法,而且编译器是否被允许也是有疑问的。

至于C ++,你应该请一位C ++专家解释(我不是其中之一)。