回忆一下类的相关知识:
看一段代码:
当三个参数的构造函数执行完以后,这时候返回的是一个匿名对象,当从三个参数的构造函数返回以后,匿名对象就会调用析构函数,这时候m_c的值就会是一个垃圾值。 这里需要说明的是,如果创建的匿名对象没有变量来接他,就会立即调用析构函数进行释放。
new和delete操作符专题
new运算符动态分配堆内存
使用形式: 指针变量 = new 类型(常量);
指针变量 = new 类型[表达式];
作用:从堆分配一块“类型”大小的存储空间,返回首地址
其中:"常量"是初始化值,可缺省
创建数组对象时,不能为对象指定初始值
delete运算符释放已分配的内存空间
使用形式: delete 指针变量;
delete[] 指针变量;
其中,“指针变量”必须是new返回的指针
代码:
new、delete和malloc、free的区别
继续引申,看二级指针做函数参数的问题:
对于int等基础类型的new delete malooc free是可以混用的!!!!!!!!!
对于类而言,使用new和free,free只是释放了类Test的内存空间,但是Test里面如果有*p,p指向了内存空间,这时候free是不能调用析构函数进行这段内存空间的释放的。
但是还有一个大问题:free时能否留下一部分内存呢??看下面的代码:
static专题
static修饰的变量只会执行一次,来段代码看看:
注意下面的代码,假设有X类,定义了4个a b c d变量,有一个static yy,yy的值是在a b c d中共享的,也就是在a b c d中yy的值是一样的
静态数据成员的说明和初始化:
必须这样做!!!
小细节注意:
细节1:
细节2:
C++中类的内存模型分析
C++的class从面向对象理论出发,将变量(属性)和函数(方法)集中定义在一起,用于描述现实世界中的类。从计算机的角度,程序依然由数据段和代码段构成。
C++编译器如何管理类、对象、类和对象之间的关系的呢?
具体的说,具体对象调用类的方法,那么C++编译器是如何区分,是哪个具体的类调用这个方法的呢???
我们用内存模型解释C++的属性和方法
1) C++类对象的成员变量和成员函数是分开存储的
成员变量:
普通成员变量:存储于对象中,与struct变量有相同的内存布局和字节对齐方式
静态成员变量:存储于全局数据区中
成员函数:
存储于代码段中
我们看一下C++编译器是如何处理的:
我们看一下this指针:
总结:
1)C++类对象中的成员变量和成员函数是分开存储的。C语言中的内存模型仍然有效!
2)C++类中的普通成员函数都隐式包含一个指向当前对象的this指针
3)静态成员函数、成员变量属于类
4)静态成员函数与普通成员函数的区别:
静态成员函数不包含指向具体对象的指针
普通成员函数包含一个指向具体对象的指针
本节结束!!腰累坏了!!!
看一段代码:
#include "iostream"
using namespace std;
class Test
{
private:
int m_a;
int m_b;
int m_c;
public:
Test(int a, int b)
{
m_a = a;
m_b = b;
Test(a, b, 10);
}
Test(int a, int b, int c)
{
this->m_a = a;
this->m_b = b;
this->m_c = c;
}
~Test()
{
cout << m_a << "," << m_b << endl;
}
public:
int getnum()
{
return m_c;
}
};
void main()
{
Test t1(1, 2);
cout << t1.getnum() << endl;
system("pause");
}
仔细研究其中一段代码,我们先截取出来:
Test(int a, int b)
{
m_a = a;
m_b = b;
Test(a, b, 10);
}
Test(int a, int b, int c)
{
m_a = a;
m_b = b;
m_c = c;
}
当执行到
Test(a, b, 10);
时,会调用三个参数的Test构造函数,按照一般的函数的话,应该没有问题,但是这里是一个构造函数,是如何执行的呢????????????
当三个参数的构造函数执行完以后,这时候返回的是一个匿名对象,当从三个参数的构造函数返回以后,匿名对象就会调用析构函数,这时候m_c的值就会是一个垃圾值。 这里需要说明的是,如果创建的匿名对象没有变量来接他,就会立即调用析构函数进行释放。
new和delete操作符专题
new运算符动态分配堆内存
使用形式: 指针变量 = new 类型(常量);
指针变量 = new 类型[表达式];
作用:从堆分配一块“类型”大小的存储空间,返回首地址
其中:"常量"是初始化值,可缺省
创建数组对象时,不能为对象指定初始值
delete运算符释放已分配的内存空间
使用形式: delete 指针变量;
delete[] 指针变量;
其中,“指针变量”必须是new返回的指针
代码:
#include "iostream"
using namespace std;
//1.new/delete 作用手工分配堆内存 malloc/free
//2.new/delete int基础类型
//3.new/delete 数组
//4.new/delete类
void main()
{
cout << "*****************" << endl;
int *p1 = new int;
*p1 = 10;//初始化数值为10
cout << *p1 << endl;
delete p1;
cout << "*****************" << endl;
int *p2 = new int(10);//初始化数值为10
*p2 = 10;
cout << *p2 << endl;
delete p2;
cout << "*****************" << endl;
int *p3 = new int[10];//初始化大小为10
for (int i = 0; i < 10; i++)
{
p3[i] = i + 1;
cout << p3[i] << endl;
}
delete[] p3;
cout << "*****************" << endl;
system("pause");
}
new、delete和malloc、free的区别
#include "iostream"
using namespace std;
//1.new/delete 作用手工分配堆内存 malloc/free
//2.new/delete int基础类型
//3.new/delete 数组
//4.new/delete类
class Test1
{
private:
int m_a;
int m_b;
public:
Test1(int a, int b)
{
m_a = a;
m_b = b;
cout << "构造执行" << endl;
}
~Test1()
{
cout << "析构执行" << endl;
}
};
//C++中的new能自动调用构造函数,delete自动调用类的析构函数,malloc是不会这样的
void main3()
{
Test1 t1(1, 2);
Test1 *p1 = new Test1(3, 4);
delete p1;
}
void main()
{
cout << "*****************" << endl;
main3();
cout << "*****************" << endl;
system("pause");
}
C++中的new能自动调用构造函数,delete自动调用类的析构函数,malloc和free是不会调用构造和析构函数的。
继续引申,看二级指针做函数参数的问题:
int CreateTest1(Test1 ** p1)
{
Test1 *tmp = new Test1(4, 5);
*p1 = tmp;
return 0;
}
int CreateTest1(Test1 * &p2)
{
p2 = new Test1(6, 7);
return 0;
}
但是有一个大问题:new delete malloc free能混用吗?
对于int等基础类型的new delete malooc free是可以混用的!!!!!!!!!
对于类而言,使用new和free,free只是释放了类Test的内存空间,但是Test里面如果有*p,p指向了内存空间,这时候free是不能调用析构函数进行这段内存空间的释放的。
但是还有一个大问题:free时能否留下一部分内存呢??看下面的代码:
delete[] (p+1)
答案是否定的!!!头指针包含了其他的内容,虽然我不知道,但是老师说有,头指针就是头指针,不能从某一段内存开始释放。
static专题
static修饰的变量只会执行一次,来段代码看看:
#include "iostream"
using namespace std;
void getstatic()
{
int a = 10;
static int b = 20;
return;
}
void main()
{
getstatic();
getstatic();
system("pause");
}
另外;
//这个函数只能在当前的源文件里执行
static void myprintf()
{
printf("锄禾日当午,生活真是苦");
printf("送走C语言,来了它大叔(C++)");
}
注意下面的代码,假设有X类,定义了4个a b c d变量,有一个static yy,yy的值是在a b c d中共享的,也就是在a b c d中yy的值是一样的
class X
{
char xx;
static char yy;
int X::yy = 0;
X a, b, c, d;
};
静态数据成员的说明和初始化:
必须这样做!!!
public:
int mem;
static int smem;
counter(int a)
{
mem = a;
}
};
//必须在类的外面进行初始化
int counter::smem = 1;
记住一句话:static修饰的变量或函数,属于这个类,也属于具体的对象小细节注意:
细节1:
static int getnum()
{
return num;
}
num是static的,在函数类型前面要加上static
细节2:
class counter
{
private:
int m_a;
static int num;
public:
counter(int a)
{
m_a = a;
num++;
}
static void getcount()
{
//getcount()函数是属于一个类的,可以先于某一个变量存在
cout << m_a << endl;//ERROR
//static变量是多个类明
cout << num << endl;
}
};
类中的函数也是属于一个类的,在这个函数体内是不能调用公共成员变量的,因为成员函数也是属于这个类,可以先于某一个变量存在,所以无法这样使用。
cout << m_a << endl;//ERROR
C++中类的内存模型分析
C++的class从面向对象理论出发,将变量(属性)和函数(方法)集中定义在一起,用于描述现实世界中的类。从计算机的角度,程序依然由数据段和代码段构成。
C++编译器如何管理类、对象、类和对象之间的关系的呢?
具体的说,具体对象调用类的方法,那么C++编译器是如何区分,是哪个具体的类调用这个方法的呢???
我们用内存模型解释C++的属性和方法
1) C++类对象的成员变量和成员函数是分开存储的
成员变量:
普通成员变量:存储于对象中,与struct变量有相同的内存布局和字节对齐方式
静态成员变量:存储于全局数据区中
成员函数:
存储于代码段中
class C
{
private:
int a =0;
int b =1;
int c =2;
const int d;
public:
int getnum()
{
return a;
}
};
对于const成员变量是放在全局数据区,成员函数是放在了代码区,都不占用具体的内存空间。
我们看一下C++编译器是如何处理的:
我们看一下this指针:
Test(int a)
{
a = a;
}
C++编译器其实是这样的:
Test(this, int a)
{
this->a = a;
}
谁调用Test,this就是谁!!!!
总结:
1)C++类对象中的成员变量和成员函数是分开存储的。C语言中的内存模型仍然有效!
2)C++类中的普通成员函数都隐式包含一个指向当前对象的this指针
3)静态成员函数、成员变量属于类
4)静态成员函数与普通成员函数的区别:
静态成员函数不包含指向具体对象的指针
普通成员函数包含一个指向具体对象的指针
本节结束!!腰累坏了!!!