当前位置: 首页 > wzjs >正文

金华网站建设开发李守洪

金华网站建设开发,李守洪,广药网站建设试卷,毕业设计2网站建设const修饰的类的对象和函数 const成员函数和const对象1 const成员函数2 调用关系3 const在成员函数中的位置4 取地址&及const取地址操作符重载 const成员函数和const对象 1 const成员函数 将const修饰的“成员函数”称之为const成员函数,const修饰类成员函数&…

const修饰的类的对象和函数

  • const成员函数和const对象
    • 1 const成员函数
    • 2 调用关系
    • 3 const在成员函数中的位置
    • 4 取地址&及const取地址操作符重载

const成员函数和const对象

1 const成员函数

const修饰的“成员函数”称之为const成员函数,const修饰类成员函数,实际修饰该成员函数隐含的this指针,表明在该成员函数中不能对类的任何成员进行修改
请添加图片描述
例如:

#include<iostream>
class Date {
public:Date(int year, int month, int day) {_year = year;_month = month;_day = day;}//编译器认为两个Print构成函数重载void Print() {using std::cout;using std::endl;cout << "Print()" << endl;cout << "year:" << _year << endl;cout << "month:" << _month << endl;cout << "day:" << _day << endl << endl;}void Print() const {using std::cout;using std::endl;cout << "Print()const" << endl;cout << "year:" << _year << endl;cout << "month:" << _month << endl;cout << "day:" << _day << endl << endl;}
private:int _year; // 年int _month; // 月int _day; // 日
};
int main() {Date d1(2022, 1, 13);d1.Print();const Date d2(2022, 1, 13);//编译器认为d2.Print(&d2),&d2的类型是const Date*,//会为d2匹配void Print() constd2.Print();return 0;
}

编译器的原则:永远是最匹配的,没有就找最合适的。权限可以缩小,但不可以放大。所以d1调用的是Print(),而d2调用的是Print() const

如果只有Print() const,则d1调用的是Print() const。例如:

#include<iostream>class Date {
public:Date(int year, int month, int day) {_year = year;_month = month;_day = day;}void Print() const {using std::cout;using std::endl;cout << "Print()const" << endl;cout << "year:" << _year << endl;cout << "month:" << _month << endl;cout << "day:" << _day << endl << endl;}
private:int _year; // 年int _month; // 月int _day; // 日
};int main() {Date d1(2022, 1, 13);d1.Print();return 0;
}

2 调用关系

const对象和const成员函数,它们与非const的对象和成员函数之间的关系:

  1. const对象不可以调用非const成员函数。权限放大。

因为非const成员函数可通过this指针间接修改对象,所以const对象不能将自身具有常属性的地址上传给this指针,防止权限放大。

参考样例:

#include<iostream>
class A {
public:void f1() {using std::cout;cout << "void f1()\n";}void f2() const {using std::cout;cout << "void f2()\n";}
};int main() {const A a;//a.f1();//不允许。a.f2();//允许,权限平移return 0;
}
  1. const对象可以调用const成员函数。权限缩小。
#include<iostream>
class A {
public:void f1() {using std::cout;cout << "void f1()\n";}void f2() const {using std::cout;cout << "void f2()\n";}
};int main() {A a;a.f2();//允许return 0;
}
  1. const成员函数内不可以调用其它的非const成员函数。
    因为const成员函数的this具有常属性,将this的值上传给非const成员函数,因为非const的成员函数不具有常属性的this,所以权限放大。
#include<iostream>
class A {
public:void f1() {using std::cout;cout << "void f1()\n";}void f2() const {using std::cout;cout << "void f2()\n";//f1();//不允许,权限放大}
};

在存在大量代码复用的类中需要特别注意。

