“新操作员”和“新操作员”之间的区别?


126

“新操作员”和“新操作员”之间有什么区别?


3
嗨,你能澄清这个问题吗?看起来某处有错字。
迪马·马连科

17
问题的措词正确,请参阅下面的答案。动态分配内存的方法是使用new运算符。该运算符可以重载。为了区分默认运算符和重载版本,默认名称称为“新运算符”,而重载版本称为“新运算符”。
Thomas Matthews,2009年

2
怎么做。我是新来的,不知道。
Sandeep,

Answers:


127

我通常会尝试用不同的措词来区分两者,以便更好地区分两者,但这在任何情况下都是一个好问题。

new运算符是分配原始内存的函数-至少从概念上讲,它与并无太大区别malloc()。除非您编写自己的容器之类的东西,否则这是很不常见的,但是您可以直接将operator称为new,例如:

char *x = static_cast<char *>(operator new(100));

也有可能在全局范围或特定类中重载new运算符。IIRC,签名是:

void *operator new(size_t);

当然,如果您重载了一个新的运算符(无论是全局的还是一个类),您也将希望/需要重载匹配的运算符删除。值得一提的是,还有一个单独的运算符new []用于为数组分配内存-但几乎可以肯定,最好完全忽略整个混乱情况。

new运算符通常是您从免费商店中创建对象所使用的运算符:

my_class *x = new my_class(0);

两者之间的区别在于new运算符分配原始内存,而没有其他分配。new运算符首先使用new运算符分配内存,然后为正确类型的对象调用构造函数,因此结果是在该内存中创建的真实活动对象。如果该对象包含任何其他对象(嵌入式对象或作为基类),则这些构造函数也将被调用。


18
对于不同的措词+1,该标准在各处使用新表达式,并且只有在使用新运算符来引用调用位置时才使用该表达式。我倾向于做同样的:运营商新分配器新的表达方式的使用。
DavidRodríguez-dribeas 2011年

3
新的表达是从new开头的整个短语。那么,您怎么称呼它的“新”部分呢?如果调用新运算符是错误的,那么我们就不应该调用sizeof运算符或&address-of运算符“ sizeof”(当它的行为类似于一个时)。
卡兹(Kaz)2012年

1
跟进卡兹的话,也许这个问题应该改写为:新操作符和新操作符有什么区别?:)
CS

2
“新操作员” vs“新关键字”
user997112 2014年

2
@antred:您可以使用来释放它operator delete(x);
杰里·科芬

35

“新操作员”

class Foo
{
public:
        void* operator new( size_t );
}

“新操作员”:

Foo* foo = new Foo();

在这个例子中,new Foo()调用Foo::operator new()

换句话说,“新运算符”调用“ operator new()”,就像+运算符调用一样operator +()


13
new不是C ++中的运算符。sizeof,例如,是一个运算符,但newdelete不是。newdelete是关键字,以及这些关键字形成的语法结构称为new-expressiondelete-expression
AnT

2
嗯,如果有的话,sizeof是语法结构,new并且delete都是有效的,合法的,可重载的运算符。从一切,我见过,new而且delete都是运营商。参见[cplusplus.com] [ cplusplus.com/doc/tutorial/classes2/]
奥斯丁·海德

7
不正确 正式的C ++术语是由语言规范而不是某些网站定义的术语。在语言规范中,没有诸如“新运算符”之类的术语,但有诸如“ operator new功能” 之类的术语。再次,sizeof被explicilty称为“操作员”,而newdelete从未被称为运营商。
2009年

6
AndreyT:不正确。C ++标准确实将“新”称为运算符,请参见13.5 / 1。

3
@AndreyT:我想像您一样,new运算符分配器,new-expression则是用法。我查看并检查了第5.3.4 / 3节中的当前标准是否使用术语new运算符。后来在§5.3.4/ 8它命名分配器充当运营商新的运营商新的[]
大卫·罗德里格斯- dribeas

22

以下是来自Scott Meyers的《更有效的C ++》一书的引文:

新操作员调用一个函数来执行必要的内存分配,并且您可以重写或重载该函数以更改其行为。新操作员调用以分配内存的函数的名称是new操作员。


