【发布时间】:2023-03-23 08:35:02
【问题描述】:
考虑以下代码:
unsigned char* a = new unsigned char[100];
void* a1 = reinterpret_cast<void*>(a);
operator delete[](a1);
short* b = new short[100];
void* b1 = reinterpret_cast<void*>(b);
operator delete[](b1);
在我看来,它是标量类型的有效语法,因为 delete-expression 等效于调用析构函数和运算符 delete。 POD 类型也一样:
struct POD {
int i;
float f;
char c;
};
POD* c = new POD[100];
void* c1 = reinterpret_cast<void*>(c);
operator delete[](c1);
标量和 POD 类型的另一件事是使用 operator new 分配并使用 delete 表达式解除分配:
void* d = operator new[](sizeof(unsigned char) * 100);
unsigned char* d1 = reinterpret_cast<unsigned char*>(d);
delete[] d1;
void* e = operator new[](sizeof(short) * 100);
short* e1 = reinterpret_cast<short*>(e);
delete[] e1;
void* f = operator new[](sizeof(POD) * 100);
POD* f1 = reinterpret_cast<POD*>(f);
delete[] f1;
所有这些示例似乎都是格式正确的,但我没有设法找到它是否真的如此。有人可以确认或告诉我我错在哪里吗?特别是我担心所有这些类型都有不同的对齐方式,应该将其传递给 operator new/delete:
alignof(unsigned char) 1
alignof(short) 2
对齐(POD)4
UPD。有些人似乎将此问题与Is it safe to delete a void pointer? 混淆了。我问的是如何将expression new 与operator delete 和operator new 与expression delete 混合使用。根据标准表达形式是用运算符形式实现的。问题是混合它们对于标量和 POD 类型的有效性如何?
【问题讨论】:
-
如果他们没问题,我会感到非常惊讶。我的(受过教育?)猜测说这很可能是 UB。
-
@HostileFork 这个问题解决了一个完全不同的情况
-
哪种情况?正如现在所制定的那样,HostileFork 是正确的。
-
究竟是什么保证
new int[10]返回的指针与它从内部调用operator new[](whatever)获得的指针相同,并且whatever == 10*sizeof(int)?
标签: c++ memory new-operator delete-operator