【C++初阶】C++基础(上)——C++关键字、命名空间、C++输入输出、缺省参数、函数重载

news2024/11/15 4:20:00

目录

1. C++关键字

2. 命名空间

2.1 命名空间的定义

2.2 命名空间的使用

3. C++输入&输出

4. 缺省参数

4.1 缺省参数概念

4.2 缺省参数分类

5. 函数重载

5.1 函数重载概念

5.2 C++支持函数重载的原理——名字修饰(name Mingling)

5.3 extern "C"


❀❀❀没有坚持的努力,本质上并没有多大的意义。


1. C++关键字

C++ 总计 63 个关键字, C 语言 32 个关键字

#include <iostream> 相当于C语言中的 #include<stdio.h>

2. 命名空间

2.1 命名空间的定义

同一个作用域里面,是不能有同名变量的。

命名冲突,在C语言没有很好的解决这个问题,但是CPP引入了namespace来解决这个问题。

使用命名空间的目的是 对标识符的名称进行本地化 ,以 避免命名冲突或名字 污染(一个命名空间就定义了一个新的作用域)

 ::域作用限定符

命名空间可以定义变量

#include <iostream>
//这是一个命名空间,可以定义变量、函数、类型
namespace ky
{
	int a = 0;
	int c = 2;
}

int b = 0;
int c = 1;

int main()
{
	int b = 1;
	int a = 1;
	printf("%d\n", b);//b = 1,访问局部变量
	printf("%d\n", ::b);//b = 0, 访问全局变量//::域作用限定符
	printf("%d\n", a);//a = 1;
	printf("%d\n", ky::a);//a = 0;
	printf("%d\n", c);//1
	printf("%d\n", ::c);//1
	printf("%d\n", ky::c);//2
	return 0;
}

命名空间可以定义函数、类型

#include <iostream>
namespace yyqx
{
	//定义函数
	void f()
	{
		printf("void f()\n");
	}
	//定义结构
	struct ListNode
	{
		int val;
		struct ListNode* next;
	};

}

namespace ky
{
	struct ListNode
	{
		int val;
		struct ListNode* next;
	};

}

int f = 0;
int main()
{
	printf("%d\n", f);//0
	printf("%p\n", yyqx::f);//结构体的地址
	yyqx::ListNode* n1 = NULL;
	ky::ListNode*  n2 = NULL;
	return 0;
}

命名空间可以嵌套而且同名的命名空间是可以同时存在的,编译器编译时会将其合并。

代码1展示: 

#include <iostream>

namespace yyqx
{
	int a = 1;
	namespace A
	{
		struct Node
		{
			int val = 0;
			struct Node* next= NULL;
		};
	}
	
}

namespace yyqx
{
	int b = 1;
	namespace B
	{
		struct Node
		{
			int val = 0;
			struct Node* next = NULL;
		};
	}
	
}

int main()
{
	struct yyqx::A::Node n1;
	struct yyqx::B::Node n2;

	return 0;
}

命名空间不影响生命周期,是全局变量还是全局变量,只是命名发生冲突时,进行隔离的作用。【命名空间只能放在全局】

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

2.2 命名空间的使用

(1)加命名空间名称及作用域限定符

(2)使用using将命名空间中某个成员引入    

using yyqx::a;//代码1//释放yyqx命名空间里面的变量a
//释放的是命名空间就加namespace,如果释放的不是命名空间而是命名空间里的数据,就不用加namespace

(3)使用using namespace 命名空间名称引入

[我们经常使用第二种,既不会容易发生冲突,又不会特别麻烦]

using namespace yyqx;//意思是把yyqx这个命名空间定义的内容释放出来
int main()
{
	struct A::Node n1;
	struct B::Node n2;

	return 0;
}
using namespace yyqx;//意思是把yyqx这个命名空间定义的内容释放出来
using namespace A;//第二层释放
//因为A在yyqx里面,所以上面两行的内容不能进行交换
int main()
{
	struct Node n1;
	struct B::Node n2;

	return 0;
}

 这里代码释放A,就不能释放B,否则就发生命名冲突(using相当于没有命名空间)

using namespace yyqx::A;

这个代码相当于释放A,但是并没有释放yyqx;

 using namespace std;//std 封C++库的命名空间

3. C++输入&输出

#include <iostream>
using namespace std;

int main()
{
	int a = 0;
	cin >> a;// >>流提取运算法,相当于scanf
	cout << a;// << 流插入运算法

	return 0;
}

#include <iostream>
using namespace std;

int main()
{
	int a = 0;
	double b = 0;
	cin >> a >> b;// >>流提取运算法,相当于scanf
	cout << a << " " << b << endl;// << 流插入运算法 endl相当于换行
	cout << a << ":" << b << '\n';
	cout << "hello world" << endl;
	return 0;
}

