c++ - 如何创建非 POD 类型的连续内存池?

标签 c++ c++11 memory-management pool

我有一个场景,我有多个操作以下列方式表示:

struct Op {
  virtual void Run() = 0;
};

struct FooOp : public Op {
  const std::vector<char> v;
  const std::string s;
  FooOp(const std::vector<char> &v, const std::string &s) : v(v), s(s) {}
  void Run() { std::cout << "FooOp::Run" << '\n'; }
};

// (...)

我的应用程序在多个阶段运行。在每一遍中,我都想创建许多这样的操作,并且在遍结束时我可以同​​时丢弃它们。所以我想为这些操作预分配一些内存块,并从这 block 内存中分配新的操作。我想出了以下代码:

class FooPool {
public:
  FooPool(int size) {
    foo_pool = new char[size * sizeof(FooOp)]; // what about FooOp alignment?
    cur = 0;
  }

  ~FooPool() { delete foo_pool; }

  FooOp *New(const std::vector<char> &v, const std::string &s) {
    return new (reinterpret_cast<FooOp*>(foo_pool) + cur) FooOp(v,s);
  }

  void Release() {
    for (int i = 0; i < cur; ++i) {
      (reinterpret_cast<FooOp*>(foo_pool)+i)->~FooOp();
    }
    cur = 0;
  }

private:
  char *foo_pool;
  int cur;
};

这似乎可行,但我很确定我需要以某种方式注意 FooOp 的对齐。此外,我什至不确定这种方法是否可行,因为操作不是 POD。

  • 我的方法有缺陷吗? (最有可能)
  • 执行此操作的更好方法是什么?
  • 有没有办法使用 unique_ptr 回收现有内存?

谢谢!

最佳答案

我认为此代码将具有类似的性能特征,而无需您处理新的和对齐的存储位置:

class FooPool {
public:
    FooPool(int size) {
        pool.reserve(size);
    }

    FooOp* New(const std::vector<char>& v, const std::string& s) {
        pool.emplace_back(v, s); // in c++17: return pool.emplace_back etc. etc.
        return &pool.back();
    }

    void Release() {
        pool.clear();
    }

private:
    std::vector<FooOp> pool;
}

这里的关键思想是您的 FooPool 本质上是在做 std::vector 所做的事情。

关于c++ - 如何创建非 POD 类型的连续内存池?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/51202249/

相关文章:

c - 是否可以在堆栈上分配结构并将其定义隐藏在源文件中?

c++ - std::optional 如何从初始值设定项列表中构造 std::variant ?

c++ - 运算符重载的基本规则和习惯用法是什么?

C++11 vector 在右值上进行复制

c++ - 如何在默认模板参数中引用自身类型?

c++ - 为什么数组匹配 std::extent 第二个 imp?

objective-c - 关于自动引用计数,我需要了解什么?

c++ - 我必须构建才能消除 Eclipse 中的错误吗?

c++ - std::move 是否总是按预期工作?

ios - ObjC - 如何明确地将所有权移交给将异步执行的 block ?