C++ 使用delete运算符删除空指针

C++ 使用delete运算符删除空指针,c++,void-pointers,C++,Void Pointers,代码有什么问题吗。它应该是什么。因为它正在抛出一个错误。运算符“delete”,应用于void*参数 int i; void *ptr = &i; delete ptr; 您的代码将无法工作,因为您试图删除未动态分配的内容。 无论如何,删除空指针是未定义的,请参阅以获取更多信息,确实是非常顽皮的代码 你没有用我的地址;使用void*ptr=&i 相反您的编译器非常宽容地发出您的代码 您正在从堆栈中删除。不好的。您只能删除 你的新事物 如果需要,编译器不知道要删除多少内存 传递void

代码有什么问题吗。它应该是什么。因为它正在抛出一个错误。运算符“delete”,应用于void*参数

int i;
void *ptr = &i;

delete ptr;

您的代码将无法工作,因为您试图删除未动态分配的内容。

无论如何,删除空指针是未定义的,请参阅以获取更多信息,确实是非常顽皮的代码

  • 你没有用我的地址;使用
    void*ptr=&i
    相反您的编译器非常宽容地发出您的代码
  • 您正在从堆栈中删除。不好的。您只能
    删除
    
    你的新事物
  • 如果需要,编译器不知道要删除多少内存 传递
    void*
    ,因为所有
    sizeof
    数据都丢失了

  • 您应该只删除分配给new的内容

    代码有什么问题吗

    除了
    inti

    第二行尝试将整数转换为指针。在特殊情况下,您可以使用
    reinterpret_cast
    将其强制通过编译器;但是,只有当整数包含有效的指针值时,程序才会正常运行。(更新:问题现在已被编辑,取而代之的是
    i
    的地址;因此此行不再错误)

    第三行尝试使用无效指针类型删除无效内存

    它应该是什么

    还有别的。不知道你想做什么,就不可能说出来。也许你想要:

    int i;
    void * ptr = &i;  // Points to `i`, losing type information.
    
    运算符
    delete
    ,应用于
    void*
    参数

    int i;
    void *ptr = &i;
    
    delete ptr;
    
    那总是错的。您只能
    删除以前分配给
    新建的
    对象;指针必须指向正确的类型

    (或基类,如果是带有虚拟析构函数的类类型)

    因此,以下是正确的;但是没有意义,除非你有充分的理由进行动态分配:

    int * ptr = new int;
    delete ptr;
    
    当然,如果您编写的代码应该能够抵抗内存泄漏和运行时错误,那么您应该使用容器和智能指针等类型来管理所有动态内存。因此,如果需要创建动态对象,应执行以下操作:

    std::unique_ptr<int> ptr(new int);
    
    std::unique_ptr ptr(新int);
    
    如果要在当前范围的末尾删除它或将其移动到另一个范围中;或

    auto ptr = std::make_shared<int>();
    
    auto ptr=std::make_shared();
    

    如果要在多个作用域之间共享所有权。无论哪种情况,指针都会在您完成对象后自动删除它。

    throw
    通常在运行时上下文中使用。您说的是编译器报告您的代码有错误。@PeterWood:上面的代码可能编译得很好…@OliCharlesworth:原始代码无法编译;我希望这个版本能给出一个警告(这将有助于解释运行时错误)。这是关于同一主题的第二个问题。你想达到什么目标?因为你显然是用错误的方式做的。你提到的链接没有回答我的问题。int*i=新的int;void*ptr=i;删除ptr;“这样行吗?”阿南回答得很好。看看第二个答案。int*i=new int;void*ptr=i;删除ptr;这样行吗?@Anand:不行,因为您必须使用
    int*
    删除
    int
    。如果没有正确的类型信息,
    delete
    会给出未定义的行为。那么在这种情况下如何删除ptr?@Anand:
    delete i
    delete static_cast(ptr)
    。但是你真的不应该一开始就在手动删除上胡闹;当然不应该使用
    void*
    来管理动态资源。这是一个多么好的答案+1绝对正确,但这不是错误消息的原因。是的,由于无法使用new分配类型为void的指针,因此也无法“删除”它。您可以。只需将代码更改为
    int*i=newint;void*ptr=i
    ptr
    现在指向使用
    new
    创建的对象,但由于其类型,您无法删除它。但是您没有分配void类型的指针,您分配了int类型之一,并将其分配给了void指针。如果
    派生的
    继承自
    ,并且它们具有虚拟析构函数,
    派生*i=新派生;基准*ptr=i;删除ptr是完全合法的。不能删除
    void*
    ,因为
    void
    不是类型,仅此而已。