(1)endl相当于换行'\n'

(2)<assert.h>在C++中也可以用,但是没有命名空间,<cassert>就有命名空间了

(3)使用 cout 标准输出对象 ( 控制台 ) cin 标准输入对象 ( 键盘 ) 时,必须 包含 < iostream > 头文件 以及按命名空间使用方法使用std
(4)C++的输入输出可以自动识别变量类型。

(5)旧编译器(vc 6.0)中还支持<iostream.h>格式,<iostream.h>格式没有命名空间

4. 缺省参数

4.1 缺省参数概念

缺省参数是 声明或定义函数时 为函数的 参数指定一个缺省值 。在调用该函数时,如果没有指定实参则采用该形参的缺省值,否则使用指定的实参。
#include <iostream>
using namespace std;

//缺省参数(默认参数)
void Test(int a = 0)
{
	cout << a << endl;
}

int main()
{
	Test();//没有传参时,使用参数的默认值a = 0
	Test(1);//传参时,使用指定的实参 a = 1;
}

4.2 缺省参数分类

(1)全缺省参数(全默认参数)

void Test(int a = 10, int b = 20, int c = 30)
{
	cout << "a = " << a << endl;
	cout << "b = " << b << endl;
	cout << "c = " << c << endl;
}

(2)半缺省参数

void Test(int a , int b = 20, int c = 30)//必须从右向左缺省,并且是连续的
{
	cout << "a = " << a << endl;
	cout << "b = " << b << endl;
	cout << "c = " << c << endl;
}
1. 半缺省参数必须 从右往左依次 来给出,不能间隔着给
2. 缺省参数不能在函数声明和定义中同时出现(最好在声明给;声明不给,定义给也不可以)
3. 缺省值必须是常量或者全局变量
4. C 语言不支持(编译器不支持)

5. 函数重载

5.1 函数重载概念

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

(1)参数类型不同

int Add(int left, int right)
{
	return left + right;
}
double Add(double left, double right)
{
	return left + right;
}

(2)参数个数不同

void f()
{
	cout << "f()" << endl;
}
void f(int a)
{
	cout << "f(int a)" << endl;
}

(3)参数类型顺序不同

void f(int a, char b)
{
	cout << "f(int a,char b)" << endl;
}
void f(char b, int a)
{
	cout << "f(char b, int a)" << endl;
}

C语言不支持同名函数,CPP支持同名函数。要求:参数名相同,参数不同

代码:

short Add(short left, short right)
{
	return left + right;
}
int Add(short left, short right)
{
	return left + right;
}

 上述代码不是函数重载,因为函数进行调用的时候,并不知道要调用哪一个函数。(仅仅只有返回值不同是不能构造函数重载的)函数重载要求参数不同。而跟返回值没关系。

5.2 C++支持函数重载的原理——名字修饰(name Mingling)

C语言不支持重载,C++支持重载。C++是如何支持的?为什么C语言不支持?

C/C++ 中,一个程序要运行起来,需要经历以下几个阶段: 预处理(预编译)、编译、汇编、链接

预处理:头文件展开、宏替换、条件编译、去掉注释

编译:检查语法、生成汇编代码

汇编:把汇编代码转换成二进制的机器码

链接:找调用函数的地址,链接对应上,合并到一起

(1)实际项目通常是由多个头文件和多个源文件构成,【当前a.cpp中调用了b.cpp中定义的Add函数时】,编译链接a.o的目标文件中没有Add的函数地址,因为Add是在b.cpp中定义的,所以Add的地址在b.o中。那么怎么办呢?

(2)  所以链接阶段就是专门处理这种问题, 链接器看到 a.o 调用 Add ,但是没有 Add 的地址,就会到 b.o 的符 号表中找 Add 的地址,然后链接到一起
//函数1
void f(int a, double b)
{
	printf("%d %lf\n", a, b);
}
//函数2
void f(double b, int a)
{
	printf("%lf %d\n", b, a);
}

链接的时候,有符号表和函数调用指令。 

C语言中,函数1和函数2,生成的符号表,都是f,所以会发生冲突,所以会发生错误,C语言就不支持函数重载

 但是在C++中,函数1和函数2生成的符号表是不同的,所以C++就支持函数重载

 

 总而言之还是函数修饰后的名字不同,C语言中仍然是函数名,而C++中是【_Z+函数长度+函数名+类型首字母(如果是指针就多加一个P)】通过这里就理解了C语言没办法支持重载,因为同名函数没办法区分。而C++是通过函数修饰规则来区分,只要参数不同,修饰出来的名字就不一样,就支持了重载

5.3 extern "C"

