1,类和对象

定义一个类,本质上是定义一个数据类型的蓝图。这实际上并没有定义任何数据,但它定义了类的名称意味着什么,也就是说,它定义了类的对象包括了什么,以及可以在这个对象上执行哪些操作。

类定义格式如下:

class Box
{
public: //在类对象作用域内,公共成员在类的外部是可访问的。
double length; // 盒子的长度
double breadth; // 盒子的宽度
double height; // 盒子的高度
};

声明类对象:

Box Box1; // 声明 Box1,类型为 Box
Box Box2; // 声明 Box2,类型为 Box

访问数据成员:

#include <iostream>
using namespace std;
class Box
{
public:
double length; // 长度
double breadth; // 宽度
double height; // 高度
};
int main( )
{
Box Box1; // 声明 Box1,类型为 Box
Box Box2; // 声明 Box2,类型为 Box
double volume = 0.0; // 用于存储体积
// box 1 详述
Box1.height = 5.0; //为实例的某个属性赋值,采用点号
Box1.length = 6.0;
Box1.breadth = 7.0;
// box 2 详述
Box2.height = 10.0;
Box2.length = 12.0;
Box2.breadth = 13.0;
// box 1 的体积
volume = Box1.height * Box1.length * Box1.breadth; //访问某个实例的类中的某个属性,同样用点号,当然还要看共有还是私有
cout << "Box1 的体积:" << volume <<endl;
// box 2 的体积
volume = Box2.height * Box2.length * Box2.breadth;
cout << "Box2 的体积:" << volume <<endl;
return ;
}

定义类成员函数:

内部定义成员函数:

class Box
{
public:
double length; // 长度
double breadth; // 宽度
double height; // 高度
double getVolume(void)
{
return length * breadth * height;
}
};

外部定义成员函数,必须要使用范围解析运算符:

double Box::getVolume(void)    //类名::函数名
{
return length * breadth * height;
}

在外部定义内联的成员函数,那么你需要一个关键字:inline

class A
{
public:void Foo(int x, int y) { } // 自动地成为内联函数
} // 头文件
class A
{
public:
void Foo(int x, int y);
}
// 定义文件,这个也是内联函数,注意inline必须与函数定义放在一块
inline void A::Foo(int x, int y){}

调用成员函数:

#include <iostream>
using namespace std;
class Box
{
public:
double length; // 长度
double breadth; // 宽度
double height; // 高度
// 成员函数声明
double getVolume(void);
void setLength( double len );
void setBreadth( double bre );
void setHeight( double hei );
};
// 成员函数定义
double Box::getVolume(void)
{
return length * breadth * height;
}
void Box::setLength( double len )
{
length = len;
}
void Box::setBreadth( double bre )
{
breadth = bre;
}
void Box::setHeight( double hei )
{
height = hei;
}
// 程序的主函数
int main( )
{
Box Box1; // 声明 Box1,类型为 Box
Box Box2; // 声明 Box2,类型为 Box
double volume = 0.0; // 用于存储体积
// box 1 详述
Box1.setLength(6.0);
Box1.setBreadth(7.0);
Box1.setHeight(5.0);
// box 2 详述
Box2.setLength(12.0);
Box2.setBreadth(13.0);
Box2.setHeight(10.0);
// box 1 的体积
volume = Box1.getVolume();
cout << "Box1 的体积:" << volume <<endl;
// box 2 的体积
volume = Box2.getVolume();
cout << "Box2 的体积:" << volume <<endl;
return ;
}

2,类访问修饰符

class Base {
public:
// 公有成员,
protected:
// 受保护成员
private:
// 私有成员
};

public:

#include <iostream>
using namespace std;
class Line
{
public:
double length;
void setLength( double len ); //声明成员函数
double getLength( void );
}; // 成员函数定义
double Line::getLength(void) //外部实现成员函数
{
return length ;
}
void Line::setLength( double len )
{
length = len;
}
// 程序的主函数
int main( )
{
Line line;
// 设置长度
line.setLength(6.0); //public支持使用类自带的成员函数修改属性值
cout << "Length of line : " << line.getLength() <<endl;
//public同样支持在外部直接赋值类的属性
line.length = 10.0; // OK: 因为 length 是公有的
cout << "Length of line : " << line.length <<endl;
return ;
}

private:

#include <iostream>

