【问题标题】:Why isn't placement new keyword/operator/function recognised without header?为什么没有标题就不能识别放置新关键字/运算符/函数?
【发布时间】:2021-08-24 06:36:05
【问题描述】:

如下:

int main()
{
    new int; // Works
    
    
    int* pmem = 0;

    new (pmem) int;// Doesn't recognize new keyword/operator/function???

}

在这种情况下,如果不包含 标头,它将无法识别“新”。这是为什么?为什么“新”不需要标题,但新位置需要?如果'new'需要定义一个函数,那么为什么'int* a = new int;'工作?由于它没有在任何地方定义,我认为它是语言的一部分。然而 'new (&int) int;' “新位置”不是语言的一部分?

Visual Studio 报错:

'operator new':没有重载函数需要 3 个参数

【问题讨论】:

  • 我什至不会依赖它。当您包含 <new> 时,新位置由授权提供。当您包含<iostream> 时,它对您“有效”是一种症状,而不是治愈方法。你熟悉的operator new 的常规形式是implicitly available 标准授权
  • 这实际上不是重复的。虽然相关,但它提出(并回答)了一个不同的问题。

标签: c++ new-operator


【解决方案1】:

新展示位置不仅仅用于“无操作”分配。这是为new 提供超出对象大小的额外参数的通用术语。一个标准的例子是std::nothrow

由于我们提供了参数,编译器必须进行重载解析以选择合适的operator new 函数。这意味着必须事先声明重载。最基本的重载是隐式声明的(以某种方式),而void* operator new(std::size_t, void* ptr) noexcept(执行此“分配”的standard library function)不是。所以我们必须包含标题 (<new>*) 以进行重载解析。

这是 30 年前做出的设计选择。它可以由另一个内置完成,但由于将对象放入预涂的原始存储被认为是一项非常高级的功能(与简单的动态分配相反),因此添加库依赖关系可能看起来并没有太大的障碍.


* - 您看到<iostream> 影响了行为,因为它可能直接或间接包含<new>。这是允许的,但不是必需的行为。

【讨论】:

  • 我正在努力解决这个问题。 new 被称为运算符,但它看起来很像重载的函数调用。我叫 new (pToMem) obj{ };就好像 size_t 的第一个参数是隐式提供的。它是一个函数调用,而普通的 new 是一个运算符?
  • new T 是一个表达式。它的部分评估涉及调用函数 (operator new)。这总是正确的。不直观的一点是,总是隐式声明一个函数。这是因为简单的动态分配是许多程序中使用的非常基本的东西。 new 表达式的其他形式需要显式声明。
  • 我自己永远无法构造函数,对吧?所以如果我想在我想要的内存中构造一个对象,比如在我的容器中,这是我能做到的唯一方法,放置新的,我需要包含标题,对吧?
  • 是的。这是准确的。
  • 但是当你调用new int; 时,为什么编译器不需要做重载解析来调用void* operator new(std::size_t)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2015-10-23
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多