R S*_*ahu 21 c++ language-lawyer delete-operator c++11 c++03
在C++ 03标准中,我看到:
5.3.5删除
2如果操作数具有类类型,则通过调用上述转换函数将操作数转换为指针类型,并使用转换后的操作数代替本节其余部分的原始操作数.在任一替代方案中,如果操作数的值
delete是空指针,则操作无效.在第一个备选(删除对象)中,操作数的值delete应该是指向非数组对象的指针或指向表示此类对象的基类的子对象(1.8)的指针(第10节).如果不是,则行为未定义.在第二种方法(删除数组)中,操作数的delete值必须是由前一个数组new-expression产生的指针值.72)如果不是,则行为是未定义的.
在C++ 11 Draft Standard(N3337)中,我看到:
5.3.5删除
2如果操作数具有类类型,则通过调用上述转换函数将操作数转换为指针类型,并使用转换后的操作数代替本节其余部分的原始操作数.在第一个替代(删除对象)中,操作数的值
delete可以是空指针值,指向由前一个新表达式创建的非数组对象的指针,或指向表示基础的子对象(1.8)的指针这类对象的类别(第10条).如果不是,则行为未定义.在第二个备选(删除数组)中,delete的操作数的值可以是空指针值或由先前数组new-expression产生的指针值.如果不是,则行为未定义.
我已经强调了两个标准中规范之间的差异.我觉得奇怪的是,2003标准更加强调必须如何处理NULL指针,而2011标准没有说明实现必须做什么.
C++ 11标准的措辞是否在草案标准和实际标准之间发生了变化?如果是这样,怎么样?
如果标准草案的措辞在实际标准中保持不变,那么在2003年和2011年之间将强有力的陈述改为几乎没有任何理由的理由是什么?
Sha*_*our 24
看起来我们可以在缺陷报告348中找到这种变化的理由,其中说:
具体而言,标准在5.3.5 [expr.delete]第2段中说:
...如果delete的操作数的值是空指针,则操作无效.
标准没有指定术语"无效".从该上下文中不清楚,被调用的释放函数是否需要不起作用,或者delete-expression不应该调用释放函数.
此外,在第4段标准中说明了默认的释放功能:
如果delete-expression调用实现释放函数(3.7.4.2 [basic.stc.dynamic.deallocation]),如果delete表达式的操作数不是空指针常量,...
为什么默认的释放函数和delete-expr的交互如此具体?
如果"无效"是解除分配函数的要求,则应在3.7.4.2 [basic.stc.dynamic.deallocation]或18.6.1.1 [new.delete.single]和18.6.1.2中说明[ new.delete.array],应该明确说明.
解决方案的一部分是你所注意到的措辞的变化,尽管围绕这种措辞的语言已经发生了很大变化,但摆脱无效语言的逻辑仍然存在,它不是一个定义明确的术语,所以应该是替换为指定语言.
Pup*_*ppy 10
最新的C++ 14草案(N3797)在本节中具有大致相同的措辞.但是这种行为同样强烈地指明,而不是完全相同的段落.
如果delete-expression的操作数的值不是空指针值,则delete-expression将调用该对象的析构函数(如果有)或要删除的数组的元素.在数组的情况下,元素将按地址递减的顺序销毁(即,与构造函数完成的顺序相反;见12.6.2).
如果delete-expression的操作数的值不是空指针值,则: - 如果没有省略要删除的对象的new-expression的分配调用(5.3.4),则delete-expression应为调用释放函数(3.7.4.2).从new-expression的分配调用返回的值应作为第一个参数传递给deallocation函数. - 否则,delete-expression不会调用释放函数(3.7.4.2).
这些段落显然与C++ 03一样强大.委员会不可能打破那些delete无效指针的程序的行为,因为这些程序很普遍,而且修复的成本太大了.这将使C++ 11无法实现.