  1. const成员函数内可以调用其它的const成员函数。权限缩小。
#include<iostream>
class A {
public:void f1() {using std::cout;cout << "void f1()\n";f2();//可以,权限缩小。}void f2() const {using std::cout;cout << "void f2()\n";}
};

3 const在成员函数中的位置

这是一个数组类:

#include<iostream>
#include<cstdlib>
class SeqList {
public:~SeqList() {free(a);}int& operator[](int i) const {//a向堆区申请内存,出了这里的作用域数据还在,可以传引用返回return a[i];}
private://c++11允许给内置类型成员初始值,甚至是调用公共库函数//但如果函数执行出错无法反馈int* a = (int*)malloc(sizeof(int) * 10);size_t size = 0;size_t capacity = 10;
};void print(const SeqList& a) {using std::cout;for (int i = 0; i < 10; i++) {cout << a[i] << ' ';a[i]++;//const只限制a本身的内容不可改变,}cout << "\n";
}int main() {SeqList a;using std::cout;for (int i = 0; i < 10; i++)a[i] = i;//修改堆区的数据print(a);print(a);return 0;
}

函数int& operator[](int i) const{}虽然对this指针本身用const修饰,但是函数返回值是堆区某个位置的引用,所以[]并没有对堆区的数据进行限制。

数组类需要通过[]进行修改和访问数据,因此在部分场合我们想通过[]修改数据,在另一场合又希望这个数据无法被修改。

所以需要提供两个[]的重载,一个只读,一个可读可写,此时编译器会匹配最合适的[]。只读的[]重载一般需要用两个const进行限制。

#include<iostream>
#include<cstdlib>
class SeqList {
public:~SeqList() {free(a);}int& operator[](int i) {//对象可读可写return a[i];}const int& operator[](int i) const{//对象只读return a[i];}
private:int* a = (int*)malloc(sizeof(int) * 10);size_t size = 0;size_t capacity = 10;
};void print(const SeqList& a) {using std::cout;for (int i = 0; i < 10; i++) {cout << a[i] << ' ';//a[i]++;//编译器为const SeqList匹配形参为const SeqList的operator[],所以不可修改}cout << "\n";
}int main() {SeqList a;using std::cout;for (int i = 0; i < 10; i++)a[i] = i;//修改堆区的数据print(a);return 0;
}

还是需求问题,程序员想要用户不修改什么数据,就加const对类的成员函数进行限制。

4 取地址&及const取地址操作符重载

默认成员函数的取地址&重载一般不用重新定义 ,编译器默认会生成。其中用到了const修饰this时构成的重载。

class Date {
public:Date* operator&() {return this;}const Date* operator&() const {//参考上文的数组类return this;}
private:int _year; // 年int _month; // 月int _day; // 日
};

这两个运算符一般不需要重载,使用编译器生成的默认取地址的重载即可,只有特殊情况,才需要重载,比如不想被别人取到对象的有效地址,于是给个假地址返回。

#ifndef _CRT_SECURE_NO_WARNINGS
#define _CRT_SECURE_NO_WARNINGS 1
#endif#include<iostream>
using std::cout;
class Date {
public:Date(int year=1900,int month=0,int day=0){_year = year;_month = month;_day = day;}Date* operator&() {return nullptr;}const Date* operator&() const {return nullptr;}
private:int _year; // 年int _month; // 月int _day; // 日
};int main() {Date a;const Date b;cout << (&a) << '\n' << (&b);return 0;
}
http://www.dtcms.com/wzjs/143410.html

相关文章:

  • 山西武汉网站建设免费的网络营销方式
  • 上海网页制作找哪家免费seo刷排名
  • 集团网站建设案例西安百度推广怎么做
  • 义乌网站建设联系方式小说网站排名
  • 网站虚拟主机有什么用百度做广告多少钱
  • 化妆品网站程序免费网站免费
  • 环球设计官网网站上海网站制作公司
  • ps做网站的优点关键词在线试听免费
  • 网站访问速度优化怎么让关键词快速上首页
  • 黄金网站网址免费前端seo是什么
  • 江阴做公司网站有哪些58精准推广点击器
  • 在国外社交网站做产品推广网络销售网站
  • 网站建站啥意思河南郑州最新消息今天
  • 做网站用ui好还是ps必应搜索引擎网址
  • 自建网站做外贸谷歌推广整站优化 mail
  • 怎么制作属于自己的网站百度平台电话
  • 深圳市公司网站建设百度一下手机版首页
  • 广告设计公司网站源码注册一个公司网站需要多少钱
  • 做壁纸网站网站搜索引擎优化主要方法
  • 昆明百度推广开户广州seo站内优化
  • 长沙百度做网站多少钱谷歌广告投放步骤
  • 百度快照入口国外seo大神
  • 自己怎样做优惠券网站代发关键词排名包收录
  • 百度餐饮网站建设加速游戏流畅的软件
  • 服装网站制作百度电话人工服务
  • 广州美容网站建设百度快照入口
  • 竹子建站教程谷歌google官网下载
  • 哈尔滨市建筑企业管理站seo岗位职责
  • 成都网站建设快速服务百度营销推广登录平台
  • 搜狐一开始把网站当做什么来做我在百度下的订单如何查询