【问题标题】:Appending to a vector with push_back as opposed to [ ]使用 push_back 而不是 [ ] 附加到向量
【发布时间】:2014-05-30 14:44:47
【问题描述】:

我正在使用的程序的一部分需要将字符串值附加到向量。当像这样附加字符串值时,我遇到了分段错误:

for(int i = 0; i < testvec.size(); i++) {
    testvec[i] = oldvec[i];
}

但我的程序使用此代码正确编译和执行:

for(int i = 0; i < testvec.size(); i++) {
    testvec.push_back(i);
}

这就是它的要点,我们所做的是更新一个向量

【问题讨论】:

  • 第二个循环要么不做任何事情(如果testvec.size() == 0),要么直到程序最终耗尽内存(否则)才终止。只要oldvec.size() &gt;= testvec.size(),第一个循环就可以(但实际上并不附加任何内容),否则会表现出未定义的行为。无论如何,我不清楚这两段代码到底应该实现什么。
  • 要将一个向量的内容附加到另一个向量的末尾,请写testvec.insert(testvec.end(), oldvec.begin(), oldvec.end());。不需要循环。
  • 问题是什么?

标签: string c++11 vector


【解决方案1】:

operator[] 索引到vector 中的已存在空间。假设您的向量是默认构造的:

std::vector<std::string> v;

然后对任何i 执行v[i] 是未定义的行为,因为不能保证任何空间都已分配用于存储值。它实际上相当于:

std::string *storage;
storage[i] = "...";

您的代码看起来仍然不正确:我猜它实际上是这样的:

for(int i = 0; i < oldvec.size(); i++) {
    testvec.push_back(oldvec[i]);
}

这是一个很长的路要走:构造一个向量,其中的元素包含在另一个向量中,最简单的方法是:

std::vector<std::string> testvec(oldvec.begin(), oldvec.end());

【讨论】:

  • 我实际上编辑了我的帖子,我认为您的答案是针对编辑之前的问题。我的代码实际上是用 push_back 而不是 operator[] 编译的。
  • std::vector&lt;std::string&gt; testvec(oldvec); 更简单。
【解决方案2】:

push_back() 是将项目附加到向量的正确方法。它将根据需要重新分配底层内存块以适应新项目。但是,operator[] 不会增长向量,因此它只能在向量先前使用 resize() 调整大小或使用 push_back() 插入时插入新项目。如果您尝试使用operator[] 而不这样做,则会导致未定义的行为。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-11-22
    • 1970-01-01
    • 2013-03-28
    相关资源
    最近更新 更多