zoukankan      html  css  js  c++  java
  • C++析构函数造成Debug Assertion Failed的问题

    昨天写了两个程序,均出现了析构函数造成Debug Assertion Failed的问题,由于是初学c++怎么想也想不通问题出在哪里。今天早上经人指点终于明白问题所在了。下面贴出代码和问题解析:(以下内容摘自本人在csdn论坛求助的帖子)

    第一个问题程序:
    //Teacher_Level.h

    #pragma once
    #include<iostream>
    using namespace std;
    int num=0;
    class Teacher
    {
    public:
    char *title;

    Teacher()
    {
    title=new char[50];
    }

    ~Teacher()
    {
    cout<<"called:"<<++num<<endl;
    if(title!=NULL)
    {
    delete[] title;
    title=NULL;
    }
    }

    };

    class Level
    {
    public:
    char *position;

    Level()
    {
    position=new char[50];
    }

    ~Level()
    {
    if(position!=NULL)
    {
    delete[] position;
    position=NULL;
    }
    }
    };


    class Teacher_Level:public Teacher,public Level
    {
    public:
    void show()
    {
    cout<<"The teacher_level:"<<endl;
    cout<<"Title:";
    puts(title);
    cout<<"Position:";
    puts(position);
    }
    };

    //main.cpp

    #include "Teacher_Level.h"
    #include<iostream>
    using namespace std;

    int main()
    {
    Teacher_Level p;
    p.title="professor";
    p.position="header";
    p.show();

    return 0;
    }

    报错如下:



    第二个问题程序:
    //CShop.h

    #pragma once
    #include<string.h>
    #include<iostream>
    using namespace std;

    class CShop
    {
    public:
    char *product;
    int price;

    CShop();
    CShop(char *CProduct,int CPrice);
    ~CShop();

    friend ostream& operator<<(ostream& os,CShop p)
    {
    cout<<"Product:";
    puts(p.product);
    cout<<"Price:";
    cout<<p.price;

    return os;
    }

    };

    CShop::CShop()
    {
    product=new char[50];
    }

    CShop::CShop(char *CProduct,int CPrice)
    {
    product=new char[50];
    strcpy(product,CProduct);
    price=CPrice;
    }

    CShop::~CShop()
    {
    if(product!=NULL)
    {
    delete[] product;
    product=NULL;
    }
    }


    //main.cpp

    #include "CShop.h"
    #include<iostream>
    using namespace std;

    int main()
    {
    char *product="book";
    int price=120;
    CShop p(product,price);
    cout<<"The information of the shop:"<<endl;
    cout<<p<<endl;

    return 0;
    }

    报错如下:

    正确解答:

    第一个:
    Teacher_Level p;  // 这里调用了构造函数,给title分配了内存
    p.title="professor";  // 这里又直接把title指向了常量区,导致析构函数里面企图delete一个常量区指针
    应该照着第二个程序的思路来给title赋值。

    第二个程序的问题稍微有点复杂。
    friend ostream& operator<<(ostream& os,CShop p)
    这里的p是按值传递的,编译器要调用拷贝构造函数来创建一个新对象。但是你自己没写拷贝构造函数,所以编译器自己生成了一个拷贝构造函数,问题由此产生,因为编译器的拷贝构造函数是所谓“浅拷贝”,简单的复制了product的地址。然后销毁这个新对象的时候就把product的地址delete了。你可能会说,delete之后把product赋值NULL了,但那是针对那个临时对象的,main里面的p的product指针没有变动,还指向最初的new的结果,然后退出main的时候就再次delete,导致出错。
    把这个<<重载函数的参数改成&p可以绕过这个问题,但是根本的解决方法是自己写一个拷贝构造函数,不是简单的复制指针,而是重新new一个指针然后strcpy。

    对于这两个程序的问题,我收获很大,特别是第二个让我理解了拷贝构造函数的调用机制。

  • 相关阅读:
    vue通过webpack打包后怎么运行
    vue中请求本地的json数据
    electron打包成桌面应用程序的详细介绍
    Web应用架构-Services
    Web应用架构-Full-text Search Service
    Web应用架构-Job Queue & Servers
    Web应用架构-Caching Service
    Web应用架构-Database
    设计模式:设计模式概述&JDK中的应用
    常见面试问题总结
  • 原文地址:https://www.cnblogs.com/tankeee/p/3957308.html
Copyright © 2011-2022 走看看