读书中字符数组/字符串如何存储在二进制文件(C/C++)中? https://stackoverflow.com/q/71932148/364696,我在思考原始字符串涉及的各种方式,"Nancy"
,将在生成的二进制文件中完好无损地显示。那个帖子的案例是:
int main()
{
char temp[6] = "Nancy";
printf("%s", temp);
return 0;
}
显然,在一般情况下(编译器无法确认是否temp
是未突变的),它实际上必须初始化一个堆栈本地数组以允许将来的突变;数组本身必须分配空间(在堆栈上,或者可能使用寄存器来实现真正奇怪的架构),并且必须在每次调用函数时填充它(让我们假设这不是main
在 C++ 中仅调用一次,并且通常在 C 中仅调用一次),以避免重入问题等。是否将初始化硬编码到程序集中,或者执行memcpy
与程序的常量数据部分无关;肯定有一些东西必须在每次调用时初始化。
相比之下,如果char temp[6] = "Nancy";
被替换为以下任意一项:
const char *temp = "Nancy";
-
char *temp = "Nancy";
(仅限 C;在 C++ 中,文字为const char[]
,尽管实际上它们在 C 中也不可变)
static const char temp[6] = "Nancy";
static char temp[6] = "Nancy";
那么程序不需要在每次调用时分配任何基于数组长度的资源(在情况 #1 和 #2 中只需分配一个指针变量),并且在除情况 #4 之外的所有情况下,它都可以将只读内存中的数据放入烘焙到二进制文件的数据常量(#4 会将其放入读写内存部分,但它仍然可以烘焙到二进制文件中并加载写入时复制)。
我的问题:标准是否提供了余地const char temp[6] = "Nancy";
行为等同于static const char temp[6] = "Nancy";
?两者都是不可变的,修改它们是违反规则的。我知道的唯一区别是:
- Without
static
,您希望数组的地址与其他本地地址位于同一位置,而不是位于程序内存的其他部分(可能会影响缓存性能)
- Without
static
,从技术上讲,您是说变量在每次调用时创建和销毁
我没有看到任何明显的问题可观察到的标准行为:
- 除了未定义的行为之外,您无法观察数组的存在和停止存在,例如返回一个指向
temp
,在没有保证的情况下
- 你不能合法地计算
ptrdiff_t
对于不相关的变量(仅在给定数组内,加上所述数组的最后一位虚拟元素)
so I'd think编译器可以安全地“视为static
对于这种情况,按照假设规则;没有办法观察差异,所以它可以做任何它感觉最好的事情。
我是否遗漏了 C 或 C++ 标准所缺少的任何内容require某种每次调用的初始化const
但非static
函数作用域数组?如果 C 和 C++ 标准不一致,我也想知道。
Edit:正如 Barmar 在常量中指出的那样,有标准合法的方法来检测这种行为在特定的编译器中, e.g.:
int myfunc() {
const char temp[6] = "Nancy";
const char temp2[6] = "Nancy";
return temp == temp2; // true if compiler implicitly made them static or combined them, false if not
}
or:
int otherfunc(const char *s) {
const char temp[6] = "Nancy";
return s == temp;
}
int myfunc() {
const char temp[6] = "Nancy";
return otherfunc(temp); // true if compiler implicitly made them shared statics, false if not
}