在C语言中,extern "C" 可以添加在函数声明的前面,也可以extern "C"后添加一个花括号,然后把函数声明括起来
在函数前加 extern "C",作用是告诉编译器,将该函数按照C 语言规则来编译。

C语言是可以调用C++和C语言的静态库和动态库的。C++是可以调用C++和C语言的静态库和动态库的。

C++调用C静态库:(虽然C++兼容C,为什么需要用到extern "C"呢?因为函数的命名修饰是不一样的,所以想调用C的函数的时候,符号表找不到我们想要的内容)

extern "C"
{
    #include "../../Stack_C/Stack_C/stack.h"
}

然后,右击属性->链接器->常规->附加库目录->找到静态库文件,最后右击属性->链接器->输入->附加依赖项Stack_C.lib;即可

C语言调用C++:(C中没有extern "C",只有C++有)

在C++的文件中,函数前面添加EXTERN_C(这个是随意定义的),然后前面再写一个条件编译(__cplusplus是C++中)[两个杠]

(第一种写法)条件编译:当在C++中,函数前面经过宏替换就是extern "C",在C语言中,就相当于什么也没有】

 (第二种写法)

 然后,右击属性->链接器->常规->附加库目录->找到静态库文件,最后右击属性->链接器->输入->附加依赖项Stack_CPP.lib;即可

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

围棋基础知识

1、气 1.1星位位置 1.2天元位置 1.3 气的位置 2、禁入点 白棋里面的位置就是禁入点&#xff0c;也可以称为没有气的位置可以称为禁入点 破解之法&#xff1a; 在于将白棋全部围住&#xff0c;下一步为围住之策&#xff0c;即可。 3、死棋和活棋 3.1活棋 3.2 死棋 白棋的样…

探寻数据服务的本质:API之外的可能性

数据服务在数据建设中发挥着重要的作用。数据服务到底啥样&#xff1f; 是不是只对外提供一个API&#xff1f; 这么简单&#xff1f; 而我希望你能在学完这部分内容之后&#xff0c;真正掌握数据服务的产品功能设计和系统架构设计。因为这会对你设计一个数据服务&#xff0c;或…

青少年护眼灯哪个好?2023全新五款台灯推荐

国内儿童青少年的视力健康问题越来越突出&#xff0c;甚至许多孩子年纪非常小就已经近视了&#xff0c;所以许多老师以及眼科医生都和家长们强调护眼台灯的重要性。不过&#xff0c;护眼台灯虽好&#xff0c;但在选购时也要注意那些无法护眼的不专业品牌&#xff0c;许多产品有…

ICC2如何计算Gate Count?

我正在「拾陆楼」和朋友们讨论有趣的话题&#xff0c;你⼀起来吧&#xff1f;知识星球入口 我们认为gate count等于standard cell(非physical only)总面积 / 最小驱动二输入与非门面积。 ICC2没有专门的命令去报告gate count&#xff0c;只能自己计算&#xff0c;使用report_d…

MySQL数据库——DDL基本操作

文章目录 前言数据库操作查看已存在的所有数据库创建数据库选中数据库删除数据库修改数据库编码 表操作创建表显示创建表时的语句显示表结构删除表修改表的结构增加列修改列删除列 修改表名 前言 DDL 操作是与数据库结构相关的操作&#xff0c;它们不涉及实际的数据操作&#…

B2B企业如何选择CRM系统?

CRM软件的优势在于简化业务流程&#xff0c;实现企业的降本增效。越来越多的B2B企业通过CRM为业务赋能&#xff0c;B2B企业如何快速找到适合公司业务的CRM系统&#xff1f;总的来说就是根据企业自身业务而量身打造的一套系统。 1.整理业务需求 B2B企业首先要考虑是业务痛点&a…

易基因:m6A-seq等揭示RBM33参与调控m6A去甲基化酶ALKBH5活性及其底物选择性|科研进展

大家好&#xff0c;这里是专注表观组学十余年&#xff0c;领跑多组学科研服务的易基因。 RNA结合蛋白&#xff08;RNA-binding protein&#xff0c;RBP&#xff09;是一类结构和功能多样化的蛋白质&#xff0c;参与多种生物过程。越来越多的证据表明&#xff0c;RBP通过调控编…

意外:WPS编程新工具,不用编程,excel用户:可以不用VBA啦

来来来&#xff0c;拓宽一下视野&#xff01; 别总以为excel和WPS只能用VBA编程&#xff0c;也别总是想着ACCESS这些老生常谈的工具。其实对于电子表格高级用户来讲&#xff0c;不会VBA&#xff0c;不用ACCESS&#xff0c;也一样可以解决复杂问题或者高级应用。 尤其是WPS用户…

C++多线程编程(第三章 利用栈特性自动释放锁RALL,锁管理器、控制器)

