C++的关键字,命名空间,缺省参数,函数重载以及原理

文章目录

  • 前言
    • 一、C++关键字(C++98)
    • 二、命名空间
      • 命名空间介绍
      • 命名空间的使用
    • 三、C++输入【cin】& 输出【cout】
    • 四、缺省参数
      • 缺省参数概念
      • 缺省参数分类
      • 缺省参数的使用
      • 小结一下
    • 五、函数重载
      • 函数重载介绍
      • 函数重载类型
    • 六、C++支持函数重载的原理--名字修饰(name Mangling)【重点】

前言

从今天开始就序列更新C++的文章了,希望大家可以耐心的坚持下去学习,有一个很好的成长~~

首先来看一下C++的介绍,百度百科C++ – >点我跳转

C++是在C的基础之上,容纳进去了面向对象编程思想,并增加了许多有用的库,以及编程范式
等。熟悉C语言之后,对C++学习有一定的帮助,本章节主要目标:

  1. 补充C语言语法的不足,以及C++是如何对C语言设计不合理的地方进行优化的,比如:作用
    域方面、IO方面、函数方面、指针方面、宏方面等。
  2. 为后续类和对象学习打基础。
  • 我们这里不讲和C语言重合的语法,直接上干货,新内容,可以关注一下C语言的专栏
  • 下面直接开始C++之旅~~

C语言有关键字,那么C++也有关键字,首先我们来认识一下这些关键字

一、C++关键字(C++98)

  • C++总计63个关键字,C语言32个关键字
  • 这些关键字我们已经在C语言阶段已经有些见到过了,那些没有见过的关键字我们在后续的练习中会反复用到,所以也不用刻意记住慢慢的就都知道了~~
asmdoifreturntrycontinue
autodoubleinlineshorttypedeffor
booldynamic_castintsignedtypeidpublic
breakelselongsizeoftypenamethrow
caseenummutablestaticunionwchar_t
catchexplicitnamespacestatic_castunsigneddefault
charexportnewstructusingfriend
classexternoperatorswitchvirtualregister
constfalseprivatetemplatevoidtrue
const_castfloatprotectedthisvolatilewhile
deletegotoreinterpret_cast

第二个我们来认识一个新的概念叫命名空间

二、命名空间

命名空间介绍

  • C++ 的命名空间(Namespace)是一种用于组织和管理代码标识符(变量、函数、类等)的方法。它可以避免命名冲突,使得在不同的命名空间中可以使用相同的标识符而不会产生命名冲突。

  • 使用命名空间可以将一组相关的标识符封装在一起,提供了更好的代码组织和模块化能力。在 C++ 中,可以通过关键字 namespace 定义一个命名空间,并在其中声明相关的标识符。


  • 我们来看下面代码,定义了一个全局变量rand,而我还引入了头文件stdlib,而这个rand是stdlib中的一个库函数,–>rand,这样我想打印这个rand的值就会与库函数里的rand产生冲突,产生重定义,这个就是C语言中的不足之处了
#include <stdio.h>
#include <stdlib.h>
int rand = 10;

int main()
{
	printf("%d\n", rand);
	return 0;
}

在这里插入图片描述

  • 在C++中就可以很好的解决这种问题:

定义命名空间,需要使用到namespace关键字,后面跟命名空间的名字,然后接一对{}即可,{}中即为命名空间的成员。

  • 首先第一个正常的命名空间定义,也就是namespace后面跟上一个名字【随便起~】,也就相当于是一个域,就好像C语言中的局部域,全局域。
namespace lsl 
{
	// 命名空间中可以定义变量/函数/类型
	int rand = 10;
	
	int Add(int left, int right)
	{
		return left + right;
	}

	struct Node
	{
		struct Node* next;
		int val;
	};
}
  • 第二个就是命名空间可以嵌套
  • 这个也可以很好的理解,就和函数嵌套一样,一个域是一个域的,互不干扰
namespace N1
{
	int a;
	int b;
	int Add(int left, int right)
	{
		return left + right;
	}
	namespace N2
	{
		int c;
		int d;
		int Sub(int left, int right)
		{
			return left - right;
		}
	}
}
  • 第三个就是同一个工程中允许存在多个相同名称的命名空间,编译器最后会合成同一个命名空间中。

在这里插入图片描述

注意:一个命名空间就定义了一个新的作用域,命名空间中的所有内容都局限于该命名空间中

  • 那么我这个命名空间域如何使用呢?

  • 来看下面这段代码

