侯捷C++高级编程(下)

对于1个类要么像指针要么像函数

主题1:转换函数

转换函数

/** 1. 转换函数没有返回类型* 2. 转换函数一般需要加上const*/
class Fraction
{
public:Fraction(int num,int den=1):m(num),n(den){cout<<"Fraction(int num,int den=1): m/n = "<< m/n<<endl;}operator double()const{cout<<"调用转换函数double():"<<(double)( m/n )<<endl;return (double)( m/n );}
private:int m;int n;
};
int main(int argc, char** argv)
{Fraction f(8,2);double d = 5 + f;/** 首先 4* */
//    Fraction d = f + 4;cout<<d<<endl;/** 输出结果:* Fraction(int num,int den=1):m/n = 4* 调用转换函数double()* 8* 分析:f(8,2): 首先调用构造函数* 然后;5 + f 中的f调用转换函数转换为double*/
}

non-explict-one-argument ctor

class Fraction
{
public:Fraction(int num,int den=1):m(num),n(den){cout<<"Fraction(int num,int den=1): m/n = "<< m/n<<endl;}Fraction operator+(const Fraction &f){cout<<"调用operator+()函数"<<endl;return Fraction(m+f.m,n+f.n);}
private:int m;int n;
};
int main(int argc, char** argv)
{Fraction f(8,2);Fraction d1 = f+5;// === f.operator+(5);/** 首先f+5中的5调用构造函数Fraction(int num,int den=1)* 然后调用operator+()函数*/
}

注意:提供默认值的构造函数可以将一种类中的为提供默认值的属性类型转换为该类类型---即将一种类型转化为本类类型 operaor double() --- 则是将本类型转化为double类型,两者转换方向刚好相反;但是我们一般所说的转换函数是后一种类型;
ambiguous error

class Fraction
{
public:Fraction(int num,int den=1):m(num),n(den){cout<<"Fraction(int num,int den=1): m/n = "<< m/n<<endl;}operator double()const{cout<<"调用转换函数double():"<<(double)( m/n )<<endl;return (double)( m/n );}Fraction operator+(const Fraction &f){cout<<"调用operator+()函数"<<endl;return Fraction(m+f.m,n+f.n);}
private:int m;int n;
};
Fraction operator+(int a,const Fraction &b)   
{
//解决5+f的问题
}
int main(int argc, char** argv)
{Fraction f(8,2);Fraction d1 = f+5;// Use of overloaded operator '+' is ambiguous (with operand types 'Fraction' and 'int')Fraction d1 = 5+f;
}

explict的使用:一般用在构造函数前面,表示此构造函数只能用于构造不能用于其他目的
explicit Fraction(int num,int den=1):m(num),n(den)
Fraction d1 = f+5;// error
但是仍然会出现:error: conversion from ‘double’ to non-scalar type ‘Fraction’ requested
解释:
f+5中首先由于在构造函数前面加上了explict所以不会ambiguous,f首先转换为double记为a,然后执行a+5后产生一个double记为c,但是c不能转化为Fraction,因为explict

:
Fraction operator+(int a,const Fraction &b)
{
//解决5+f的问题
}
是否可以成员函数实现,是否是下面的

class Fraction
{friend  Fraction operator+(int a,const Fraction &f){;} //注意这不是Fraction的成员函数,这个是全局函数。只不过在Fraction中声明为友元函数之后直接实现了。
}
//这里的5+f的实现利用friend成员函数没有this指针的特点

关于友元函数

  1. 友元函数没有this指针
  2. 因为友元函数是类外的函数,所以它的声明可以放在类的私有段或公有段且没有区别。
  3. 友元函数是不能被继承的,就像父亲的朋友未必是儿子的朋友
    友元函数的分类:
    根据这个函数的来源不同,可以分为三种方法:
    普通函数友元函数:
    目的:使普通函数能够访问类的友元
    语法:
    声明: friend + 普通函数声明
    实现位置:可以在类外或类中
    实现代码:与普通函数相同
    调用:类似普通函数,直接调用