using namespace std;

class Box
{
public:
double length;
void setWidth( double wid );
double getWidth( void ); private:
double width;
}; // 成员函数定义,成员函数属于公有,但是操作的是私有的属性
double Box::getWidth(void)
{
return width ;
} void Box::setWidth( double wid )
{
width = wid;
} // 程序的主函数
int main( )
{
Box box; // 对于私有变量width来说,不使用成员函数设置宽度是不行的
// box.width = 10.0; // Error: 因为 width 是私有的
box.setWidth(10.0); // 只能使用成员函数设置宽度,也就是说私有的属性只有通过它自己定义的方法才能改变,外部不能改变它。
cout << "Width of box : " << box.getWidth() <<endl;
return ;
}

protected:只有自己或者子类的成员函数才能访问

#include <iostream>
using namespace std; class Box
{
protected:
double width;
}; class SmallBox:Box // SmallBox 是派生类
{
public:
void setSmallWidth( double wid );
double getSmallWidth( void );
}; // 子类的成员函数
double SmallBox::getSmallWidth(void)
{
return width ;
}
void SmallBox::setSmallWidth( double wid )
{
width = wid;
}
// 程序的主函数
int main( )
{
SmallBox box;
// 使用成员函数设置宽度
box.setSmallWidth(5.0);
cout << "Width of box : "<< box.getSmallWidth() << endl;
return ;
}
  • 1.private 成员只能被本类成员(类内)和友元访问,不能被派生类访问;

  • 2.protected 成员可以被派生类访问。

3,构造函数和析构函数

构造函数:

c++中构造函数的名称与类的名称是完全相同的,并且不会返回任何类型,也不会返回 void。构造函数可用于为某些成员变量设置初始值。

#include <iostream>

using namespace std;

class Line
{
public:
void setLength( double len );
double getLength( void );
Line(); // 这是构造函数,构造函数里带参数也是可以的,就和普通函数带参数一样 private:
double length;
}; // 成员函数定义,包括构造函数
Line::Line(void) //定义构造函数,在class里直接定义也行。
{
cout << "Object is being created" << endl;
} void Line::setLength( double len )
{
length = len;
} double Line::getLength( void )
{
return length;
}
// 程序的主函数
int main( )
{
Line line; //一旦实例化就会跑构造函数 // 设置长度
line.setLength(6.0);
cout << "Length of line : " << line.getLength() <<endl; return ;
}

构造函数可以用特殊的格式来初始化类内的某些属性:

Line::Line( double len): length(len)
{
cout << "Object is being created, length = " << len << endl;
} //和下面的代码效果一样:
Line::Line( double len)
{
cout << "Object is being created, length = " << len << endl;
length = len;
}
//假设有一个类 C,具有多个字段 X、Y、Z 等需要进行初始化,同时初始化多个属性
C::C( double a, double b, double c): X(a), Y(b), Z(c)
{
....
}

析构函数:

类的析构函数是类的一种特殊的成员函数,它会在每次删除所创建的对象时执行。

析构函数的名称与类的名称是完全相同的,只是在前面加了个波浪号(~)作为前缀,它不会返回任何值,也不能带有任何参数。析构函数有助于在跳出程序(比如关闭文件、释放内存等)前释放资源。

#include <iostream>

using namespace std;

class Line
{
public:
void setLength( double len );
double getLength( void );
Line(); // 这是构造函数声明
~Line(); // 这是析构函数声明 private:
double length;
}; // 成员函数定义,包括构造函数
Line::Line(void)
{
cout << "Object is being created" << endl;
}
Line::~Line(void)
{
cout << "Object is being deleted" << endl;
} void Line::setLength( double len )
{
length = len;
} double Line::getLength( void )
{
return length;
}
// 程序的主函数
int main( )
{
Line line; // 设置长度
line.setLength(6.0);
cout << "Length of line : " << line.getLength() <<endl;
//line.~Line(); 这样也是可以滴,手动析构以后系统还是会再检查一遍
return ;
}

4,拷贝构造函数

其实就是拷贝一个对象的实例,尽管听起来简单,但是拷贝的时候一定要注意指针或者引用等,小心语法错误