namespace lsl
{
	// 命名空间中可以定义变量/函数/类型
	int a = 0;
	int b = 1;
	int Add(int left, int right)
	{
		return left + right;
	}
	struct Node
	{
		struct Node* next;
		int val;
	};
}
int main()
{
	printf("%d\n", a);
	return 0;
}

在这里插入图片描述

  • 上面图片清晰的展示到,是不能这样用的,已经是在一个域里面了,所以就要使用特定的方法来使用这个域里面变量,函数和类型

命名空间的使用

命名空间的使用有三种方式:

  • 第一种方式加命名空间名称及作用域限定符【::】也就是两个冒号,也就是域作用限定符
int main()
{
	printf("%d\n", lsl::a);
	return 0;
}

在这里插入图片描述

  • 第二种方式使用using将命名空间中某个成员引入

在这里插入图片描述

  • 第三种方式就是使用using namespace 命名空间名称引入,也就是展开,让指定的命名空间里的内容在外面都可以访问

在这里插入图片描述

这里的最后一种方式相信大家学c++或多或少也都见到过,平常在使用c++的时候都要有这么一句using namespace std;,std是C++标准库的命名空间名,C++将标准库的定义实现都放到这个命名空间中,这里的展开和头文件的展开是不一样的,不要混淆了~~

到这里我们也知道了,首先是先从局部域来搜索,然后从全局域再搜索,搜索不到就报错了,然而我们这里新增加了一个域作用限定符【::】,有了这个就是指定域搜索


  • 编译器搜索原则:

不指定域:当前局部域,全局域
指定域:如果指定了,直接去指定域搜索


三、C++输入【cin】& 输出【cout】

  • 在学习一门语言的时候,大部分人都会第一次写下这么一段代码,打印hello world,C++怎么来打印呢?
#include<iostream>
using namespace std;
int main()
{
	cout << "hello world" << endl;
	return 0;
}

在这里插入图片描述

说明:

  1. 使用cout标准输出对象(控制台)和cin标准输入对象(键盘)时,必须包含 < iostream >头文件以及按命名空间使用方法使用std
  2. coutcin是全局的流对象,endl是特殊的C++符号,表示换行输出,他们都包含在包含头文件中。后面在实际应用中会回用到很多,慢慢都会介绍~~
  3. <<流插入运算符>>流提取运算符
  4. 使用C++输入输出更方便,不需要像printf/scanf输入输出时那样,需要手动控制格式。C++的输入输出可以自动识别变量类型
  • 注意:早期标准库将所有功能在全局域中实现,声明在.h后缀的头文件中,使用时只需包含对应头文件即可,后来将其实现在std命名空间下,为了和C头文件区分,也为了正确使用命名空间,规定C++头文件不带.h;旧编译器(vc 6.0)中还支持<iostream.h>格式,后续编译器已不支持,因此推荐使用+std的方式。

  • 这里的cout【输出】,cin【输入】可以自动识别类型

在这里插入图片描述

std命名空间的使用惯例:

std是C++标准库的命名空间,如何展开std使用更合理呢?

  1. 在日常练习中,建议直接using namespace std即可,这样就很方便。
  2. using namespace std展开,标准库就全部暴露出来了,如果我们定义跟库重名的类型/对象/函数,就存在冲突问题。该问题在日常练习中很少出现,但是项目开发中代码较多、规模大,就很容易出现。所以建议在项目开发中使用,像std::cout这样使用时指定命名空间 +using std::cout展开常用的库对象/类型等方式。

四、缺省参数

缺省参数概念

  • 缺省参数是声明或定义函数时为函数的参数指定一个缺省值。
  • 在调用该函数时,如果没有指定实参则采用该形参的缺省值,否则使用指定的实参。

接下来看一个案例就能明白了:

void Func(int a = 0)
{
	cout << a << endl;
}
int main()
{
	Func(); // 没有传参时,使用参数的默认值
	Func(10); // 传参时,使用指定的实参
	return 0;
}

在这里插入图片描述

缺省参数分类

  • 全缺省参数【也就是从左到右形参都有默认值】
void Func(int a = 10, int b = 20, int c = 30)
{
	cout<<"a = "<<a<<endl;
	cout<<"b = "<<b<<endl;
	cout<<"c = "<<c<<endl;
}
  • 半缺省参数【必须是从右到左赋值,不可以从左到右】
void Func(int a, int b = 10, int c = 20)
{
	cout<<"a = "<<a<<endl;
	cout<<"b = "<<b<<endl;
	cout<<"c = "<<c<<endl;
}