7
该术语显然是由书的作者发明的(或者也许是从过时的资料中借来的)。在正式的C ++术语中,没有“新运算符”这样的术语。
AnT

2
@AndreyT:我在C ++ 11中搜索了“新运算符”,发现它在四个地方被引用。具体来说,有两次提到“展示位置新运算符”
Mooing Duck 2015年

11

“新操作员”和“新操作员”之间没有区别。两者都指的是同一件事:可重载/可替换operator new函数,通常为new-expressions创建的对象执行原始内存分配

还要注意的是既不语言规范存在术语(这是官方术语的定义来源)。

new在程序中使用它创建对象时,它称为new-expressionNew-expression由关键字组成new和语法定义的其他语法部分组成。此表达式语法的任何部分都不会被称为“运算符”。

原始内存分配功能operator new正式称为“ operator new功能”。请注意,单词operatornew按此顺序只是两个单独的C ++语言关键字。他们没有形成英文术语“ operator new”。在语言规范中,找不到任何将“ operator new”作为英语术语的引用。每次这只是两个独立关键字的组合,它们为内存分配函数产生声明语法。

同样,在履历表中:在C ++中没有正式的英语术语,如“新操作员”或“新操作员”。在语言规范中,前一个序列仅作为关键字的组合而不是英语术语出现。后者根本不存在。


14
您似乎迷失了一些学究性的手淫。该标准在地点上含糊不清,这是其中之一。“讨论新运算符”与“讨论加号运算符”或“讨论+运算符”一样有意义。

7

创建新对象时,使用运算符new 分配内存,然后调用构造函数以初始化内存。在新的运营商确实都分配和初始化,那里的运营商新的只做分配。


6

OP的问题措词不正确。最好将其定为“'新运营商'与'新表达'之间的区别?” 注意“新的操作员”通常也指“新的操作员功能”。

周围有很多正确的答案,下面是我的:

1>'new expression'调用'operator new'分配原始内存,然后调用构造函数

apple * p = new apple(); //new expression

2>'operator new'仅分配原始内存,与malloc差别不大

void* mem = operator new(sizeof(apple)); //just like calling malloc()
apple* p2 = new(mem) apple(1); //call construct here using placement new.

2

new运算符:C ++支持使用new运算符动态分配对象。新操作员从称为免费存储的池中为对象分配内存。新运算符将特殊功能运算符称为new。

operator new:如果请求的存储空间为零字节,则operator new返回指向不同对象的指针(即,重复调用operator new将返回不同的指针)。如果分配请求的内存不足,则new操作符将返回NULL或引发异常。运算符new的第一个参数必须为size_t类型(在STDDEF.H中定义的类型),并且返回类型始终为void *。

这是MSDN链接,以获取更多详细信息:

操作员新功能

新的运营商


1
稍微澄清一下:新的非放置运算符必须始终抛出分配失败(根据标准);和展示位置形式(例如::new(std::nothrow))都可以执行此操作(该特定示例返回空指针)。

1
  1. new是运算符和关键字。

    请参阅[1]在2.13和&在2.12中。

  2. new做两件事:T * t = new T(arg);

    1)为对象分配内存:void * ptr = 运算符new(sizeof(T));

    // 运算符new是一个函数(就像c中的malloc一样),而不是运算符。(请参见3.7.4中的[1])。但是条款7 [2]表示它也是一个运算符。在我看来,运算符和函数之间的差异很小,当您回想起重载运算符是由函数实现时,您可以看到它。

    //我们可以重载此操作符/函数(新的操作符),以执行我们想要的操作。

    2)在分配的内存中初始化对象:在ptr上调用T :: T(arg)

    // 只有编译器才能执行此操作。我和你都不能。

    //如果T有成员,则编译器还将调用成员对象的构造函数和基类的构造函数。而且此调用是递归的。只有编译器可以做到这一点。

  3. 因此,new操作员会执行new任务的一部分,只有在这一部分中我们才能做些事情。

    [1]:ISO / IEC,N3690。http://ww.open-std.org/jtc1/sc22/wg21/docs/papers/2013/n3690.pdf

    [2]:Meyers,Scott。有效的C ++,第3版。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.