#include<iostream>
#include<string>
#include<set>
#include<time.h>
#include<cstring>
#include <vector>
#define LL long long
#define MAXN 100010
using namespace std;
int tot=0;
class A {
private:
int lima;
int limb;
int las=tot;
public:
A(){las=++tot;lima = 1;limb =12 ;cout<<las<<" A created;"<<endl;}
//explicit A(int a,int b):lima(a),limb(b){las=++tot;cout<<las<<" A common created"<<endl;} 会使得参数列表失效
A(int a,int b):lima(a),limb(b){las=++tot;cout<<las<<" A common created"<<endl;}
A(A&& a){las=++tot;lima = a.lima; limb = a.limb;cout<<las<<" A move created"<<endl;}
A(const A& a){las=++tot;lima = a.lima;limb = a.limb; cout<<las<<" A copy created"<<endl;}
~A(){cout<<las<<" A deleted"<<endl;};
};
inline A liss(int lim1,int lim2)
{
A limp(lim1,lim2);
return limp;
}
vector<A>vec;
int main()
{
//A lim(12,15);
vec.reserve(20); /*把这个打开,防止扩容机制造成的拷贝构造结果混乱*/
//vec.push_back(lim);
//vec.emplace_back(lim);
//cout<<"where delete?"<<endl;
/*观察结果:过程相同,都调用拷贝构造函数直接深拷贝构造,原因:传入参数都为左值*/
//vec.push_back(A(lim));
//vec.emplace_back(A(lim));
//cout<<"where delete?"<<endl;
/*观察结果:过程一样,都产生临时变量并且调用移动构造函数,和网上说的不一样,推测函数返回值可能有问题,以下再次验证*/
//vec.push_back(liss(125,133));
//vec.emplace_back(liss(125,153));
//cout<<"where delete?"<<endl;
/*观察结果:过程一样,都产生临时变量并且调用移动构造函数,和网上说的不一样,查询原码发现,部分编译器对于单个右值返回,pushback会使用右值引用接住后再次使用move转为右值并调用emplaceback*/
//vec.push_back({158,957});
//vec.emplace_back(158,957);
//cout<<"where delete?"<<endl;
/*观察结果:
1 A common created
2 A move created
1 A deleted
3 A common created
where delete?
2 A deleted
3 A deleted
这就意味着对于传入右值参数的情况,push_back会先直接构造一个类,然后调用移动构造函数将类移动到vec末尾
而emplace_back会直接在末尾构造这个类
注意有的编译器会产生优化,单个右值传入的情况编译器会直接优化为emplaceback执行
而参数列表能够明显的看出区别,和网上所说一致,实验成功
*/
//int a1=147,b1=254;
//vec.push_back({a1,b1});
//vec.emplace_back(a1,b1);
//cout<<"where delete?"<<endl;
/*观察结果:
1 A common created
2 A move created
1 A deleted
3 A common created
where delete?
2 A deleted
3 A deleted
这就意味着对于传入左值参数的情况,和上面是一样的
*/
return 0;
}