缺省参数的使用

  • 我们可以这样使用:
  • 第一个参数就是匹配的一个形参,依次匹配,不可跳跃的传参

在这里插入图片描述

  • 实际上我们是还可以这样用的,比如说我是定义了一个栈,栈在初始化的的时候不知道一开始初始化多少个,这个时候我们就可以使用缺省参数,指定传参。
  • 比如我知道要插入100个数据,我就直接指定100的大小就可以,减少扩容消耗
  • 如果不知道多少个就默认4个就可以啦~~

在这里插入图片描述

还有一个重要的点,就是下面这里

  • 我们这里可以分文件写这个栈

在这里插入图片描述

  • 我们这里的声明定义可以同时写吗?

我们有人写代码的时候就有可能写成这样的操作,声明的参数和定义的参数不一样,那么是依谁的为准呢?

在这里插入图片描述

  • 我们这里直接给出结论,是必须在声明给,为什么呢?
  • 这就需要了解代码的编译原理了,到时候会发表一篇C语言的编译程序环境和预处理,程序编译+链接全过程,尽情期待~~
  • 在同一文件下,缺省值在函数的声明与定义中同时定义,在编译阶段的语法检查时,直接报错了~

小结一下

1. 半缺省参数必须从右往左依次来给出,不能间隔着给
2. 缺省参数不能在函数声明和定义中同时出现
3. 缺省值必须是常量或者全局变量
4. C语言不支持(编译器不支持)


五、函数重载

函数重载介绍

函数重载:是函数的一种特殊情况,C++允许在同一作用域中声明几个功能类似的同名函数,这些同名函数的形参列表(参数个数 或 类型 或 类型顺序)不同,常用来处理实现功能类似数据类型不同的问题。

函数重载类型

函数重载有3个类型,我们分别来看一下:

  • 第一个就是参数类型不同

在这里插入图片描述

第二个是参数个数不同

在这里插入图片描述

  • 第三个就是参数类型顺序不同

在这里插入图片描述

  • 最后这里要注意:构成函数重载的条件是函数名相同,参数不同,构成函数重载【非常重要】

下面我们来看一道题【自己先做一下】来巩固一下:

以下不是double compare(int,int)的重载函数的是( )

A. int compare(double,double)
B. double compare(double,double)
C. double compare(double,int)
D. int compare(int,int)

解析:

A.重载必须是参数列表有所不同(包括个数和类型),所以参数类型不同,构成重载
B.参数类型不同,构成重载
C.参数类型不同,构成重载
D.函数重载不能依靠返回值的不同来构成重载,因为调用时无法根据参数列表确定调用哪个重载函 数,故错误


六、C++支持函数重载的原理–名字修饰(name Mangling)【重点】

那么为什么C++支持函数重载呢?而C语言不支持呢?

  • 靠的就是名字修饰

在这里插入图片描述

  1. 实际项目通常是由多个头文件和多个源文件构成,而通过C语言阶段学习的编译链接,我们可以知道,【当前a.cpp中调用了b.cpp中定义的Add函数时】,编译后链接前,a.o的目标文件中没有Add的函数地址,因为Add是在b.cpp中定义的,所以Add的地址在b.o中。那么怎么办呢?
  2. 所以链接阶段就是专门处理这种问题,链接器看到a.o调用Add,但是没有Add的地址,就会到b.o的符号表中找Add的地址,然后链接到一起。
  3. 那么链接时,面对Add函数,链接接器会使用哪个名字去找呢?这里每个编译器都有自己的函数名修饰规则。
  4. 由于Windows下vs的修饰规则过于复杂,而Linux下g++的修饰规则简单易懂,下面我们使用了g++演示了这个修饰后的名字。
  5. 通过下面我们可以看出gcc的函数修饰后名字不变。而g++的函数修饰后变成【_Z+函数长度+函数名+类型首字母】。

在这里插入图片描述

  • gcc编译后的结果:

在这里插入图片描述

结论:在linux下,采用gcc编译完成后,函数名字的修饰没有发生改变,之所以就函数名不能相同

  • 采用C++编译器编译后结果:

在这里插入图片描述

结论:在linux下,采用g++编译完成后,函数名字的修饰发生改变,编译器将函数参
数类型信息添加到修改后的名字中,所以就支持函数重载


  • Windows下名字修饰规则

