静态内存实例中的字符串计数

时间:2013-07-28 14:51:26

标签: c++ c string memory static

据我所知,编译时类C字符串只作为一个实例保存在静态内存中。例如,我在下面的gcc 4.6运行示例中得到了true。但我想知道它总是真的可以携带。 C和C ++上的行为很有趣。

#include <iostream>

bool amIportable(const char* value) {
  const char* slocal = "Hello";
  return (slocal==value);
}

int main() {
  const char* s = "Hello";
  std::cout << std::boolalpha 
            << amIportable(s) << '\n'
            << amIportable("Hello") << '\n';
}

4 个答案:

答案 0 :(得分:12)

不,这并非总是如此,也不是便携式的。

合并相同的字符串文字是由编译器和链接器协同执行的优化。 GCC和Microsoft编译器的最新版本都支持它,但只有在设置某些优化开关时才会支持它。

而且它不仅仅是一个“开启”或“关闭”功能。不同的编译器和不同的优化设置也会影响积极地执行此操作的方式。例如,有时字符串文字仅在单个函数的范围内合并,有时则在翻译单元的级别上发生,有时链接器可能会涉及跨多个翻译单元进行合并。

这是允许的,因为C和C ++标准将此行为保留为依赖于实现。

答案 1 :(得分:9)

不,它的实现依赖于C和C ++。

C11§6.4.5/ 7 字符串文字

  

如果这些数组的元素具有适当的值,则未指定这些数组是否相同。如果程序试图修改这样的数组,则行为是未定义的。

C ++11§2.14.5/ 12 字符串文字

  

是否所有字符串文字都是不同的(即存储在非重叠对象中)是实现定义的。尝试修改字符串文字的效果未定义。

答案 2 :(得分:2)

  

但我不知道它总是如此

不,至少C标准说的是“两个相同的字符串文字是否存储在同一个数组中是实现定义的”。

答案 3 :(得分:2)

您正在比较两种不同的字符串文字 具有相同的价值。根据C ++标准,它是 实现定义了相同的字符串文字是否占用 相同的内存与否(这意味着实现必须 记录它的作用);根据C标准,它是 不确定的。 (我认为C ++标准允许 实现以记录&#34;字符串的内容 如果相同内容的文字共享相同的实例 是在相同的翻译单位,并不共享相同 否则。)

如果你的目标是能够只比较指针,通常 解决方案是使用一个函数(静态,如果它是一个类成员) 返回字符串文字:

char const*
value()
{
    return "Hello";
}

bool
isHello( char const* str )
{
    return str == valule;
}

然后确保通过获取字符串的所有实例 致电value()