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

网络系统管理员获取ip地址seo技术培训价格表

网络系统管理员获取ip地址,seo技术培训价格表,云浮哪有公司做网站的,如何使用二级域名做网站友元 可以通过friend关键字,把一个全局函数、另一个类的成员函数或者另一个类整体,声明为授权类的友元友元拥有访问授权类任何非公有成员的特权友元声明可以出现在授权类的公有、私有或者保护等任何区域且不受访问控制限定符的约束友元不是成员&#xf…

友元

  • 可以通过friend关键字,把一个全局函数、另一个类的成员函数或者另一个类整体,声明为授权类的友元
  • 友元拥有访问授权类任何非公有成员的特权
  • 友元声明可以出现在授权类的公有、私有或者保护等任何区域不受访问控制限定符的约束
  • 友元不是成员,其作用域并不隶属于授权类,也不拥有授权类类型的this指针。

操作符标记和操作符函数

双目操作符表达式

L#R

成员函数形式:L.operator#(R)

  • 左操作数是调用对象,右操作数是参数对象

全局函数形式:operator#(L,R)

  • 左操作数是第一个参数,右操作数是第二个参数

单目操作符表达式

#O/O#

  • 成员函数形式:O.operator#()
  • 全局函数形式:operator#(O)

三目操作符表达式: F#S#T

三目操作符无法重载

经典双目操作符

运算类双目操作符:+、-、*、/等

  • 左右操作数均可以为非常左值、常左值或右值
  • 表达式的结果为右值
