5

我正在开发内存密集型应用程序,它应该正确处理内存不足的情况。

我有类似的东西

class memory_manager {
    // returns true if slot created (and function is being run)
    // false otherwise
    static bool create_slot(int id, std::function<void (slot&)>); ........
}

此类处理、记录等所有内存不足问题,保留所有插槽的所有权,并驱动并发。

但是,我没有处理std::bad_alloc以下代码:

slot_data_to_copy dat;

memory_manager::create_slot(100, [&dat](slot& sx) { sx.assign_data(dat); });

我假设抛出是在捕获变量期间完成的。(我实际上捕获了更多,这只是一个示例)

闭包在哪里创建?我能控制它吗?或者,如果我以接受参数的方式更新管理器,例如

slot_data_to_copy dat;

memory_manager::create_slot<slot_data_to_copy>
       (100, dat, [](slot& sx, slot_data_to_copy& dat) 
           { sx.assign_data(dat); }
       );

是否保证它根本不抛出?

我在 Windows 上使用 Visual C++ 和在 Linux 上使用 GCC 进行编译,但我仅在 Windows 上观察到这种行为(在 linux 上,我可能在可以处理它的地方耗尽了内存)。

编辑:

http://en.cppreference.com/w/cpp/utility/functional/function/function - std::function 包含 nothrow 运算符。我可能遗漏了一些东西,但在这种(lambda)情况下使用的是哪一个?

4

2 回答 2

4

闭包在哪里创建?

一个 lambda 表达式创建一个未命名类型的对象,它只是一个普通的仿函数类。捕获的变量是该未命名类型的成员。

您的代码memory_manager::create_slot(100, [&dat](slot& sx) { sx.assign_data(dat); });基本上与以下内容相同:

slot_data_to_copy dat;

struct unnamed_lambda_type {
  slot_data_to_copy &dat;

  unnamed_lambda_type(slot_data_to_copy &dat_) : dat(dat_) {}

  void operator() (slot &sx) const {
    sx.assign_data(dat);
  }
};

memory_manager::create_slot(100, unnamed_lambda_type(dat) );

闭包在哪里创建?

闭包对象就像任何其他临时对象一样,通常分配在堆栈上。

于 2013-10-09T19:34:28.523 回答
1

闭包lambda;捕获的变量是匿名结构的数据成员(这就是 lambda)。创建你的 lambda 不能抛出bad_alloc;您的错误在其他地方(可能会创建std::function,这可能会将 lambda 复制到堆上)。

旁注:您在 lambda 中通过引用捕获;确保您slot_data_to_copy dat在调用 lambda 时没有被破坏。您应该按值复制它或立即调用 lambda。

于 2013-10-09T18:46:52.973 回答