在这里插入图片描述

  • 对比Linux会发现,windows下vs编译器对函数名字修饰规则相对复杂难懂,但道理都是类似的,我们就不做细致的研究了。

  • 扩展学习:C/C++函数调用约定和名字修饰规则–有兴趣好奇的同学可以自行搜索看一看,里面有对vs下函数名修饰规则讲解

  • 通过这里就理解了C语言没办法支持重载,因为同名函数没办法区分。而C++是通过函数修饰规则来区分只要参数不同修饰出来的名字就不一样,就支持了重载。

  • 如果两个函数函数名和参数是一样的,返回值不同是不构成重载的,因为调用时编译器没办
    法区分。

最后,本章简单的介绍了C++的关键字,介绍了命名空间的作用和使用,知道了C++的输出和出入,会用缺省参数,以及函数重载~~

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

科普栏目|负氧离子水壁炉低能耗的背后的原因与生活优势

科普栏目&#xff5c;负氧离子水壁炉低能耗的背后的原因与生活优势 在当今追求绿色生活和能源高效利用的潮流中&#xff0c;负氧离子水壁炉以其低能耗的特性成为了家庭装饰领域的一颗明珠。究竟是什么原因使得这项技术在能耗方面脱颖而出呢&#xff1f;而低能耗又能为生活带来…

freeswitch智能外呼系统搭建流程

1.获取实时音频数据 media_bug &#xff08;好多mrcp方式也崩溃所以用以下方式&#xff09; 可以参考 方式可以通过socket或者webscoket freeswitch[1.05]用websocket发送mediabug语音流到ASRProxy实现实时质检和坐席辅助 - 知乎 2.webscoket 好多c的库放模块容易崩溃 可以…

适合孩子读书用什么的落地灯?落地护眼灯测评推荐

现代人用眼负荷极大&#xff0c;不仅白天要办公&#xff0c;晚上更是玩手机、刷短视频或是晚间看书阅读&#xff0c;所以营造一个健康的照明环境很重要&#xff01; 如何营造一个健康的照明环境呢&#xff1f;那就不得不提起最近就很火的落地护眼灯。不同于其他台灯灯具&#…

flutter极光推送配置厂商通道(华为)笔记--进行中

一、基础集成按照下面官方文档进行 厂商通道相关参数申请教程 集成厂商 集成指南 官方文档&#xff1a;厂商通道回执配置指南 注意&#xff1a;不同厂商对app上架的要求不同&#xff0c;华为、荣耀 对app上架没有硬性要求 遇到问题 1、引入apply plugin: com.huawei.agconn…

Java玩转《啊哈算法》排序之桶排序

过去心不可得&#xff0c;现在心不可得&#xff0c;未来心不可得 目录在这里 楔子代码地址桶排序代码核心部分优缺点 完整代码演示 升级版核心代码完整代码演示 楔子 大家好&#xff01;本人最近看了下《啊哈算法》&#xff0c;写的确实不错&#xff0c;生动形象又有趣&#x…

k8s的安全机制

k8s是分布式集群管理工具&#xff0c;k8s作用是容器编排 1、安全机制核心&#xff1a;API server。API server作为整个集群内部通信的中介&#xff0c;也是外部控制的入口&#xff0c;所有的安全机制都是围绕api sserver来进行设计的。请求api server资源要满足3个条件&#x…

Garbage First收集器(简称G1)

概述&#xff1a;Garbage First&#xff08;简称G1&#xff09;收集器是垃圾收集器技术发展历史上的里程碑式的成果&#xff0c;它开创了收集器面向局部收集的设计思路和基于Region的内存布局形式。 G1开创的基于Region的堆内存布局是它能够实现这个目标的关键。虽然G1也仍是遵…

开始学习Vue(路由)

一、什么是路由 SPA 指的是一个 web 网站只有唯一的一个 HTML 页面&#xff0c;所有组 件的展示与切换都在这唯一的一个页面内完成。 此时&#xff0c;不同组件之间的切换需要通过前端路由来实现。 结论&#xff1a;在 SPA 项目中&#xff0c;不同功能之间的切换&#xff0…

无人机航迹规划(六):七种元启发算法(DBO、LO、SWO、COA、LSO、KOA、GRO)求解无人机路径规划(提供MATLAB代码)

一、七种算法&#xff08;DBO、LO、SWO、COA、LSO、KOA、GRO&#xff09;简介 1、蜣螂优化算法DBO 蜣螂优化算法&#xff08;Dung beetle optimizer&#xff0c;DBO&#xff09;由Jiankai Xue和Bo Shen于2022年提出&#xff0c;该算法主要受蜣螂的滚球、跳舞、觅食、偷窃和繁…

