这是相当牵强的,但是以下代码"安全" (即保证不会导致分段错误):
std::vector<int> vec(1); // Ensures that &vec[0] is valid
vec.reserve(100);
memset(&vec[0], 0x123, sizeof(int)*100); // Safe?
我意识到这很难看 - 我只是想知道它是否技术上安全,而不是“非常好”。我猜它唯一的用法可能是忽略存储在给定索引之外的值。
请注意! How can I get the address of the buffer allocated by vector::reserve()?涵盖了相同的主题,但如果这是安全并且存在陷阱,那么我会更感兴趣。
编辑:原始代码错误,将原始memcpy
替换为memset
。
答案 0 :(得分:16)
不,这不安全。
在reserve()
之后,保证向量不会重新分配存储,直到达到capacity()
。
但是,该标准没有说明向量实现可以对size()
和capacity()
之间的存储做什么。也许它可以用于一些内部数据 - 谁知道?也许地址空间只是保留而不是映射到实际的RAM?
访问[0..size]之外的元素是未定义的行为。 可以进行一些硬件检查。
答案 1 :(得分:2)
向量重新分配使现有指针,引用等无效。预留可以触发重新分配(23.3.6.2,[vector.capacity])但是你要取的地址是第一个元素在最终重新分配之后(在这种情况下根本不会发生,但除此之外)。所以我发现代码没有问题。
答案 2 :(得分:2)
首先请注意,memset
会将0x123
截断为单个字节并写入,而不是写入四字节模式。
然后,不要这样做,只需使用容器:std::vector<int> vec(100, whatever_value_you_want);
但是要回答这个问题,如果编译器没有为任何事情使用分配的空间,它可能看起来特别适用于POD类型。当然,如果有人打电话给resize
,insert
,push_back
等,那么它会将您已经写入内存的任何内容都吹走,并且矢量的大小也会出错。没有理由编写这样的代码。