记录 C++ vector reserve 导致的脏数据问题

今天解决了一个程序运行时崩溃问题。

程序功能是:查找所有图层的关系,判断是否存在环路。代码逻辑是:遍历所有图层,把每个图层的继承图层、包含图层列出来放进各自的 std::vector 中,之后读取 vector 中的数据对图层关系做成环判断。程序运行到判断阶段时读取到的图层关系数据越界,超过了 vector 的 size。

代码类似这样:

class LoopCheck {
public:
  LoopCheck(size_t layer_count) : layer_array_(layer_count) {}

  void check() {
    // ...
    size_t idx = calculateId();
    getLayer(idx).doSomething();
    // ...
  }

  Layer& getLayer(size_t idx) {
    if (layer_array_.capacity() < idx) {
      layer_array_.reserve(idx +1);
    }
    return layer_array_[idx];
  }
private:
  std::vector<Layer> layer_array_;
};

崩溃原因是, LoopCheck 构造参数 layer_count 不准确,因此在 getLayer() 内判断了一下 layer_array_ 容量是否足够,不够就扩容一下。然而这里忽略了没有重置 layer_array_size() ,导致扩容出来的元素是脏数据,之后获取这些元素 Layer 内部数据,实际是其他 Layer 的索引,再来这里 getLayer() ,自然就都乱掉了。

解决:就在 reserve 之后加了一个 layer_array_.resize(idx + 1)

本作品采用《CC 协议》,转载必须注明作者和本文链接
讨论数量: 0
(= ̄ω ̄=)··· 暂无内容!

讨论应以学习和精进为目的。请勿发布不友善或者负能量的内容,与人为善,比聪明更重要!