1、什么是RALL&#xff0c;手动代码实现 RALL&#xff08;resource Acquisition Is Initialization &#xff09;C 之父Bjarne Stroustrup 提出&#xff1b; 使用局部对象来管理资源的技术称为资源获取即初始化&#xff1b;它的生命周期是由操作系统来管理的&#xff0c;无需人…

Hive分区分桶

分区 分区概念 在逻辑上分区表与未分区表没有区别&#xff0c;在物理上分区表会将数据按照分区键的列值存储在表目录的子目录中&#xff0c;目录名“分区键键值”。其中需要注意的是分区键的值不一定要基于表的某一列&#xff08;字段&#xff09;&#xff0c;它可以指定任意…

ubuntu软件:录制视频和截图工具,压缩视频

1. 自带录制视频工具&#xff1b; 使用方式&#xff1a; 无需下载 开始录屏/结束录屏&#xff1a;Ctrl Alt Shift r 当看到 Ubuntu 桌面的右上方多了一个红色的小圆点&#xff0c;代表正在录制 注意&#xff1a; 录屏默认的时长30秒&#xff0c;超时会自动结束&#xff01…

Postman如何导出接口的几种方法

本文主要介绍了Postman如何导出接口的几种方法&#xff0c;文中通过示例代码介绍的非常详细&#xff0c;具有一定的参考价值&#xff0c;感兴趣的小伙伴们可以参考一下 前言&#xff1a; 我的文章还是一贯的作风&#xff0c;简确用风格&#xff08;简单确实有用&#xff09;&am…

无涯教程-jQuery - serialize( )方法函数

serialize()方法将一组输入元素序列化为数据字符串。 serialize( ) - 语法 $.serialize( ) serialize( ) - 示例 假设无涯教程在serialize.php文件中具有以下PHP内容- <?php if( $_REQUEST["name"] ) {$name$_REQUEST[name];echo "Welcome ". $na…

JavaScript小结测试

题目 有两个体操队&#xff0c;海豚队和考拉队。他们互相竞争3次。平均得分最高的赢家将获得奖杯! 利用下面的测试数据&#xff0c;计算每队的平均得分 比较各队的平均分&#xff0c;以确定比赛的获胜者&#xff0c;并将其打印到控制台。不要忘了可能会出现平局&#xff0c;所…

ENVI提取NDVI与植被覆盖度估算

目标是通过ENVI计算植被覆盖度结合ArcGIS出图得到植被覆盖图。 一、植被覆盖度的定义: 植被覆盖度( FractionalVegetation Cover,FVC) 通常定义为植被( 包括叶、茎、枝) 在地面的垂直投影面积占统计区总面积的百分比,它量化了植被的茂密程度,反应了植被的生长态势,是刻画…

C语言结构体大小分析

一&#xff0c;基本类型 C语言自带的数据类型大小如下 数据类型大小&#xff08;字节&#xff09;char1short2int4long4或8float4double8long double16 二&#xff0c;自定义类型---struct C语言除了以上这些基本类型&#xff0c;还支持用户自己定义数据类型 类似于一下形…

Android Banner - ViewPager

现在来给viewpager实现的banenr加上自动轮播 自动轮播的原理&#xff0c;使用handler的延迟消息来实现。 自动轮播实现如下内容 开始轮播&停止轮播 可配置轮播时长、轮播方向 通过自定义属性来配置轮播时长&#xff0c;方向 感知生命周期&#xff0c;可见时开始轮播&…

【Ansible】Ansible自动化运维工具的应用与常用命令

ansible自动化运维工具 一、ansible 的概述1. ansible 的概念2. ansible 的特性 二、ansible 的部署与命令1. ansible 的部署1.1 服务器ip地址设置1.2 ansible 服务器部署 2. ansible 命令行模块2.1 command 模块2.2 shell 模块2.3 cron 模块2.4 user 模块2.5 group 模块2.6 co…

Spring Batch教程(三)示例:从mysql中读取数据写入文本和从多个文本中读取内容写入mysql

Spring batch 系列文章 Spring Batch教程&#xff08;一&#xff09; 简单的介绍以及通过springbatch将xml文件转成txt文件 Spring Batch教程&#xff08;二&#xff09;示例&#xff1a;将txt文件转成xml文件以及读取xml文件内容存储到数据库mysql Spring Batch教程&#xff…

在CSDN的几年,我的Python书籍,第三次重印了!

大家好&#xff0c;我是黄伟&#x1f92d; 我的书籍《快学Python&#xff1a;自动化办公轻松实战》第3次重印了&#xff0c;感谢大家的支持。 这本书干货多多&#xff0c;零基础教你Python自动化办公&#xff0c;让你工作效率提升10倍&#xff0c;提前1小时下班。 因此&#…