// 运算类双目操作符函数
#include <iostream>
using namespace std;class Human{
public:Human(int age = 0, const char* name="匿名"):m_age(age),m_name(name){// [int m_age = age;]// [string m_name(name);]}void getInfo(){cout << "姓名:" << m_name << ", 年龄:" << m_age << endl;}// 成员形式操作符函数
//  Human operator+(const Human& r) const {
//      return Human(this->m_age+r.m_age, (this->m_name+"+"+r.m_name).c_str());
//  }
private:int m_age;string m_name;friend Human operator+(const Human& l,const Human& r); // 友元声明
};
// 全局形式操作符函数
Human operator+(const Human& l, const Human& r){return Human(l.m_age+r.m_age, (l.m_name+"+"+r.m_name).c_str());
}int main(void){Human a(22,"张飞"), b(20,"赵云");  // 非常左值const Human c(25,"关羽"), d(32,"马超"); // 常左值Human res = a + b; // ==> a.operator+(b)  或 operator+(a,b)res.getInfo();res = c + d; // ==> c.operator+(d)  或 operator+(c,d)res.getInfo();res = Human(45,"黄忠") + Human(35,"刘备"); // ==> Human(45,"黄忠").operator+(Human(35,"刘备")) 或 //     operator+(Human(45,"黄忠"),Human(35,"刘备"))res.getInfo();return 0;
}

赋值类双目操作符:=、+=、-=、*=、/=等

  • 右操作数可以为非常左值、常左值或右值,但左操作数必须为非常左值
  • 表达式结果为左操作数本身(而非副本)
// 赋值类双目操作符函数
#include <iostream>
using namespace std;class Human{
public:Human(int age = 0, const char* name="匿名"):m_age(age),m_name(name){// [int m_age = age;]// [string m_name(name);]}void getInfo(){cout << "姓名:" << m_name << ", 年龄:" << m_age << endl;}// 成员形式操作符函数Human& operator+=(const Human& r){this->m_age = this->m_age + r.m_age;this->m_name = this->m_name + "+" + r.m_name;return *this;}
private:int m_age;string m_name;friend Human operator+(const Human& l,const Human& r); // 友元声明
};全局形式操作符函数
//Human& operator+(Human& l, const Human& r){
//       l->m_age = l->m_age + r.m_age;
//       l->m_name = l->m_name + "+" + r.m_name;
//       return *l;
//}int main(void){Human a(22,"张飞"), b(20,"赵云");  // 非常左值const Human c(25,"关羽"), d(32,"马超"); // 常左值((a+=b)+=c)+=Human(45,"黄忠");a.getInfo();return 0;
}

比较类双目操作符:>、<、==、<=、>=等

  • 左右操作数为非常左值、常左值或右值
  • 表达式结果为 bool
// 比较类双目操作符函数
#include <iostream>
using namespace std;class Human{
public:Human(int age = 0, const char* name="匿名"):m_age(age),m_name(name){// [int m_age = age;]// [string m_name(name);]}void getInfo(){cout << "姓名:" << m_name << ", 年龄:" << m_age << endl;}
//    // 成员形式操作符函数
//    bool operator==(/*const Human* this */ const Human& that)const{
//        return this->m_age==that.m_age && this->m_name==that.m_name;
//    }
//    bool operator!=(/*const Human* this */ const Human& that)const{return this->m_age!=that.m_age || this->m_name!=that.m_name;
//        return !(*this==that);//使用operator==
//    }
private:int m_age;string m_name;friend bool operator==(const Human& l, const Human& r); // 友元声明friend bool operator!=(const Human& l, const Human& r); // 友元声明
};
// 全局形式操作符函数
bool operator==(const Human& l, const Human& r){return l.m_age==r.m_age && l.m_name==r.m_name;
}
bool operator!=(const Human& l, const Human& r){
//      return l.m_age!=r.m_age || l.m_name!=r.m_name;return !(l==r);//使用operator==
}int main(void){Human a(22,"张飞"), b(20,"赵云");  // 非常左值const Human c(25,"关羽"), d(32,"马超"); // 常左值cout << (a == b) << endl; //0 ==> a.operator==(b) 或者 ...cout << (a != b) << endl; //1 ==> a.operator!=(b) 或者 ...cout << (c == d) << endl; //0 ==> c.operator==(d) 或者 ...cout << (c != d) << endl; //1 ==> c.operator!=(d) 或者 ...cout << (Human(45,"黄忠") == Human(35,"刘备")) << endl; //0 ==> Human(45,"黄忠").operator==(Human(35,"刘备")) 或者 ...cout << (Human(45,"黄忠") != Human(35,"刘备")) << endl; //1 ==> Human(45,"黄忠").operator!=(Human(35,"刘备")) 或者 ...return 0;
}

经典单目操作符

运算类单目操作符:-、~、!等

  • 操作数为非常左值、常左值或右值
  • 表达式的结果为右值
// 运算类单目操作符函数
#include <iostream>
using namespace std;class Human{
public:Human(int age = 0, const char* name="匿名"):m_age(age),m_name(name){// [int m_age = age;]// [string m_name(name);]}void getInfo(){cout << "姓名:" << m_name << ", 年龄:" << m_age << endl;}// 成员形式操作符函数Human operator-(/* const Human* this */)const{return Human(-this->m_age,("-"+this->m_name).c_str());}
private:int m_age;string m_name;
//    friend Human operator-(const Human& l); // 友元声明
};//Human operator-(const Human& l){
//    return Human(-l.m_age,("-"+l.m_name).c_str());
//}
int main(void){Human a(22,"张飞"), b(20,"赵云");  // 非常左值const Human c(25,"关羽"), d(32,"马超"); // 常左值Human res = -a; // ==> a.operator-() 或  ...res.getInfo();//姓名:-张飞, 年龄:-22res = -c; // ==> c.operator-() 或  ...res.getInfo();//姓名:-关羽, 年龄:-25res = -Human(45,"黄忠"); // ==> Human(45,"黄忠").operator-() 或 ...res.getInfo();//姓名:-黄忠, 年龄:-45return 0;
}

前自增减类单目操作符: 前++、前–

  • 操作数为非常左值
  • 表达式的结果为操作数本身(而非副本)

后自增减类单目操作符: 后+ +、后–

  • 操作数为非常左值
  • 表达式的结果为右值,且为自增减以前的值
// 自增减类单目操作符函数
#include <iostream>
using namespace std;class Human{
public:Human(int age = 0, const char* name="匿名"):m_age(age),m_name(name){// [int m_age = age;]// [string m_name(name);]}void getInfo(){cout << "姓名:" << m_name << ", 年龄:" << m_age << endl;}//成员形式操作符函数
//    //   前++   ++a
//    Human& operator++(/* Human* this */){
//        this->m_age+=1;   // 直接加1
//        this->m_name+="a";   // 直接加
//        return *this;
//    }后++  a++
//    Human operator++(/* Human* this */int){
//        Human old = *this;   // 备份原来的值
//        this->m_age+=1;  // 直接加1
//        this->m_name+="a";   // 直接加
//        return old;  // 返回原来的值
//    }
private:int m_age;string m_name;friend  Human& operator++(Human&  l); // 友元声明friend  Human operator++(Human&  l,int); // 友元声明
};//   前++   ++aHuman& operator++(Human&  l){l.m_age+=1;   // 直接加1l.m_name+="a";   // 直接加return l;}//    后++  a++Human operator++(Human& l,int){Human old = l;   // 备份原来的值l.m_age+=1;  // 直接加1l.m_name+="a";   // 直接加return old;  // 返回原来的值}int main(void){Human a(22,"张飞"), b(20,"赵云");  // 非常左值const Human c(25,"关羽"), d(32,"马超"); // 常左值//姓名:张飞a, 年龄:23(++a).getInfo(); // a.operator++() 或 ...//姓名:赵云, 年龄:20(/*|...|*/b++).getInfo(); // b.operator++(0) 或 ...//姓名:赵云a, 年龄:21b.getInfo();return 0;
}

其他操作符

输出操作符: <<

  • 左操作数为非常左值形式的输出流(ostream)对象,右操作数为左值或右值
  • 表达式的结果为左操作数本身(而非副本)
  • 左操作数的类型为ostream,若以成员函数形式重载该操作符,就应将其定义为ostream类的成员,该类为标准库提供,无法添加新的成员,因此只能以全局函数形式重载该操作符

ostream& operator< < (ostream& os, const RIGHT& right) { ...}

// 输入/输出流操作符函数
#include <iostream>
using namespace std;class Human{
public:Human(int age = 0, const char* name="匿名"):m_age(age),m_name(name){// [int m_age = age;]// [string m_name(name);]}
/*  void getInfo(){cout << "姓名:" << m_name << ", 年龄:" << m_age << endl;}*/// 成员形式操作符函数
private:int m_age;string m_name;friend ostream& operator<<(ostream& os, const Human& that);friend istream& operator>>(istream& is, Human& that);
};
// 全局形式操作符函数
ostream& operator<<(ostream& os, const Human& that){os << "姓名:" << that.m_name << ", 年龄:" << that.m_age;return os;
}//istream& operator>>(istream& is, Human& that){
//    is >> that.m_name >> that.m_age;
//    return is;
//}int main(void){Human a(22,"张飞");  // 非常左值const Human b(20,"赵云");  // 常左值cout << a << endl; // cout.operator<<(a) 或 operator<<(cout,a)cout << b << endl; // cout.operator<<(b) 或 operator<<(cout,b)cout << Human(45,"黄忠") << endl; // cout.operator<<(Human(45,"黄忠")) 或 operator<<(cout,Human(45,"黄忠"))//    cin >> a; // cin.operator>>(a) 或 operator>>(cin,a)cout << a << endl;return 0;
}

输入操作符: >>

  • 左操作数为非常左值形式的输入流(istream)对象,右操作数为非常左值
  • 表达式的结果为左操作数本身(而非副本)
  • 左操作数的类型为istream,若以成员函数形式重载该操作符,就应将其定义为istream类的成员,该类为标准库提供,无法添加新的成员,因此只能以全局函数形式重载该操作符

istream& operator>> (istream& is, RIGHT& right) { ...}

// 输入/输出流操作符函数
#include <iostream>
using namespace std;class Human{
public:Human(int age = 0, const char* name="匿名"):m_age(age),m_name(name){// [int m_age = age;]// [string m_name(name);]}
/*  void getInfo(){cout << "姓名:" << m_name << ", 年龄:" << m_age << endl;}*/// 成员形式操作符函数
private:int m_age;string m_name;friend ostream& operator<<(ostream& os, const Human& that);friend istream& operator>>(istream& is, Human& that);
};
// 全局形式操作符函数
ostream& operator<<(ostream& os, const Human& that){os << "姓名:" << that.m_name << ", 年龄:" << that.m_age;return os;
}istream& operator>>(istream& is, Human& that){is >> that.m_name >> that.m_age;return is;
}int main(void){Human a(22,"张飞");  // 非常左值cin >> a; // cin.operator>>(a) 或 operator>>(cin,a)cout << a << endl;return 0;
}

下标操作符:[]

  • 一般用于在容器类型中以下标方式获取数据元素
  • 非常容器的元素为非常左值,常容器的元素为常左值

类型转换操作符

若源类型是基本类型,目标类型是类类型,则只能通过类型转换构造函数实现自定义类型转换

class 目标类型{目标类型(const 源类型& src){ ... }
}

若源类型是类类型,目标类型是基本类型,则只能通过类型转换操作符函数 实现自定义类型转换

class 源类型{operator 目标类型(void) const { ...}
}

若源类型和目标类型都是类类型 (而非基本类型) ,则既可以通过类型转换构造函数也可以通过类型转换操作符函数实现自定义类型转换,但不要两者同时使用

若源类型和目标类型都是基本类型,则无法实现自定义类型转换,基本类型间的类型转换规则完全由编译器内置

类型转换构造函数和类型转换操作符函数

// 类型转换构造函数和类型转换操作符函数
#include <iostream>
using namespace std;class Integer{
public:Integer(int i):m_i(i){//【int m_i = i;】cout << "Integer类的类型转换构造函数被调用" << endl;}operator int(/* const Integer* this */)const{cout << "Integer类的类型转换操作符函数被调用" << endl;return this->m_i;}
private:int m_i;
};int main(void){int n = 666;// int --> Integer(基本类型-->类类型)Integer ix = n; // 定义匿名Integer对象,利用匿名Integer对象.Integer(n) --> 触发类型转换构造函数// Integer ix = n.operator Integer() --> int类中没有一个operator Integer(走不通)                // Integer --> int(类类型 --> 基本类型)int m = ix; // 定义匿名int对象,利用匿名int对象.int(ix)-->int类中没有一个形参是Integer类型的构造函数(走不通)// int m = ix.operator int() --> 触发类型转换操作符函数return 0;
}
// 类型转换构造函数和类型转换操作符函数
#include <iostream>
using namespace std;class Dog; // 短式声明/前置声明class Cat{
public:Cat(const char* name):m_name(name){// [string m_name(name);]}void talk() {cout << m_name << ": 喵喵~~~" << endl;}operator Dog(/* const Cat* this */)const; // 声明
private:string m_name;friend class Dog; // 友元声明
};class Dog{
public:Dog(const char* name):m_name(name){// [string m_name=name;]}
/*    Dog(const Cat& that):m_name(that.m_name){ // 类型转换构造(定制了Cat-->Dog的转换规则)//【string m_name = that.m_name;】cout << "Dog类的类型转换构造函数被调用" << endl;}*/void talk() {cout << m_name << ": 汪汪~~~" << endl;}
private:string m_name;
};
Cat::operator Dog(/* const Cat* this */)const{ // 定义cout << "Cat类的类型转换操作符函数被调用" << endl;return Dog(this->m_name.c_str());
}int main( void ) {Cat smallwhite("小白"); Dog bigyellow = smallwhite;  // 定义匿名Dog类对象,利用匿名Dog类对象.Dog(smallwhite)-->触发Dog类的类型转换构造函数// Dog bigyellow = smallwhite.operator Dog() --> 触发Cat类的类型转换操作符函数return 0;
}

操作符重载的局限

不是所有的操作符都能重载,以下操作符不能重载

  • 作用域限定操作符(::)
  • 直接成员访问操作符(.)
  • 条件操作符(?:)
  • 字节长度操作符(sizeof)
  • 类型信息操作符(typeid)

无法重载所有操作数均为基本类型的操作符: 如实现 1+1=3

c++的前++和后++

  1. 在C语言中
    前++: 先加1,再使用 ++a
    后++: 先使用,再加1 a++
  2. 在C++语言中,不管是前++还是后++,都是直接加1(内部原理和C语言并不同)
    但是C++希望用户感觉和C一样

c++的前++和后++的区别

  • 表达式方式区别:i++是先取变量i,再将变量i值+1;而++i是先将变量i值+1,再取变量i。在循环遍历容器变量时,这两种方式的结果都是一样的,但是,本质的效率上有很大的区别,下面介绍另一种效率区别。
  • 效率:两种方式iterator遍历的次数是相同的,但在STL中效率不同,前++返回引用,后++返回一个临时对象,因为iterator是类模板,使用 it++这种形式要返回一个无用的临时对象,而it++是函数重载,所以编译器无法对其进行优化,所以每遍历一个元素,你就创建并销毁了一个无用的临时对象。C++的标准库,还有符合标准C++的教材,除了特殊需要和对内置类型外,基本都是使用++it来进行元素遍历的,不管是源代码还是教材中都是如此。

下面是标准库源码:
在这里插入图片描述

http://www.15wanjia.com/news/5244.html

相关文章:

  • 网站开发 价格最新地址
  • 东莞门户网站建设报价表搜索引擎收录
  • 怎么做网站劫持企业文化ppt
  • 胶州网站建设公司百度店面定位怎么申请
  • 网站开发net源码江阴企业网站制作
  • 自己可以做网站服务器seo 专业
  • 扬州鼎盛开发建设有限公司网站100个电商平台
  • 网站做app安全吗深圳全网信息流推广公司
  • 福田网站建设龙岗网站建设龙岗网站建设龙岗网站建设百度关键词怎么刷上去
  • 2022年楼市最新政策优化落实新十条措施
  • 公司动态网站模板下载百度公司注册地址在哪里
  • 做兼职一般去哪个网站好seo论坛
  • 电商网站开发流程代码东莞全网推广
  • 襄阳住房和城乡建设网站win10优化大师好用吗
  • 南宁做网站价格制作网站需要什么
  • 淘宝上做网站不靠谱网站服务器查询
  • 小程序自己做网站seo优化博客
  • 胜芳哪里做网站公司seo
  • 世界上做的最好的前端网站官方网站怎么注册
  • 濮阳做网站多少钱谷歌seo建站
  • 南通给公司做网站的今天疫情最新消息
  • 有专门做网站的公司吗推广公司属于什么公司
  • wordpress 安装包金融网站推广圳seo公司
  • 党建网站怎么做百度推广靠谱吗
  • 织梦移动网站模板郑州网络推广哪家口碑好
  • 重庆蜡像制作优化公司
  • 韦恩图在线制作网站seo快速上排名
  • 公司网站建设工作总结营销推广技巧
  • c mvc 大型网站开发公司怎么建立自己的网站
  • 虾皮网站有的做吗有什么引流客源的软件