对象生存周期和系统优化

返回值与临时量
#if 0
/*
返回值规则:
	1.类类型
		都是以临时量带回及原因
	2.其他类型
					字节数	<=4   由eax寄存器带回
							>4   <=8   由eax  和edx 寄存器带回
							>8      由临时量带回
*/
class Test
{
public:
	Test(int a=10):ma(a)  
	{
		cout<<"Test::Test(int)"<<endl;
	}

Test(const Test& rhs):ma(20)
{
	cout<<"Test::Test(Test)"<<endl;
}
	//const Test * const
int getValue()const
{
	
	return ma;
}
void  show()
{
	getValue();
	cout<<"ma"<<ma<<endl;
}
~Test()
{
	cout<<"Test::~Test()"<<endl;
}

private:
	int ma;
};

Test Getval(Test rhs)
{
	Test temp=rhs;										
	return temp;
}
int main()
{
	Test test1(20);
	Getval(test1).show();
}

/*
	以对象类型返回,不管几个字节 都是由临时量带回来
					为什么?  

		代码----》》					Test test1(20);
									Getval(test1).show();

		打印---》》》					Test::Test(int)
										Test::Test(Test)
										Test::Test(Test)
										Test::Test(Test)
										Test::~Test()
										Test::~Test()
										ma20
										Test::~Test()
										Test::~Test()
Getval全局函数结束后返回了一个临时对象	

	用临时对象调用show函数
	之所以用临时对象返回  而不用寄存器返回
	是因为寄存器不能取地址 ,而对象调用成员方法需要把对象地址传给
		this指针所以只能以临时量的方式返回,临时对象是存放在内存中,
	通过返回值已经知道了类型  就是一个显式生成临时对象  
		存放在内存中 相当于一个普通的变量
		
	Test::Test(int)       Test test1;
	Test::Test(Test)	  Test rhs=test1;
	Test::Test(Test)	  Test temp=rhs;
	Test::Test(Test)	  以临时对象返回
空类问题
		空类  
			class Node
			{
				public:
				void show()
				{
					cout<<"hello"<<endl;
				}
			};

		gcc中空的结构体是0
那么空类的字节为什么是1?
		因为用对象调用成员方法的时候需要传递对象地址给this指针,
		0是没有地址的, 所以最少需要1个字节大小的地址
*/
返回临时量的几种情况
  • 显式生成临时对象是为了生成新的对象(即为了生成 作返回值用途 的临时对象);

     class Test
     {
     public:
     	Test(int a=10):ma(a)  
     	{
     		cout<<"Test::Test(int)"<<endl;
     	}
    
     Test(const Test& rhs):ma(20)
     {
     	cout<<"Test::Test(Test)"<<endl;
     }
     	//const Test * const
     int getValue()const
     {
     	
     	return ma;
     }
     void  show()
     {
     	getValue();
     	cout<<"ma"<<ma<<endl;
     }
     ~Test()
     {
     	cout<<"Test::~Test()"<<endl;
     }
     
     private:
     	int ma;
     };
     
     Test Getval(Test& rhs)
     {
     	return Test(rhs);
     }
     
     int main()
     {
     	Test test1(20);
     	Getval(test1);
     }
     /*
     			Test::Test(int)
     			Test::Test(Test)
     			Test::~Test()
     			Test::~Test()
     
     			 return Test(rhs);
     */
    
  • Test(rhs);显示生成了临时对象,然后显式生成临时对象的方式 优化生成 作返回值用途的临时对象
    又因为main函数 Test test2=Getval(test1) 又以生成作返回用途的临时对象的方式 来优化生成 test2

     class Test
     {
     public:
     Test(int a=10):ma(a)  
     {
     	cout<<"Test::Test(int)"<<endl;
     }
    
     Test(const Test& rhs):ma(20)
     {
     	cout<<"Test::Test(Test)"<<endl;
     }
     	//const Test * const
     int getValue()const
     {
     	
     	return ma;
     }
     void  show()
     {
     	getValue();
     	cout<<"ma"<<ma<<endl;
     }
     ~Test()
     {
     	cout<<"Test::~Test()"<<endl;
     }
     
     private:
     	int ma;
     };
     
     Test Getval(Test& rhs)
     {
     	return Test(rhs);
     }
     
     int main()
     {
     	Test test1(20);
     	Test test2=Getval(test1);
     }
    
  • 不能返回局部变量的指向或者引用
    Test test2=Getval(test1);
    Test& Getval(Test& rhs){return Test(rhs);}
    返回的是局部对象地址

     class Test
     {
     public:
     Test(int a=10):ma(a)  
     {
     	cout<<"Test::Test(int)"<<endl;
     }
    
     Test(const Test& rhs):ma(20)
     {
     	cout<<"Test::Test(Test)"<<endl;
     }
     	//const Test * const
     int getValue()const
     {
     	return ma;
     }
     void  show()
     {
     	getValue();
     	cout<<"ma"<<ma<<endl;
     }
     ~Test()
     {
     	cout<<"Test::~Test()"<<endl;
     }
     
     private:
     	int ma;
     };
    
     Test& Getval(Test& rhs)
     {
     	return Test(rhs);
     }
     int main()
     
     {
     	Test test1(20);
     	Test test2=Getval(test1);
     }
    
     Test(rhs);显示生成了临时对象rhs, 
     Test& 不生成作返回用途的对象  只返回显式生成的临时对象的地址
     	又因为main函数  Test test2=Getval(test1) 
     					对象test2 =  临时对象的地址
     							Getval(地址)解引用
     						Test test2 = *
    
     			返回的是一个地址,所以整个过程没有优化
    
     临时对象生存周期  ;结束  return Test(rhs);结束就调用析构
    
     			而返回的却是这个已经销毁的临时对象的地址。
    
  • 不能返回局部变量的指向或者引用
    //Test test2=Getval(test1);
    //Test& Getval(Test& rhs){Test tmp(rhs);return tmp;}
    //调用拷贝构造后覆盖tmp的栈帧

     class Test
     {
     public:
     	Test(int a=10):ma(a)  
     	{
     		cout<<"Test::Test(int)"<<endl;
     	}
    
     Test(const Test& rhs):ma(20)
     {
     	cout<<"Test::Test(Test)"<<endl;
     }
     	//const Test * const
     int getValue()const
     {
     	
     	return ma;
     }
     void  show()
     {
     	getValue();
     	cout<<"ma"<<ma<<endl;
     }
     ~Test()
     {
     	cout<<"Test::~Test()"<<endl;
     }
     
     private:
     	int ma;
     };
     
     Test& Getval(Test& rhs)
     {
     	Test tmp(rhs);
     	return tmp;
     }
     int main()
     {
     Test test1(20);
     Test test2=Getval(test1);
     }
      开始,实参传形参,作形参变量或者对象的初始化。
     	然后开辟Getval函数的函数栈帧,
     		tmp这个对象再这个栈帧上的一个内存块
     	将tmp返回 即 将这个对象地址返回  
     		函数调用完要清栈帧
     	 tmp就要将这个内存块归还给系统,tmp就成了无效的对象
     	 
     	 Test test2=Getval(test1);
     	 要调用拷贝构造函数生成test2,就会由栈帧的开辟,
     	 	就会覆盖tmp的栈帧,值就会发生变化出错
    
函数指针
typedef int(*FUNC)(int,int);
int sum(int a,int b)
{
	return a+b;
}
int main()
{
	FUNC fun=&sum;
	int n=*fun(10,20);
}
.*操作符
class Test
{
public:
	Test(int a):ma(a)
	{
	}
	void show()
	{
		cout<<ma<<endl;
	}
private:
	int ma;
};
typedef void(Test::*func)();
int main()
{
	Test t1(10);
	func =&Test::show;
	(t1.*func)();
	
	Test t2=new Test(20);
	(t2->*func)();
}
->*操作符
class Test
{
public:
	Test(int a):ma(a)
	{
	}
	void show()
	{
		cout<<ma<<endl;
	}
private:
	int ma;
};
typedef void(Test::*func)();
int main()
{
	Test t2=new Test(20);
	(t2->*func)();
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值