class INTEGER{friend void Print(const INTEGER& obj);//声明友元函数};void Print(const INTEGER& obj){//函数体}void main(){INTEGER obj;Print(obj);//直接调用}

类Y的所有成员函数都为类X友元函数—友元类
目的:使用单个声明使Y类的所有函数成为类X的友元,它提供一种类之间合作的一种方式,使类Y的对象可以具有类X和类Y的功能。
语法:
声明位置:公有私有均可,常写为私有(把类看成一个变量)
声明: friend + 类名(不是对象哦)

class girl;class boy{public:void disp(girl &);};void boy::disp(girl &x) //函数disp()为类boy的成员函数,也是类girl的友元函数{cout<<"girl's name is:"<<x.name<<",age:"<<x.age<<endl;//借助友元,在boy的成员函数disp中,借助girl的对象,直接访问girl的私有变量}class girl{privatechar *name;int age;friend boy; //声明类boy是类girl的友元};

类Y的一个成员函数为类X的友元函数
目的:使类Y的一个成员函数成为类X的友元,具体而言:在类Y的这个成员函数中,借助参数X,可以直接以X的私有变量
语法:
声明位置:声明在公有中 (本身为函数)
声明:friend + 成员函数的声明
调用:先定义Y的对象y—使用y调用自己的成员函数—自己的成员函数中使用了友元机制
代码:
实现代码和2.4.2.3中的实现及其相似只是设置友元的时候变为friend void boy::disp(girl &);

主题2:pointer-like classes 智能指针

pointer-like classes 智能指针

template<class T>
class shared_ptr
{
public:T& operator*()const{return *px;}T* operator->()const{return px;}shared_ptr(T* p):px(p){};
private:T* px;long *pn;
};
struct FOO
{void method();
};
int main(int argc, char** argv)
{shared_ptr<FOO> sp(new FOO);FOO f(*sp);sp->method(); // == px->method(0)  ->会作用之后会继续出现->return 0;
}

pointer-like classes 迭代器

template <class T, class Refclass Ptr>
struct __list_iterator { //这是一个链表typedef __list_iterator<T, Ref, Ptr> self;typedef Ptr pointer;typedef Ref pointer;typedef __list_node<T>* link_type;link_type node;bool operator==(const self& x) const { return node == x.node; }bool operator==(const self& x) const { return node != x.node; }reference operator*() const { return (*node).data; }pointer operator-> const { return &(operator*())}self& operator++() { node = (link_type)((*node).next); return *this }self& operator++(int) { self tmp = *this; ++*this; return tmp; }self& operator--() { node = (link_type)((*node).prep); return *this }self& operator--(int) { self tmp = *this; --*this; return tmp; }
};

主题3: function-like classes 仿函数

template<class T>
struct identity
{const T& operator()(const T& x)const{return x;}
};

主题4:namespace

#include <iostream>
#include<list>namespace jj01
{
//开始设计template<typename T>using Lst=list<T,allocator<T>>;void test()
}
int main()
{jj01::test()
}

主题6: 模板

class template,类模板

Function template 函数模板

member template 成员模板

template <class T1,class T2>
struct pair  {typedef T1 first_type;typedef T2 second_type;T1 first;T2 second;pair() :first(T1()),second(T2())  { }pair(const T1& a,const T2& b) :first(a), second(b)  {  }template <class U1,class U2>  //这里,模板套模板,成员模板pair(const pair<U1,U2>& p): first(p.first),second(p.second)  {  }
};class Base1{};
class Derived1:public Base1{};pair<Derived1,Derived2> p;
pair<Base1,Base2> p2(p);
等价于pair<Base1,Base2> pw(pair<Derived1,Derived2>());  //用子类初始化父类

specialization 模板特化

template <class Key>
struct hash  {  };
--------------------上面的是泛化-------
template<>  //Key被锁定了
struct hash<char>  {size_t operator() (char x)  const  { return x;  }
}template<>  //Key被锁定了
strcut hash<int>  {size_t operator() (int x)  const  {return x;  }template<>  //Key被锁定了
struct hash<long>  {size_t operator() (long x)  const  {  return x;  }
};

parti specialization 模板偏特化

个数的偏

在这里插入图片描述
因为上面的模板有两个参数,但是目前我只需一个值绑定一个

范围的偏

在这里插入图片描述

template template parameter 模板模板参数

在这里插入图片描述
XCIS<string,list> mylist1; 第一个确定为string,但是第二个不确定传入模板;但是是错误的;虽然 Container变为 list但是一些容器的模板有一个以上的参数,我们一般只是定义了一个参数,上面不通过是由于语法问题参数不足导致
在这里插入图片描述
打岔:由于unique和weak的一些特性导致错误。
在这里插入图片描述
上面不是模板模板参数,由于list已经指定模板了

variadic templates 数量不定的模板参数

void print()
{cout<<"------"<<endl;}template<typename T,typename ... Types>
void print(const T& firstArg,const Types&...args)
{//  参数:一个 + 一包cout<<firstArg<<endl;cout<<sizeof...(args)<<ends;print(args...);
}
int main()
{print(7.5,"hello",42);/*
7.5
2 hello
1 42
0 ------这个模板参数可变的函数:参数可以分为一个+一包,这个函数是递归调用首先是:print(first=7.5,args=("hello",42)) 然后输出firstArg,然后size...(args)==2然后是:print(first="hello",args=(42)),打印出“hello”然后size...(args)==1最后是:print(first=42,args=),打印42,然后size...(args)===1调用无参数的print()*/return 0;
}

C++标准库

在这里插入图片描述

for(int i:{1,2,3,4})cout<<i;
//{1,2,3}是个容器

主题7:reference 引用

  1. object和其reference的大小相同,地址也相同(全都是假象)
  2. reference通常不用于声明变量,一般用于函数的参数类型和函数返回类型

主题8:对象模型

继承关系下的构造和析构

  1. 构造应该由内而外
  2. 析构应该由外二内

组合关系下的构造和析构

  1. 构造应该由内而外
  2. 析构应该由外二内

继承+组合 关系下的构造和析构

对象模型:vptr(虚指针)和vtbl(虚表)

  1. 只要一个类含有虚函数,那么该类一定含有虚指针。多一个虚函数就多一个虚指针
  2. 父类有虚函数子类一定有虚函数
    在这里插入图片描述
    函数:
  3. 静态绑定
  4. 动态绑定
    动态绑定的条件
  • 虚函数
  • 向上转型

this

主题9:const

  1. const只能放在成员函数后面

主题10:new delete

重载 operator new,operator new[],operator delete,operator delete[]

在这里插入图片描述

在这里插入图片描述
https://zhuanlan.zhihu.com/p/526244459

placement new

https://blog.csdn.net/qq_41453285/article/details/103547699

关于这里没有看明白(最后几节)

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/82814.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

WebGL: 几个入门小例子

本文通过WebGL例子&#xff0c;来帮助WebGL入门学习。 一、概述 WebGL (Web Graphics Library)是一组基于Open ES、在Web内渲染3D图形的Javascript APIs。 Ref. from Khronos Group: WebGL WebGL™ is a cross-platform, royalty-free open web standard for a low-level 3D …

web前端之JS

文章目录 介绍一、JS引入到文件1.1 嵌入到HTML文件中1.2 引入本地独立JS文件1.3 引入网络来源文件 二、JS的注释三、JS输出方式四、JS数据类型4.1 判断数据类型 typeof4.2 charAt返回指定位置的字符4.3 concat连接两个字符串4.4 substring从原字符串提取字符串并返回4.4 substr…

netty面试题2

1、一次完整的HTTP请求的所经历的步骤 1、首先进行DNS域名解析&#xff08;本地浏览器缓存、操作系统缓存或者DNS服务器&#xff09;&#xff0c;首先会搜索浏览器自身的DNS缓存&#xff08;缓存时间比较短&#xff0c;大概只有1分钟&#xff0c;且只能容纳1000条缓存&#xff…

Python爬虫的解析(学习于b站尚硅谷)

目录 一、xpath  1.xpath插件的安装  2. xpath的基本使用  &#xff08;1&#xff09;xpath的使用方法与基本语法&#xff08;路径查询、谓词查询、内容查询&#xff08;使用text查看标签内容&#xff09;、属性查询、模糊查询、逻辑运算&#xff09;  &#xff08;2&a…

TCP三次握手、四次握手过程,以及原因分析

TCP的三次握手和四次挥手实质就是TCP通信的连接和断开。 三次握手&#xff1a;为了对每次发送的数据量进行跟踪与协商&#xff0c;确保数据段的发送和接收同步&#xff0c;根据所接收到的数据量而确认数据发送、接收完毕后何时撤消联系&#xff0c;并建立虚连接。 四次挥手&…

基于 Emscripten + WebAssembly 实现浏览器操作 Excel

一、为什么要造这个轮子 【C】使用WebAssembly在浏览器端操作Excel_wasm文件用什么打开_你的薄荷醇的博客-CSDN博客使用WebAssembly在浏览器端操作Excel_wasm文件用什么打开https://blog.csdn.net/weixin_44305576/article/details/125545900?ops_request_misc%257B%2522requ…

msvcp120.dll丢失的解决方法,哪种解决方法更实用

msvcp120.dll是Microsoft Visual C 2013库中的一个动态链接库文件。它包含了在使用Visual C 2013编译的应用程序中所需的函数和资源。这个文件通常用于在Windows操作系统上运行使用Visual C 2013编写的软件。如果缺少或损坏了msvcp120.dll文件&#xff0c;可能会导致相关软件无…

P1194 买礼物(最小生成树)(内附封面)

买礼物 题目描述 又到了一年一度的明明生日了&#xff0c;明明想要买 B B B 样东西&#xff0c;巧的是&#xff0c;这 B B B 样东西价格都是 A A A 元。 但是&#xff0c;商店老板说最近有促销活动&#xff0c;也就是&#xff1a; 如果你买了第 I I I 样东西&#xff0…

Linux基础与拓展

文章目录 虚拟机网络连接方式VIMvi和vim常用的三种模式各种模式的相互切换快捷键 用户管理权限 基本介绍&#xff1a;添加用户指定/修改密码删除用户切换用户用户组 路径命令学习mkdir命令介绍语法注意 touch 创建文件介绍语法 cat 查看文件内容介绍语法 more 查看文件内容介绍…

vue动态生成行

vue代码 <el-table :data"form.lineInfos" :bordertrue style"width: 99.99%;"> <el-table-column type"index" label"序号" width"50"></el-table-column> <el-table-column prop"unitPrice&qu…

Swagger技术-自动生成测试接口

简介 前端资源和后端资源分开&#xff0c;前端通过nginx运行&#xff0c;后端通过tomcat运行 前端技术框架&#xff1a; Swagger 作用&#xff1a;生成各种样式的接口文档&#xff0c;以及在线接口调试页面等 kinfe4j是基于mvc框架继承swagger生成api文档的增强解决方案 …

【云原生】Docker-compose中所有模块学习

compose模块 模板文件是使用 Compose 的核心&#xff0c;涉及到的指令关键字也比较多。但大家不用担心&#xff0c;这里面大部分指令跟 docker run 相关参数的含义都是类似的。 默认的模板文件名称为 docker-compose.yml&#xff0c;格式为 YAML 格式。 version: "3&quo…

Nios初体验之——Hello world!

文章目录 前言一、系统设计1、系统模块框图2、系统涉及到的模块1、时钟2、nios2_qsys3、片内存储&#xff08;onchip_rom、onchip_ram&#xff09;4、串行通信&#xff08;jtag_uart&#xff09;5、System ID&#xff08;sysid_qsys&#xff09; 二、硬件设计1、创建Qsys2、重命…

网络安全 Day27-运维安全项目-堡垒机部署

运维安全项目-堡垒机部署 1. 运维安全项目-架构概述2. 运维安全项目之堡垒机2.1 堡垒机概述2.2 堡垒机选型2.3 环境准备2.4 部署Teleport堡垒机2.4.1 下载与部署2.4.2 启动2.4.3 浏览器访问teleport2.4.4 进行配置2.4.5 安装teleport客户端 2.5 teleport连接服务器 1. 运维安全…

opencv基础48-绘制图像轮廓并切割示例-cv2.drawContours()

绘制图像轮廓&#xff1a;drawContours函数 在 OpenCV 中&#xff0c;可以使用函数 cv2.drawContours()绘制图像轮廓。该函数的语法格式是&#xff1a; imagecv2.drawContours( image, contours, contourIdx, color[, thickness[, lineType[, hierarchy[, maxLevel[, offset]]…

openGauss学习笔记-31 openGauss 高级数据管理-索引

文章目录 openGauss学习笔记-31 openGauss 高级数据管理-索引31.1 语法格式31.2 参数说明31.3 示例 openGauss学习笔记-31 openGauss 高级数据管理-索引 索引是一个指向表中数据的指针。一个数据库中的索引与一本书的索引目录是非常相似的。 索引可以用来提高数据库查询性能&…

2023河南萌新联赛第(五)场:郑州轻工业大学 --Kruskal

题目描述 给定一张nnn个点的无向完全图&#xff0c;其中两点之间的路径边权为两点编号的按位与&#xff08;编号为 (1,2,...,n)(1,2,...,n)(1,2,...,n)&#xff09;&#xff0c;即w(u,v)u&v(1≤u,v≤n)w\left(u, v \right )u\&v \left( 1 \le u, v \le n \right)w(u,v…

CSS:盒子模型 与 多种横向布局方法

目录 盒子模型块级盒子内联级盒子内联块级盒子弹性盒子display 改变模型区域划分text 内容区padding 填充区border 边框区margin 外边距直接设置盒子大小 布局横向布局方法一 float 浮起来方法二 内联块级元素实现方法三 弹性盒子模型 盒子模型 块级盒子 独占一行&#xff0c…

layui的基本使用-日期控件的业务场景使用入门实战案例一

效果镇楼; 1 前端UI层面; <!DOCTYPE html> <html lang="en"> <head><meta charset="UTF-8"><meta http-equiv="X-UA-Compatible" content="IE=edge"><meta name="viewport" conten…

【前端】html

HTML标签&#xff08;上&#xff09; 目标&#xff1a; -能够说出标签的书写注意规范 -能够写出HTML骨架标签 -能够写出超链接标签 -能够写出图片标签并说出alt和title的区别 -能够说出相对路径的三种形式 目录&#xff1a; HTML语法规范HTML基本结构标签开发工具HTML常用标…