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。
对于这两个程序的问题,我收获很大,特别是第二个让我理解了拷贝构造函数的调用机制。
C++析构函数造成Debug Assertion Failed的问题的更多相关文章
- (转)Debug Assertion Failed! Expression: _pFirstBlock == pHead
最近在VS上开发C++程序时遇到了这个错误: Debug Assertion Failed! Expression:_pFirstBlock == pHead 如图: 点击Abort之后,查看调用 ...
- Qt 调试时的错误——Debug Assertion Failed!
在VS2008中写qt程序时调试出现此问题,但在release模式下就不存在,在网上搜罗了一圈,是指针的问题. 问题是这样的: 需要打开两个文件,文件中数据类型是float,我使用QVector进行保 ...
- Solve Error Debug Assertion Failed Expression vector iterators incompatible Using PCL in Release Mode of VS2010
When using PCL 1.4.0 in the release mode building under VS2010, we might sometime get the error &quo ...
- Debug Assertion Failed!
问题并没有解决..... 不知道怎么回事,先都没有这样的情况... VC++调程序出现如下错误: Debug Assertion Failed! Program: D:wyuS ...
- C++ error:Debug Assertion Failed.Expression:_BLOCK_TYPE_IS_VALID(phead->nBlock)
Debug Assertion Failed.Expression:_BLOCK_TYPE_IS_VALID(phead->nBlockUse) 关于上面这个错误,我在上一篇文章中的程序遇到过了 ...
- Debug Assertion Failed! Expression: _pFirstBlock == pHead
点击Abort之后,查看调用栈,发现异常在函数return时被时产生,进一步看是vector的析构函数被调用时产生,以前没开发过C++项目,没什么经验,这个错误让我很困惑,第一,我电脑上并没有f盘:第 ...
- opencv检错:程序运行过程正常,当跳出函数时出现断言错误(Debug Assertion Failed)
转载http://blog.csdn.net/u012327581/article/details/51351780 1.问题描述 在VS2015下配置好Opencv后,程序在函数运行过程中正常,调试 ...
- MFC:“Debug Assertion Failed!” ——自动生成的单文档程序项目编译运行就有错误
今天照着孙鑫老师的VC++教程学习文件的操作,VS2010,单文档应用程序,项目文件命名为File,也就有了自动生成的CFileDoc.CFileView等类,一进去就编译运行(就是最初自动生成的项目 ...
- 读书笔记——Windows核心编程(2)禁止C运行时触发的所有Debug Assertion Failed对话框
1 定义一个函数 void _invalid_parameter( const wchar_t * expression, const wchar_t * function, const wchar_ ...
随机推荐
- vmware ubuntu14.04 忘记密码
重置root密码 启动系统,一直点击esc键盘,出现如下界面,选择Advanced options for Ubuntu 按回车键确认: 选择recovery mode,按 e : 到 linux / ...
- scaleform中ActionScript和UnrealScript的交互
转自:http://www.cnblogs.com/NEOCSL/p/4174134.html scaleform是制作UI的好工具: 1.他可以解放程序员用代码控制的UI效果,例如平移,旋转和缩放都 ...
- ACM之Java技巧
一.Java之ACM注意点 关于四舍五入 小数保留几位: DecimalFormat df = new DecimalFormat("0.00"); String num = d ...
- matlab下的caffe接口配置(Windows)
本文基于大部分网上方法 http://blog.csdn.net/d5224/article/details/51916178,外加一点自己的个人实际配置经历,环境变量在配置后尽管显示正确并且重启多次 ...
- WPF TabControl SelectionChanged 重复执行的问题
很邪门的问题,我曾经都感觉是微软的bug了. 问题是这样的:在我的tabcontrol下的tabitem中有一个combobox控件,由于一些原因,需要执行tabcontrol的SelectionCh ...
- CodeChef - ELHIDARR Find an element in hidden array(二分交互)
Find an element in hidden array There is an array of length N consisting of non-negative integers. T ...
- 利用URL重写隐藏复杂的URL
第一步:模拟映射页面 我们想在一个页面上点击guid.html链接,跳转到比较复杂URL的guid_{492f3e0b-848e-11da-9550-00e08161165f}.html页面.即定义一 ...
- react中创建组件以及使用
组件基本使用import React, { Component } from 'react'; // 在组件头部引用 class Home extends Component { // 创建类 ren ...
- es6常用方法
一.let 和 constlet 声明变量,只在所在的块区有效,不存在变量提升:var 存在变 量提升const 声明常量,只在所在块区有效 二.变量的解构赋值1.数组的解构赋值let [a, b, ...
- 检查浏览器是否有此插件如flash
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...