LP-AM243x EtherNet/IP 连接施耐德 M241 EIP主站测试

硬件环境&#xff1a;LP-AM243x 开发板 施耐德 Modicon M241 软件环境&#xff1a; INDUSTRIAL-COMMUNICATIONS-SDK-AM243X MCU-PLUS-SDK-AM243X — MCU SDK for AM243x 调试过程&#xff1a; 首先&#xff0c;让AM243x能够运行 Null Boot&#xff0c; Starting NULL Boo…

力扣hot100 除自身以外数组的乘积 前后缀积

Problem: 238. 除自身以外数组的乘积 文章目录 思路前后缀积 思路 前后缀积 ⏰ 时间复杂度: O ( n ) O(n) O(n) &#x1f30e; 空间复杂度: O ( n ) O(n) O(n) class Solution {public int[] productExceptSelf(int[] nums){int n nums.length;int[] p new int[n];//除…

Obsidian - 使用小记(Typora切换过来)

文章目录 关于 Obsidian打开已有的 文件夹将图片改为 Typora 的保存文件夹 关于 Obsidian 官网 https://obsidian.md/github : https://github.com/obsidianmd 个人版免费 一直习惯用 Typora 编写markdown git 记录笔记&#xff0c;多次被安利 Obsidian 后&#xff0c;今天尝…

解决TortoiseGit软件Git Show log时显示Too many files to display的问题

1 问题描述 有时代码提交修改的文件比较多&#xff0c;当查看log时无法显示出来修改的文件列表&#xff0c;如下所示&#xff1a; 2 解决方法 将LogTooManyItemsThreshold尽可能配置得大一些。 三 参考资料 https://gitlab.com/tortoisegit/tortoisegit/-/issues/3878

session反序列化

据陈腾师傅所说&#xff1a; 1.漏洞产生原因&#xff1a;写入格式和读取格式不一样。 下面是三种常见的存储格式&#xff1a; 处理器 对应的存储格式 php键名竖线经过serialize()函数序列化处理的值php_serialize(php>5.54)经…

vue3+Element plus实现登录功能

一、想要实现的效果 二、搭建登录静态 1、实现左边背景和右边登录栏的总体布局布局&#xff1a; <el-row class"content"><!--el-col 列&#xff1a; --><el-col :span"16" :xs"0" class"content-left"></el-c…

司铭宇老师:电话销售心态培训:电话销售被拒绝怎么调整心态

电话销售心态培训&#xff1a;电话销售被拒绝怎么调整心态 在电话销售这个行业中&#xff0c;遭遇拒绝是家常便饭。无论你如何努力&#xff0c;总有那么些时候&#xff0c;客户会对你的产品或服务说“不”。然而&#xff0c;这并不意味着你的努力白费。关键在于如何调整心态&am…

洗内裤的小洗衣机买啥牌子的?四款家用小洗衣机推荐

随着内衣洗衣机的流行&#xff0c;很多小伙伴在纠结该不该入手一款内衣洗衣机&#xff0c;专门来洗一些贴身衣物&#xff0c;答案是非常有必要的&#xff0c;因为我们现在市面上的大型洗衣机只能做清洁&#xff0c;无法对我们的贴身衣物进行一个高强度的清洁&#xff0c;而小小…

Java|IDEA 运行和打包报错解决

IDEA 运行和打包报错解决 java.lang.NoSuchFieldError&#xff1a;com.sun.tools.javac.tree.JCTree$JCImport 报错信息 环境&#xff1a;JDK 21 java: java.lang.NoSuchFieldError: Class com.sun.tools.javac.tree.JCTree$JCImport does not have member field com.sun.t…

Messari发布重磅研报,波场TRON 2023 Q4期间实现多项突破

近日,顶级加密数据研究机构Messari发布了波场TRON 2023 Q4调研报告,报告从网络数据、生态、稳定币和RWA等多个方面对波场TRON进行了细致研究,并给与了波场TRON极大的肯定。这份调研报告帮助投资者和社区更好地了解波场TRON的发展前景和竞争优势。同时,这些数据和见解可以提高投…

嵌入式学习五

使用circuit JS模拟器讲解 一&#xff1a;欧姆定律 演示电压电阻的关系 欧姆定律 二&#xff1a;电阻 计算电阻串并联的阻值 电阻 电阻越串越大&#xff0c;越并越小 并联电路增加通路 三&#xff1a;电容器 观察电容的充放电 电容器 电容就是一个临时存储电量的容器 当电…
最新文章