成员列表初始化
创建变量,并将其初始化是创建函数的必要部分。
#include <iostream>
#include <string>
class Entity
{
private:
std::string m_name;
public:
Entity()
{
m_name = "nothing"
}
Entity (const std::string& name)
{
m_name = name;
}
const std::string& GetName()const
{
return m_name;
}
};
int main()
{
Entity e;
std::cout<<e.GetName()<<std::endl;
Entity e1("shaojie");
std::cout<<e1.GetName()<<std::endl;
std::cin.get();
}
控制台显示
nothing
shaojie
在这里我们用到了两个构造函数,并且对函数进行重载。目的就是在不输入时初始化m_name为nothing,在有输入时初始化其为shaojie。
我们用成员初始化列表再写一遍函数
#include <iostream>
#include <string>
class Entity
{
private:
std::string m_name;
public:
Entity():m_name("nothing")
{
}
Entity (const std::string& name):m_name(name)
{
}
const std::string& GetName()const
{
return m_name;
}
};
int main()
{
Entity e;
std::cout<<e.GetName()<<std::endl;
Entity e1("shaojie");
std::cout<<e1.GetName()<<std::endl;
std::cin.get();
}
控制台显示
nothing
shaojie
我们就是将花括号内部赋值换到:后边,对就是这么简单。它有什么作用呢?看下面的代码
#include <iostream>
#include <string>
class Entity
{
private:
std::string m_name;
int x,y,z;
public:
Entity():m_name("nothing")
{
x = 0;
y = 0;
z = 0;
void Init();
}
Entity (const std::string& name):m_name(name)
{
}
const std::string& GetName()const
{
return m_name;
}
};
int main()
{
Entity e;
std::cout<<e.GetName()<<std::endl;
Entity e1("shaojie");
std::cout<<e1.GetName()<<std::endl;
std::cin.get();
}
我们加入xyz并将其初始化,还加入函数Init()。看上去乱乱的,我们将其如下改写
#include <iostream>
#include <string>
class Entity
{
private:
std::string m_name;
int x,y,z;
public:
Entity():m_name("nothing"),x(0),y(0),z(0)
{
void Init();
}
Entity (const std::string& name):m_name(name)
{
}
const std::string& GetName()const
{
return m_name;
}
};
int main()
{
Entity e;
std::cout<<e.GetName()<<std::endl;
Entity e1("shaojie");
std::cout<<e1.GetName()<<std::endl;
std::cin.get();
}
我们将数值初始化放在:后边,这样只要看花括号内就是到时执行某种函数。
private:
std::string m_name;
int m_score;
public:
Entity():m_name("nothing"),score(0)
{
}
还有一件事我们在初始化多个时“:”后要按照private创建变量的顺序去初始化,否则部分编译器会报错。
初始化成员列表就是将变量初始化与函数分开,变量放在:后,函数放在{},加强代码可读性。
初始化对象
栈建立
初始化对象我们无形中用过许多次了自从如何创建Log类。
#include <iostream>
#include <string>
class Entity
{
private:
std::string m_name;
public:
Entity():m_name("nothing"){}
Entity (const std::string& name):m_name(name){}
const std::string& GetName()const
{
return m_name;
}
};
int main()
{
Entity e;
std::cout<<e.GetName()<<std::endl;
Entity e1("shaojie");
std::cout<<e1.GetName()<<std::endl;
std::cin.get();
}
我们用上文提到的Entity类举例子,初始化对象实际就是创建实例在main中。
e和e1两个对象分别在Entity中用两个不同的初始化函数,这就是初始化还对象。
不过还有一个问题Entity e ;与Entity e1("shaojie");都是在栈(笔记15提到过)上创建的,就是说我们如果在函数内创建对象,函数结束,栈内内存都被释放,如下栗子。
#include <iostream>
#include <string>
class Entity
{
private:
std::string m_name;
public:
Entity():m_name("nothing"){}
Entity (const std::string& name):m_name(name){}
const std::string& GetName()const
{
return m_name;
}
};
void Function()
{
Entity e1("shaojie");
}
int main()
{
std::cout<<e1.GetName()<<std::endl;
std::cin.get();
}
我们将Entity e1的初始化放在Function内,因为我们写的创建的对象是在栈中建立的,所以运行到Entity的}时,e1就被释放,无法打印出“shaojie”。
堆建立
怎么办呢?在堆上建立。
#include <iostream>
#include <string>
class Entity
{
private:
std::string m_name;
public:
Entity():m_name("nothing"){}
Entity (const std::string& name):m_name(name){}
const std::string& GetName()const
{
return m_name;
}
};
int main()
{
//Entity e1("shaojie");
Entity* e1 = new Entity("shaojie");
std::cout<<(*e1).GetName()<<std::endl;
delete e1;
std::cin.get();
}
来看看我们更改了什么
1.Entity e1("shaojie");我们对Entity更改为指针
2.我们在Entity ("shaojie")这个构造函数之前加入了new
3.输出流改为*e1指针
4.加入了delete e1
我先来解释3,就是因为1Entity变为指针所以他要变成指针。那么为什么1要变为指针呢?
因为2的关键字“new”。new就是在堆上创建对象的关键字,他将对Entity(“shaojie”)进行操作并返回Entity在堆上分配的地址,正因为其返回的是一个地址所以解释了2进而解释了1.
4因为new的存在我们在堆上创建了对象,还记得堆与栈的区别,我们需要选择位置手动释放e1
delete e1;的位置看我们的意愿。
总的来说,就在栈与堆的生存时间上,那我们会不会在堆建立时候忘记delete这行代码呢?可能是会的。智能指针可以帮助我们(挖坑)
标签:std,初始化,const,name,18,C++,Entity,string From: https://blog.csdn.net/weixin_64418869/article/details/140684374