C++中nothrow的介绍及使用

在C中,使用malloc等分配内存的函数时,一定要检查其返回值是否为”空指针”,并以此作为检查内存操作是否成功的依据,这种Test-for-NULL代码形式是一种良好的编程习惯,也是编写可靠程序所必需的。

在C++中new在申请内存失败时默认会抛出一个std::bad_alloc 异常。如果出现这个异常,那就意味着内存耗尽,或者有其它原因导致内存分配失败。所以,按照C++标准,如果想检查new是否成功,则应该通过try catch捕捉异常。但有些编译器不支持try catch。C++标准化委员会不想遗弃这些Test-for-NULL的代码,所以他们提供了operator new的另一种可选形式---- nothrow,用以提供传统的Failure-yields-NULL行为。

当使用new申请一块内存失败时,抛出异常std::bad_alloc是C++标准中规定的标准行为,所以使用try { p = new int[size];} catch(std::bad_alloc) { … } 的处理方式。

struct nothrow_t {
	// placement new tag type to suppress exceptions
};

extern const nothrow_t nothrow; // constant for placement new tag

其中,nothrow_t通常是一个空结构,其唯一目的是提供编译器一个可根据重载规则识别具体调用的类型。用户一般简单地使用"new(std::nothrow) 类型"(nothrow是一个nothrow_t类型的常量)来调用这个placement new操作符。它与标准new的区别是,new在分配内存失败时会抛出异常,而"new(std::nothrow)"在分配内存失败时会返回一个空指针。

new operator分配内存失败后,缺省的行为不是返回NULL,而是抛出异常std::bad_alloc。所以判断返回值是否为NULL没有任何意义。

  std::nothrow: This constant value is used as an argument for operator new and operator new[] to indicate that these functions shall not throw an exception on failure, but return a null pointer instead.

By default, when the new operator is used to attempt to allocate memory and the handling function is unable to do so, a bad_alloc exception is thrown. But when nothrow is used as argument for new, it returns a null pointer instead.

This constant (nothrow) is just a value of type nothrow_t, with the only purpose of triggering an overloaded version of the function operator new (or operatornew[]) that takes an argument of this type.

以下是测试代码:

#include "nothrow.hpp"
#include <iostream>
#include <new> // std::nothrow

// reference: http://www.cplusplus.com/reference/new/nothrow/
int test_nothrow1()
{
	std::cout << "Attempting to allocate 1 MiB...";
	char* p = new (std::nothrow) char[1048576];
	if (p == 0)
		std::cout << "Failed!\n";
	else {
		std::cout << "Succeeded!\n";
		delete[] p;
	}

	return 0;
}

// reference: http://en.cppreference.com/w/cpp/memory/new/nothrow
int test_nothrow2()
{
	try {
		while (true) {
			new int[100000000ul];   // throwing overload
		}
	}
	catch (const std::bad_alloc& e) {
		std::cout << e.what() << '\n';
	}

	while (true) {
		int* p = new(std::nothrow) int[100000000ul]; // non-throwing overload
		if (p == nullptr) {
			std::cout << "Allocation returned nullptr\n";
			break;
		}
	}

	return 0;
}
GitHubhttps://github.com/fengbingchun/Messy_Test

  • 7
    点赞
  • 18
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
引用\[1\]的代码展示了在C++使用nothrow的示例。nothrow是一个常量对象,用于在使用placement new操作符时指定不抛出异常。通过使用"new(std::nothrow) 类型"的语法,可以在内存分配失败时返回一个空指针,而不是抛出std::bad_alloc异常。这与标准的new操作符的行为不同,标准的new操作符在内存分配失败时会抛出异常。 引用\[2\]的代码展示了nothrow_t结构的定义和使用。nothrow_t通常是一个空结构,其唯一目的是提供编译器一个可根据重载规则识别具体调用的类型。用户可以使用"new(std::nothrow) 类型"的语法来调用placement new操作符,并使用nothrow常量来指定不抛出异常。 引用\[3\]提到,在C++,标准的new操作符在申请内存失败时会抛出std::bad_alloc异常。为了检查new是否成功,可以使用try-catch语句来捕捉异常。然而,有些编译器不支持try-catch语句。为了解决这个问题,C++标准化委员会提供了operator new的另一种可选形式,即nothrow使用nothrow时,内存分配失败时会返回一个空指针,而不是抛出异常。这种行为可以用来替代传统的Test-for-NULL代码。 所以,总结起来,nothrowC++用于在内存分配失败时返回一个空指针,而不抛出异常。它可以通过使用"new(std::nothrow) 类型"的语法来指定不抛出异常的方式进行使用。 #### 引用[.reference_title] - *1* *2* *3* [C++nothrow介绍使用](https://blog.csdn.net/liu0808/article/details/86629987)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v91^insertT0,239^v3^insert_chatgpt"}} ] [.reference_item] [ .reference_list ]

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值