要声明类,可使用关键字 class,并在它后面依次包含类名,一组放在{}内的成员属性和成员函数, 以及结尾的分号。
class Human
{
// Member attributes:
string name;
string dateOfBirth;
string placeOfBirth;
string gender;
// Member functions:
void Talk(string textToTalk);
void IntroduceSelf();
...
};
通过关键字 class,C++ 提供了一种功能强大的方式,让您能够创建自己的数据类型,并在其中封装属性和使用它们的函数
类相当于蓝图,仅声明类并不会对程序的执行产生影响。在程序执行阶段,对象是类的化身。要使用类的功能,通常需要创建其实例—对象,并通过对象访问成员方法和属性
Human firstMan; // firstMan: an object of class Human
就像可以为其他类型(如 int)动态分配内存一样,也可使用 new 为 Human 对象动态地分配内存
int* pointsToNum = new int; // an integer allocated dynamically
delete pointsToNum; // de-allocating memory when done using
Human* firstWoman = new Human(); // dynamically allocated Human
delete firstWoman; // de-allocating memory
如果有一个指针 firstWoman,它指向 Human 类的一个实例,则可使用指针运算符(->)来访问成员,也可使用间接运算符(*)来获取对象,再使用句点运算符来访问成员:
Human* firstWoman = new Human();
(*firstWoman).IntroduceSelf();
firstWoman->dateOfBirth = "1970";
firstWoman->IntroduceSelf();
delete firstWoman;
如果对象是使用 new 在自由存储区中实例化的,或者有指向对象的指针,则可使用指针运算符(->) 来访问成员属性和方法:
#include <iostream>
#include <string>
using namespace std;
class Human
{
public:
string name;
int age;
void introduce_self()
{
cout << "i am " + name << " and am " << age << " years old " << endl;
}
};
int main(){
Human *jiangyu = new Human();
(*jiangyu).age = 28;
(*jiangyu).name = "jiangyu";
(*jiangyu).introduce_self();
cout << endl;
// 使用指针运算符访问成员属性和方法
jiangyu->age = 128;
jiangyu->name = "jiangyu_2";
cout << "use ->" << endl;;
jiangyu->introduce_self();
delete jiangyu;
return 0;
}
关键字public 和private
C++让您能够将类属性和方法声明为公有的,这意味着有了对象后就可获取它们;
也可将其声明 为私有的,这意味着只能在类的内部(或其友元)中访问。
#include <string>
#include <iostream>
using namespace std;
class Human
{
private:
int age;
string your_name;
public:
int get_age()
{
return age;
}
void set_age(int human_age)
{
age = human_age;
}
string get_name()
{
return your_name;
}
void set_name(string name)
{
your_name = name;
}
};
int main(){
Human* lilei = new Human();
int age_set = 20;
string the_name = "jiangyu";
(*lilei).set_age(age_set);
(*lilei).set_name(the_name);
cout << (*lilei).get_age() << endl;
cout << (*lilei).get_name() << endl;
delete lilei;
}
如果试图使用下述代码访问成员 age:
cout << (*lilei).age << endl; // compile error
报错 age 申明为private 非
通常是以编写 Human 类的程序员 认为的合适方式暴露 age 如 get_age()
构造函数
构造函数是一种特殊的函数(方法),在根据类创建对象时被调用。与函数一样,构造函数也可以 重载。
在类声明中实现(定义)构造函数
class Human {
public: Human()
{
// constructor code here
}
}
在类声明外定义构造函数
class Human {
public: Human(); // constructor declaration
};
// constructor implementation (definition)
Human::Human() {
// constructor code here
}
没有默认构造函数,而在如果提供了重载的构造函数时,C++编译器不会为您生成默认构造函数。如果没有提供重载的构造函数且没有提供默认构造函数时,编译器会提供一个默认构造函数。
包含初始化列表的构造函数
#include <string>
#include <iostream>
using namespace std;
class Human
{
private:
int age;
string your_name;
public:
Human(string name, int human_age)
:your_name(name),age(human_age)
{
cout << "Constructed a human called " << your_name;
cout << ", " << age << " years old" << endl;
}
};
int main(){
Human* lilei = new Human("hehe",13);
delete lilei;
}
初始化列表由包含在括号中的参数声明后面的冒号标识,冒号后面列出了各个成员变量及其初始值。
初始值可以是参数(如 humansName),也可以是固定的值。使用特定参数调用基类的构造函数时, 初始化列表也很有用
接受带默认值的参数的默认构造函数
#include <string>
#include <iostream>
using namespace std;
class Human
{
private:
int age;
string your_name;
public:
Human(string name = "hehe", int human_age = 13)
:your_name(name),age(human_age)
{
cout << "Constructed a human called " << your_name;
cout << ", " << age << " years old" << endl;
}
};
int main(){
Human* lilei = new Human();
delete lilei;
}
将sizeof( )用于类
运算符 sizeof( )指出类声明中所有数据属性占用的总内存量,单位为字节
友元函数
不能从外部访问类的私有数据成员和方法,但这条规则不适用于友元类和友元函数。要声明友元 类或友元函数,可使用关键字 friend
#include <string>
#include <iostream>
using namespace std;
class Human
{
private:
friend void display_age(const Human& person);
int age;
string your_name;
public:
Human(string name = "hehe", int human_age = 13)
:your_name(name),age(human_age)
{
cout << "Constructed a human called " << your_name;
cout << ", " << age << " years old" << endl;
}
};
void display_age(const Human& person)
{
cout << person.age << endl;
}
int main(){
Human* lilei = new Human();
cout << "Accessing private member age via friend function: ";
display_age(*lilei);
delete lilei;
}
第 8 行的声明告诉编译器,函数 display_age( )是全局函数,还是 Human 类的友元,因此能够访问 Human 类的私有数据成员。
友元类
第 8行指出 Utility 类是 Human 类的友元,该声明让 Utility 类的所有方法都能访问 Human 类的私有数据成员和方法。
#include <string>
#include <iostream>
using namespace std;
class Human
{
private:
friend class Utility; //友元类
int age;
string your_name;
public:
Human(string name = "hehe", int human_age = 13)
:your_name(name),age(human_age)
{
cout << "Constructed a human called " << your_name;
cout << ", " << age << " years old" << endl;
}
};
class Utility
{
public:
static void display_age(const Human& person)
{
cout << person.age <<endl;
}
};
int main(){
Human* lilei = new Human();
cout << "Accessing private member age via friend class: ";
Utility::display_age(*lilei);
delete lilei;
}