#include <iostream>
//拷贝构造函数
using namespace std; class Line
{
public:
int getLength( void );
Line( int len ); // 简单的构造函数
Line( const Line &obj); // 拷贝构造函数
~Line(); // 析构函数 private:
int *ptr;
}; // 在对象的外部定义函数内容,成员函数定义,包括构造函数
Line::Line(int len)
{
cout << "调用构造函数" << endl;
// 为指针分配内存
ptr = new int; //新建一个int数据类型
*ptr = len;
} Line::Line(const Line &obj) //指明了要拷贝的是line这个对象,因为这个对象已经被构造过了
{
cout << "调用拷贝构造函数并为指针 ptr 分配内存" << endl;
ptr = new int;
*ptr = *obj.ptr; //为啥是指针呢,因为ptr是个指针,相当于*(obj.ptr)
} Line::~Line(void)
{
cout << "释放内存" << endl;
delete ptr;
}
int Line::getLength( void )
{
return *ptr;
} void display(Line obj)
{
cout << "line 大小 : " << obj.getLength() <<endl;
} // 程序的主函数
int main( )
{
Line line(); display(line); return ;
}

返回:

调用构造函数
调用拷贝构造函数并为指针 ptr 分配内存
line 大小 : 10
释放内存
释放内存
//函数声明等一致的情况下,拷贝构造函数也可以是直接复制实例
//接上一个函数
// 程序的主函数
int main( )
{
Line line1(); Line line2 = line1; // 这里也调用了拷贝构造函数 display(line1);
display(line2); return ;
}

返回是这样的:

调用构造函数
调用拷贝构造函数并为指针 ptr 分配内存
调用拷贝构造函数并为指针 ptr 分配内存
line 大小 : 10
释放内存
调用拷贝构造函数并为指针 ptr 分配内存
line 大小 : 10
释放内存
释放内存
释放内存

5,友元函数

友元函数不是类的成员函数,而是定义在类的外部,但是又能访问私有和保护成员的函数,友元函数用friend指定。

class Box
{
double width;
public:
double length;
friend void printWidth( Box box );
void setWidth( double wid );
};
#include <iostream>

using namespace std;

class Box
{
double width;
public:
friend void printWidth( Box box ); //注意此处的友元函数传递的参数是类实例哦。
void setWidth( double wid );
}; // 成员函数定义
void Box::setWidth( double wid )
{
width = wid;
} // 请注意:printWidth() 不是任何类的成员函数
void printWidth( Box box )
{
/* 因为 printWidth() 是 Box 的友元,它可以直接访问该类的任何成员 */
cout << "Width of box : " << box.width <<endl;
} // 程序的主函数
int main( )
{
Box box; // 使用成员函数设置宽度
box.setWidth(10.0); // 使用友元函数输出宽度
printWidth( box ); return ;
}

最新文章

  1. C# Azure 存储-分布式缓存Redis工具类 RedisHelper
  2. 【requireJS源码学习03】细究requireJS的加载流程
  3. localstorage sessionstorage cookie 备忘
  4. 【源码分享】WPF漂亮界面框架实现原理分析及源码分享
  5. Unity Shaders and Effets Cookbook
  6. Nginx 反向代理学习(一)
  7. QSS总结以及最近做的Qt项目
  8. TestNG之执行顺序
  9. Redis作为多个Windows服务运行配置方法
  10. showdialog窗体不在任务栏显示的问题处理
  11. Acdream1217 Cracking&#39; RSA(高斯消元)
  12. [ASP.NET 技术点滴] Jquery 前端验证
  13. TreeView绑定无限层级关系类
  14. 『安全工具』Nessus多功能扫描器
  15. Wincc flexable的局势视图的组态
  16. 基于Vue的页面切换左右滑动效果
  17. Linux 6.4 设置yum 为centOS源
  18. 冲刺Two之站立会议10
  19. Linux基础命令---ifdown、ifup
  20. 使用ActionFilterAttribute实现MVC后台授权

热门文章

  1. 1级搭建类109-Oracle 12cR2 SI FS(Windows Server 2019)公开
  2. 区间dp(模板+例题)
  3. java学习笔记之IO编程—内存流、管道流、随机流
  4. vue router的其他属性、 值的传递 、 懒加载
  5. 自定义结构体 Map
  6. Linux系统编程、网络编程-文件I/O
  7. bat文件一键运行python自动化脚本
  8. AE 打开Shp文件
  9. js中事件代理(委托)
  10. centos添加用户并赋予 root管理员权限