当前位置:   article > 正文

C++面向对象-类的基本使用方法_c++类方法

c++类方法

什么是面向过程

什么是面向过程?
根据程序的执行过程,来设计软件的所有细节。

面向过程的缺点:
开发大型项目时,越来越难以把控,甚至失去控制。
后期维护、更新成本很大。

解决方案:
使用面向对象。

面向过程是C语言的东西,C++是面向对象

什么是面向对象?
面向对象是一种开发思想,一种全新的开发方式。
面向对象思想的重要性:
开发大型项目必备,是高级程序员的必备技能!

面向对象编程,最重要的第一个概念:类

“人类”是一个抽象的概念,不是具体的某个人。
“类”,是看不见,摸不着的,是一个纯粹的概念.
“类”,是一种特殊的“数据类型”,不是一个具体的数据。

注意:类, 和基本数据类型(char/int/short/long/long long/float/double)不同

什么是对象?

对象,是一个特定“类”的具体实例。

对象和普通变量有什么区别?
一般地,一个对象,就是一个特殊的变量,但是有跟丰富的功能和用法。

类的构成:方法和数据
在这里插入图片描述
在这里插入图片描述

对象的基本使用

这里我们用类来创建一个小萝莉


```cpp
#include <iostream>
#include <windows.h>
#include <string>

using namespace std;


class Lolita{
public://公有的,对外的
	void introduction();
	void hobby();

	string getName();
	int getage();
	int getstature();

private://私有的
	string name;
	int age;
	int Stature;
};//注意这里要带分号

void Lolita::introduction(){
	cout<<"你好,我是一名小萝莉!"<<endl;
}

void Lolita::hobby(){
	cout<<"我的兴趣爱好是:吃喝玩乐!"<<endl;
}

string Lolita::getName(){
	return name;
}

int Lolita::getage(){
	return age;
}

int Lolita::getstature(){
	return Stature;
}


int main(void){
	Lolita Bite;
	Bite.introduction();
	Bite.hobby();

	system("pause");
	return 0;
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53

上面是类最基本的用法

默认构造函数

没有参数的构造函数,称为默认构造函数。
1.合成的默认构造函数
但没有手动定义默认构造函数时,编译器自动为这个类定义一个构造函数。
1)如果数据成员使用了“类内初始值”,就使用这个值来初始化数据成员。【C++11】
2)否则,就使用默认初始化(实际上,不做任何初始化)

就好比下面这段代码,我调用上面这个萝莉的年龄age使用的就是默认构造函数

#include <iostream>
#include <windows.h>
#include <string>

using namespace std;


class Lolita{
public://公有的,对外的
	void introduction();
	void hobby();

	string getName();
	int getage();
	int getstature();

private://私有的
	string name;
	int age;
	int Stature;
};//注意这里要带分号

void Lolita::introduction(){
	cout<<"你好,我是一名小萝莉!"<<endl;
}

void Lolita::hobby(){
	cout<<"我的兴趣爱好是:吃喝玩乐!"<<endl;
}

string Lolita::getName(){
	return name;
}

int Lolita::getage(){
	return age;
}

int Lolita::getstature(){
	return Stature;
}


int main(void){
	Lolita Bite;
	Bite.introduction();
	Bite.hobby();
	cout<<"萝莉的年龄是:"<<Bite.getage()<<endl;

	system("pause");
	return 0;
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52

在这里插入图片描述
注意:
只要手动定义了任何一个构造函数,编译器就不会生成“合成的默认构造函数”
一般情况下,都应该定义自己的构造函数,不要使用“合成的默认构造函数”
【仅当数据成员全部使用了“类内初始值”,才宜使用“合成的默认构造函数”】
类内初始值就是在创建数据的时候已经初始化好了

手动定义的默认构造函数

#include <iostream>
#include <windows.h>
#include <string>

using namespace std;


class Lolita{
public://公有的,对外的
	void introduction();
	void hobby();
	Lolita();//手动定义的“默认构造函数”

	string getName();
	int getage();
	float getstature();

private://私有的
	string name;
	int age;
	float Stature;
};//注意这里要带分号

void Lolita::introduction(){
	cout<<"你好,我是一名小萝莉!"<<endl;
}

void Lolita::hobby(){
	cout<<"我的兴趣爱好是:吃喝玩乐!"<<endl;
}

string Lolita::getName(){
	return name;
}

int Lolita::getage(){
	return age;
}

float Lolita::getstature(){
	return Stature;
}

Lolita::Lolita(){
	name="咬米";
	age=18;
	Stature=1.6;
}

int main(void){
	Lolita Bite;
	Bite.introduction();
	Bite.hobby();

	cout<<"萝莉的名字是:"<<Bite.getName()<<endl;
	cout<<"萝莉的年龄是:"<<Bite.getage()<<"岁"<<endl;
	cout<<"萝莉的身高是:"<<Bite.getstature()<<"米"<<endl;

	system("pause");
	return 0;
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61

在这里插入图片描述
说明:如果某数据成员使用类内初始值,同时又在构造函数中进行了初始化,
那么以构造函数中的初始化为准。
相当于构造函数中的初始化,会覆盖对应的类内初始值。

自定义的重载构造函数

简单的说就是,自己可以在创建对象的时候自己根据需求自定义里面的值

#include <iostream>
#include <windows.h>
#include <string>

using namespace std;


class Lolita{
public://公有的,对外的
	void introduction();
	void hobby();
	Lolita();//手动定义的“默认构造函数”.
	Lolita(string x,int y,float j);//自定义构造函数

	string getName();
	int getage();
	float getstature();

private://私有的
	string name;
	int age;
	float Stature;
};//注意这里要带分号

void Lolita::introduction(){
	cout<<"你好,我是一名小萝莉!"<<endl;
}

void Lolita::hobby(){
	cout<<"我的兴趣爱好是:吃喝玩乐!"<<endl;
}

string Lolita::getName(){
	return name;
}

int Lolita::getage(){
	return age;
}

float Lolita::getstature(){
	return Stature;
}

Lolita::Lolita(){
	name="咬米";
	age=18;
	Stature=1.6;
}
//自定义构造函数
Lolita::Lolita(string x,int y,float j){
	this->name=x;
	this->age=y;
	this->Stature=j;
}

int main(void){
	Lolita Bite;
	Bite.introduction();
	Bite.hobby();
	cout<<"萝莉的名字是:"<<Bite.getName()<<endl;
	cout<<"萝莉的年龄是:"<<Bite.getage()<<"岁"<<endl;
	cout<<"萝莉的身高是:"<<Bite.getstature()<<"米"<<endl;

	cout<<"----华丽的分割线----"<<endl;

	Lolita tmp("小米",20,1.65);
	cout<<"萝莉的名字是:"<<tmp.getName()<<endl;
	cout<<"萝莉的年龄是:"<<tmp.getage()<<"岁"<<endl;
	cout<<"萝莉的身高是:"<<tmp.getstature()<<"米"<<endl;

	system("pause");
	return 0;
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74

在这里插入图片描述

拷贝构造函数

1.手动定义的拷贝构造函数
在下面的代码中,我把打印输出信息封装成了prin函数,太懒了,懒得一个个打印输出

什么时候调用拷贝构造函数

1.调用函数时,实参是对象,形参不是引用类型
如果函数的形参是引用类型,就不会调用拷贝构造函数
2.函数的返回类型是类,而且不是引用类型
3.对象数组的初始化列表中,使用对象。

#include <iostream>
#include <windows.h>
#include <string>

using namespace std;


class Lolita{
public://公有的,对外的
	void introduction();
	void hobby();
	void prin();

	Lolita();//手动定义的“默认构造函数”.
	Lolita(string x,int y,float j);//自定义构造函数
	Lolita(const Lolita&man);//手动定义的拷贝构造函数

	string getName();
	int getage();
	float getstature();

private://私有的
	string name;
	int age;
	float Stature;
};//注意这里要带分号

void Lolita::introduction(){
	cout<<"你好,我是一名小萝莉!"<<endl;
}

void Lolita::hobby(){
	cout<<"我的兴趣爱好是:吃喝玩乐!"<<endl;
}

void Lolita::prin(){
	introduction();
	hobby();
	cout<<"我的名字是:"<<name<<endl;
	cout<<"我的年龄是:"<<age<<"岁"<<endl;
	cout<<"我的身高是:"<<Stature<<"米"<<endl;
}

string Lolita::getName(){
	return name;
}

int Lolita::getage(){
	return age;
}

float Lolita::getstature(){
	return Stature;
}

Lolita::Lolita(){
	name="咬米";
	age=18;
	Stature=1.6;
}
//自定义构造函数
Lolita::Lolita(string x,int y,float j){
	this->name=x;
	this->age=y;
	this->Stature=j;
}
//使用自定义的拷贝构造函数
Lolita::Lolita(const Lolita&man){
	name=man.name;
	age=man.age;
	Stature=man.Stature;
}

int main(void){
	Lolita Bite1("蔡萝莉",20,1.63);
	Lolita Bite2(Bite1);
	Bite1.prin();
	cout<<"----华丽的分割线----"<<endl;
	Bite2.prin();

	system("pause");
	return 0;
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83

在这里插入图片描述

合成的拷贝构造函数

合成拷贝构造函数就是什么都不做,直接赋值,但是这样称为浅拷贝,遇到指针什么的就完犊子了,因为指针指的是地址
不定义拷贝构造函数,编译器会生成“合成的拷贝构造函数”
解决办法就是使用深拷贝,就是自己写一个,如果有指针类型的值,就用new开创一块新内存

#include <iostream>
#include <Windows.h>
#include <string>
#include <string.h>

using namespace std;

// 定义一个“人类”
class Human {
public:
	Human();
	Human(int age, int salary);
	Human(const Human&);  //不定义拷贝构造函数,编译器会生成“合成的拷贝构造函数”

	void eat();
	void sleep();
	void play();
	void work();

	string getName();
	int getAge();
	int getSalary();
	void setAddr(const char *newAddr);
	const char* getAddr();

private:
	string name = "Unknown";
	int age = 28;
	int salary;
	char *addr;
};

Human::Human() {
	name = "无名氏";
	age = 18;
	salary = 30000;
}

Human::Human(int age, int salary) {
	cout << "调用自定义的构造函数" << endl;
	this->age = age;      //this是一个特殊的指针,指向这个对象本身
	this->salary = salary;
	name = "无名";

	addr = new char[64];
	strcpy_s(addr, 64, "China");
}

Human::Human(const Human &man) {
	cout << "调用自定义的拷贝构造函数" << endl;
	age = man.age;      //this是一个特殊的指针,指向这个对象本身
	salary = man.salary;
	name = man.name;
	// 深度拷贝
	addr = new char[64];
	strcpy_s(addr, 64, man.addr);
}

void Human::eat() {
	cout << "吃炸鸡,喝啤酒!" << endl;
}

void Human::sleep() {
	cout << "我正在睡觉!" << endl;
}

void Human::play() {
	cout << "我在唱歌! " << endl;
}

void Human::work() {
	cout << "我在工作..." << endl;
}

string Human::getName() {
	return name;
}

int Human::getAge() {
	return age;
}

int Human::getSalary() {
	return salary;
}

void Human::setAddr(const char *newAddr) {
	if (!newAddr) {
		return;
	}

	strcpy_s(addr, 64, newAddr);
}

const char* Human::getAddr() {
	return addr;
}

int main(void) {
	Human  h1(25, 35000);  // 使用自定义的默认构造函数
	Human  h2(h1);  // 使用自定义的拷贝构造函数

	cout << "h1 addr:" << h1.getAddr() << endl;
	cout << "h2 addr:" << h2.getAddr() << endl;

	h1.setAddr("长沙");

	cout << "h1 addr:" << h1.getAddr() << endl;
	cout << "h2 addr:" << h2.getAddr() << endl;

	system("pause");
	return 0;
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
  • 88
  • 89
  • 90
  • 91
  • 92
  • 93
  • 94
  • 95
  • 96
  • 97
  • 98
  • 99
  • 100
  • 101
  • 102
  • 103
  • 104
  • 105
  • 106
  • 107
  • 108
  • 109
  • 110
  • 111
  • 112
  • 113

赋值构造函数

#include <iostream>
#include <windows.h>
#include <string>

using namespace std;


class Lolita{
public://公有的,对外的
	void introduction();
	void hobby();
	void prin();

	Lolita();//手动定义的“默认构造函数”.
	Lolita(string x,int y,float j);//自定义构造函数
	Lolita(const Lolita&man);//手动定义的拷贝构造函数
	Lolita& operator=(const Lolita&);//赋值构造函数

	string getName();
	int getage();
	float getstature();

private://私有的
	string name;
	int age;
	float Stature;
};//注意这里要带分号

void Lolita::introduction(){
	cout<<"你好,我是一名小萝莉!"<<endl;
}

void Lolita::hobby(){
	cout<<"我的兴趣爱好是:吃喝玩乐!"<<endl;
}

void Lolita::prin(){
	introduction();
	hobby();
	cout<<"我的名字是:"<<name<<endl;
	cout<<"我的年龄是:"<<age<<"岁"<<endl;
	cout<<"我的身高是:"<<Stature<<"米"<<endl;
}

string Lolita::getName(){
	return name;
}

int Lolita::getage(){
	return age;
}

float Lolita::getstature(){
	return Stature;
}

Lolita::Lolita(){
	name="咬米";
	age=18;
	Stature=1.6;
}
//自定义构造函数

Lolita::Lolita(string x,int y,float j){
	this->name=x;
	this->age=y;
	this->Stature=j;
}
//使用自定义的拷贝构造函数
Lolita::Lolita(const Lolita&man){
	name=man.name;
	age=man.age;
	Stature=man.Stature;
}
//赋值构造函数
Lolita& Lolita::operator=(const Lolita &man){
	if(this==&man){
		return *this;//坚持是不是对自己赋值比如:Bite1=Bite1
	}
	name=man.name;
	age=man.age;
	Stature=man.Stature;

	return *this;
}
int main(void){
	Lolita Bite1("蔡萝莉",20,1.63);
	Lolita Bite2;
	//Lolita Bite2(Bite1);//这样使用的是拷贝函数
	Bite2=Bite1;//这样使用的才是赋值构造函数
	Bite1.prin();
	cout<<"----华丽的分割线----"<<endl;
	Bite2.prin();

	system("pause");
	return 0;
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
  • 88
  • 89
  • 90
  • 91
  • 92
  • 93
  • 94
  • 95
  • 96
  • 97

在这里插入图片描述
如果没有定义赋值构造函数,编译器会自动定义“合成的赋值构造函数”,
与其他合成的构造函数,是“浅拷贝”(又称为“位拷贝”)。

析构函数

作用:
对象销毁前,做清理工作。

具体的清理工作,一般和构造函数对应
比如:如果在构造函数中,使用new分配了内存,就需在析构函数中用delete释放。

如果构造函数中没有申请资源(主要是内存资源),
那么很少使用析构函数。

函数名:
~类型
没有返回值,没有参数,最多只能有一个析构函数

访问权限:
一般都使用public

使用方法:
不能主动调用。
对象销毁时,自动调用。
如果不定义,编译器会自动生成一个析构函数(什么也不做)在这里插入代码片

#include <iostream>
#include <Windows.h>
#include <string>
#include <string.h>

using namespace std;

// 定义一个“人类”
class Human {
public:
	Human();
	Human(int age, int salary);
	Human(const Human&);  //不定义拷贝构造函数,编译器会生成“合成的拷贝构造函数”
	Human& operator=(const Human &);
	~Human(); //析构函数
     ......

private:
	string name = "Unknown";
	int age = 28;
	int salary;
	char *addr;
};

Human::Human() {
	name = "无名氏";
	age = 18;
	salary = 30000;

	addr = new char[64];
	strcpy_s(addr, 64, "China");
	cout << "调用默认构造函数-" << this << endl;
}

......

Human::~Human() {
	cout << "调用析构函数-" << this  << endl;  //用于打印测试信息
	delete addr;
}

void test() {
	Human h1;

	{
		Human h2;
	}
	cout << "test()结束" << endl;
}

int main(void) {
	test();

	system("pause");
	return 0;
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56

如果对你有用请点赞,谢谢!

在这里插入图片描述

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/花生_TL007/article/detail/244347
推荐阅读
  

闽ICP备14008679号