Skip to content

Latest commit

 

History

History
42 lines (32 loc) · 1.87 KB

File metadata and controls

42 lines (32 loc) · 1.87 KB

条款49:了解new-handler的行为

operator new 无法满足某一内存分配需求时,它会抛出异常,在此之前,它会先调用一个客户指定的错误处理函数,即new-handler。为了指定这个函数,客户必须调用 set_new_handler

namespace std {
  typedef void (*new_handler)();
  new_handler set_new_handler(new_handler p) throw();
}

set_new_handler 的参数是个指针,指向 operator new 无法分配足够内存时该调用的函数,其返回值也是个指针,指向set_new_handler被调用前正在执行的new-handler函数。

你可以这样使用 set_new_handler

void outOfMem() {
  std::cerr << "Unable to satisfy request for memory\n";
  std::abort();
}
int main() {
  std::set_new_handler(outOfMem);
  int* pBigDataArray = new int[100000]l
  ...
}

如果new分配内存失败,outOfMem会被调用,程序在输出一个信息后终止。

一个设计良好的new-handler函数必须做以下事情:

  • 让更多内存可被使用。 一般做法是使用内存池。
  • 安装另一个new-handler。 如果当前的new-handler无法分配更多内存,就可以调用另一个可以分配更多内存的new-handler替换自己。
  • 移除new-handler。 将null指针传给set_new_handler,operator new会在内存分配不成功时抛出异常。
  • 抛出bad_alloc。 会被传播到申请内存的代码处。
  • 不返回。 通常调用abort或exit。

C++并不支持class专属的new-handler,但其实也不需要。你可以令每一个class提供自己的set_new_handler和operator new即可。set_new_handler使客户可以指定class专属的new-handler,operator new确保在分配class对象时用class专属的new-handler替换global new-handler。

请记住

  • set_new_handler允许客户指定一个函数,在内存分配无法获得满足时被调用。