C++---命名空间

目录

  • c语言中的问题
  • 命名空间的定义
  • 注意事项
    • 第一点:同名命名空间
    • 第二点:命名空间中的全局变量与局部变量
  • 命名空间的使用
    • 第一种使用方法
    • 第二种使用方法
    • 第三种使用方法
  • 注意事项
    • 第一点:没有名字的命名空间
    • 第二点:局部优先原则
    • 第三点:命名空间和结构体

c语言中的问题

大家在学习c语言的时候有没有发现一个问题,就是我们在创建变量的时候,如果两个变量的名字是一样的话就会报出变量重定义的问题,比如说下面的代码:

#include<stdio.h>
int main()
{int num = 10;int num = 10;return 0;
}

我们将此代码运行一下就可以发现我们这里会报出一个错误:
在这里插入图片描述
但是我们在编写一个大的项目的时候会创建许许多多的变量出来,而且一个大型的项目一般都是分给多个人来完成,每个人负责编写一些文件,最后再通过#include" 文件名" 将不同程序员写的不同的文件合并到一起,但是这样我们就会出现一个问题就是,我们这里不同的人会创建出不同的变量,这些变量有着不同的作用和功能,但是他们可能会有同样的名字,因为程序员在写的时候他是不知道其他程序员是怎么想的,比如说一号程序员在写的时候为了记录一个函数的返回值他就创建了一个整型的变量并且将其取名为:ret,而另一个程序员在编写程序的时候为了得到另一个函数的返回值也创建一个名为ret的整型变量,这样的话我们将这两个程序员写的文件合并到一起去的时候是不是就可能出现这个问题啊,比如说下面的代码:

#include<stdio.h>
#include<stdlib.h>
int rand = 10;
int main()
{printf("%d", rand);return 0;
}

这段代码创建了一个全局变量rand,然后我们想在main函数里面打印一下这个rand的值,但是我们这里引入stdlib.h这个文件,在这个文件里面也使用了rand这个名字,如果我们不知道有这件事并且运行这段代码的话,我们就会发现这里就会报出许多错误出来:
在这里插入图片描述
而且一个大型的项目所需要的变量和函数是非常的多的,而这就会大大的增加因名字相同而出现问题的概率,那么为了解决这个问题我们c++就增加了一个新的内容叫命名空间。分析了c语言出现的问题原因,不同的程序创建出来的不同的变量可能会有取同样的名字,这样在汇总的时候就会导致出现重定义的问题,那么c++就对此给出了一个解决方法:对这些变量再加上一层包装,并且程序员还要对这些包装取一个名字,在这个包装里面程序员可以添加自己想要创建的变量,定义的函数,以及结构体等等。比如说一号程序员创建了一个命名空间名为one,二号程序员创建了一个命名空间名为two,这样两个程序员即使在命名空间中使用了相同的变量名也不会出现错误。

命名空间的定义

要想使用命名空间我们就得先来认识关键字:namespace,他的使用模板就如下:
在这里插入图片描述
首先写一个namespace,然后在后面写上这个命名空间的名字,然后在下面加一个大括号,这个大括号里面放的就是你们想创建的变量或者结构体或者函数等等,比如我们下面的代码:

#include<stdio.h>
namespace ycf
{int a = 10;struct student{int age;char name[20];char sex[10];};int add(int x, int y){return x + y;}
}
int main()
{return 0;
}

这里就创建了一个命名空间,给命名空间取名为ycf在命名空间中创建整型变量a将其初始化为10,定义了一个add函数创建一个结构体,那么这就是ycf命令空间里面的内容,当然我们这里可以创建多个命名空间不止这一个。那么这就是我们定义命名空间的全部内容,当然这里还有一些注意事项希望大家注意一下。

注意事项

第一点:同名命名空间

如果有多个名字相同的命名空间,那么我们的编译器就会自动地将这些命名空间进行合并,合并成同一个名字的命名空间,比如说下面的代码:

#include<stdio.h>
namespace a
{int b = 10;int c = 20;
}
namespace a
{double e = 1.0;double f = 2.0;
}
int main()
{return 0;
}

这里创建了两个命名空间,但是他们的名字是一样的,那么编译器就会将这两个命名空间合并成一个,也就变成了这样:

#include<stdio.h>
namespace a
{int b = 10;int c = 20;double e = 1.0;double f = 2.0;
}int main()
{return 0;
}

第二点:命名空间中的全局变量与局部变量

命名空间中定义的变量是全局变量,只有定义在函数里的变量才是局部变量。

namespace ycf
{int ret=10;int add(){int a=10;int b=10;return a+b;}
}
int main()
{return 0;
}

这段代码中ret变量虽然在命名空间当中但是他是属于全局变量的,在程序运行的过程中就已经创建成功了,而函数中的变量a b则是只有在调用函数add的时候才会进行创建属于局部变量。

命名空间的使用

第一种使用方法

第一种方法使用限定符::来访问命名空间中的变量。使用方法就是左边放置命名空间的名称右边放置你想要使用的命名变量,可以通过下面的例子来学习·:

#include<stdio.h>
namespace a
{int b = 10;int c = 20;double e = 1.0;double f = 2.0;
}int main()
{printf("%d\n", a::b);printf("%f\n", a::e);return 0;
}

我们这里想打印命名空间里面的变量b和e的值,那么我们这里就用printf函数,在限定符::的左边填入命名空间的名字,右边填入该命名空间中你想使用的变量或者类型的名字。

第二种使用方法

第二种方法需要使用using将命名空间中某个成员引入。我们上面讲过命名空间相当于是一个包装,将不同或者相同的变量或者类型装在一起,我们要想使用这些变量的话就得用限定符,但是有时候命名空间里面的变量我们会经常用到,不断使用第一种方法必定会让我们感到烦躁所以第二种方法就是直接使用,将命名空间中的特定变量解放出来,那么这里的方法就是这样:using 命名空间 具体对象名比如下面的代码:

#include<stdio.h>
namespace a
{int b = 10;int c = 20;double e = 1.0;double f = 2.0;int add(int x, int y){return x + y;}
}
using a::c;
using a::f;
int main()
{printf("%d\n", c);printf("%f\n", f);return 0;
}

通过这个代码大家应该就可以发现:我们将c和f释放之后,我们再使用命名空间里面的c和f的时就可以跟正常的变量一模一样了,但是这个方法大家要注意的一点就是我们这里将常用的东西进行展开之后我们在自己定义变量的时候就得避免重名。

第三种使用方法

第三种方法就是将命名空间全部释放,使用using namespace和该命名空间的名字便可以完成全部解放比如下面的代码:

#include<stdio.h>
namespace a
{int b = 10;int c = 20;double e = 1.0;double f = 2.0;int add(int x, int y){return x + y;}
}
using namespace a;
int main()
{printf("%d\n", c);printf("%f\n", f);printf("%d\n", add(10, 20));return 0;
}

这样我们在使用该命名空间里面的所有东西的时候都无需使用该限定符,但是这里大家要注意的一点就是:我们平时写代码做一些小的项目的时候可以这么使用,但是以后进入公司写一些大项目的时候就不要这么写了。

注意事项

第一点:没有名字的命名空间

大家可能会看到有关限定符的这种写法就是在限定符的左边什么都没有,比如说这样:printf("%d", ::a);我们知道限定符的左边填入的是命名空间的名字,那如果我们这里不填入呢?那他表示的意思就是我们要引入一个命名空间里面的一个变量或者类型,但是这个命名空间的名字为空,那大家这里想想,什么样的命名空间没有名字呢?那是不是就只能是全局变量了,所以当::左边为空的时候,右边的那些变量就表示的是没有被封装到命名空间里面的全局变量,比如说下面的代码:

#include<stdio.h>
namespace n1
{int a = 10;
}
namespace n2
{int a = 20;
}namespace n3
{int a = 30;
}namespace n4
{int a = 40;
}
int a = 50;
int main()
{int a = 60;printf("%d", ::a);return 0;
}

大家看看这段代码,我们这里要打印::a的值,但是我们左边没有给他的命名空间的名字,所以他这里就会在跑到我们的全局变量去找这里的a,因为我们这里在全局变量中定义了一个a,并将其值初始化为50,所以我们这里打印的值就是50在这里插入图片描述
但是大家有没有想过一个问题,为什么这里打印的为什么不是60呢?如果大家有这样的疑问的话就得把文章往上翻看到这么一句话:命名空间中定义的变量是全局变量,只有定义在函数里的变量才是局部变量。而这个::限定符他的作用就是访问命名空间里面的内容的,而命名空间里面的内容又全部都是全局变量不可能是局部变量,所以我们这里访问的值都是全局变量,所以当我们不给他要访问的命名空间的名字的时候,他要访问也是访问全局变量,所以这里打印的就是50,如果我们将这个全局变量的a去掉的话我们来看看会发生什么?在这里插入图片描述
我们发现他这里就直接报错了,所以这里大家要注意一下这种使用的情况。

第二点:局部优先原则

局部优先原则,我们在使用一个变量的时候,编译器会先在局部中查找这个变量,如果局部没有找到的话他就会在全局中查找这个变量比如说下面的这个代码:

#include<stdio.h>
int a = 10;
int main()
{int a = 20;printf("%d", a);return 0;
}

这段代码的运行结果就是20,因为在局部中定义了该名字的变量并将其值赋值为20,那么在c++中如果你想使用某个命名空间中的变量或者内容,但是该空间没有的话他是不会在其他地方寻找的比如说下面的代码:

#include<stdio.h>
namespace N
{int a = 10;
}
int b = 10;
int main()
{int b = 10;printf("%d", N::b);return 0;
}

我们在全局和局部中都定义了一个名为b的局部变量,但是我们在命名空间N中却没有定义该变量,那么我们下面要使用N中的变量b时,他就只会去命名空间N中查找该变量,如果没找到他也不会去其他的地方进行查找,而是直接报错,那么我们来看看这里代码的运行结果:
在这里插入图片描述
同样的道理我们再来看看下面的代码:

#include<stdio.h>
namespace N
{int a = 10;
}
int main()
{int a = 10;printf("%d", ::a);return 0;
}

我们这段代码是在命名空间N和局部中定义了一个变量a,但是没有在全局变量中定义一个变量a,那这时我们要打印全局变量中的变量a的话就只会在全局变量中查找,如果全局找不到也不会去局部和命名空间中查找而是直接报错,那么我们将这段代码运行之后就会报错:
在这里插入图片描述

第三点:命名空间和结构体

我们可以在命名空间里面定义一个结构体,就好比这样:

#include<stdio.h>
namespace N
{struct student{				int age;			char name[20];char sex[10];	};
}
int main()
{return 0;
}

但是我们在使用这个结构体的时候就得这样:先写struct +命名空间名+限定符+定义的结构体的类型名+结构体的名字,就好比如下这样:

#include<stdio.h>
namespace N
{struct student{				int age;			char name[20];char sex[10];	};
}
int main()
{struct N::student ycf = { 0 };return 0;
}

我们来看看这个能不能编译成功:
在这里插入图片描述
那么我们这里就是编译成功的,如果我们对这个结构体加上typedef进行重命名的话我们这里就得做出一些改变我们就可以将这里的struct去掉,将后面的定义的结构体的类型名改成新的名字即可,比如下面的代码:

#include<stdio.h>
namespace N
{typedef struct student{int age;char name[20];char sex[10];}student;
}
int main()
{N::student ycf = { 0 };return 0;
}

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

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

相关文章

【UI设计】可视化大屏原型设计

文章目录 一、墨刀中的几个可视化大屏框架原型 一、墨刀中的几个可视化大屏框架原型

【推理llm论文精度】DeepSeek-R1:强化学习驱动LLM推理能力飞跃

最近deepseek R1模型大火&#xff0c;正好复习一下他家的技惊四座的论文https://arxiv.org/pdf/2501.12948 近年来&#xff0c;大型语言模型&#xff08;LLM&#xff09;在推理能力上取得了显著进展&#xff0c;但如何进一步有效提升仍然是研究热点。DeepSeek-AI发布了 DeepS…

启明星辰发布MAF大模型应用防火墙产品,提升DeepSeek类企业用户安全

2月7日&#xff0c;启明星辰面向DeepSeek等企业级大模型业务服务者提供的安全防护产品——天清MAF&#xff08;Model Application Firewall&#xff09;大模型应用防火墙产品正式发布。 一个新赛道将被开启…… DeepSeek的低成本引爆赛道规模 随着DeepSeek成为当前最热的现象级…

day10-字符串

目录 字符串1、API 和 API 帮助文档2、String概述3、String构造方法代码实现 和 内存分析3.1 创建String对象的两种方式3.2 Java的内存模型 4、字符串的比较4.1 号的作用4.2 equals方法的作用 练习5、用户登录6、遍历字符串和统计字符个数7、字符串拼接和翻转8、较难练习-金额转…

使用git commit时‘“node“‘ 不是内部或外部命令,也不是可运行的程序

第一种&#xff1a; 使用git commit -m "xxx"时会报错&#xff0c;我看网上的方法是在命令行后面添加--no-verify&#xff1a;git commit -m "主题更新" --no-verify&#xff0c;但是不可能每次都添加。 最后解决办法是&#xff1a;使用git config --lis…

DeepSeek从入门到精通:全面掌握AI大模型的核心能力

文章目录 一、DeepSeek是什么&#xff1f;性能对齐OpenAI-o1正式版 二、Deepseek可以做什么&#xff1f;能力图谱文本生成自然语言理解与分析编程与代码相关常规绘图 三、如何使用DeepSeek&#xff1f;四、DeepSeek从入门到精通推理模型推理大模型非推理大模型 快思慢想&#x…

使用OBS推流,大华摄像头 srs服务器播放

说明&#xff1a; ffmpeg可以推流&#xff0c;但是是命令行方式不太友好&#xff0c;还可以使用主流的OBS开源推流软件&#xff0c;可从官网Open Broadcaster Software | OBS 下载最新版本&#xff0c;目前很多网络主播都是用它做直播。该软件支持本地视频文件以及摄像头推流。…

从大规模恶意攻击 DeepSeek 事件看 AI 创新隐忧:安全可观测体系建设刻不容缓

作者&#xff1a;羿莉&#xff08;萧羿&#xff09; 全球出圈的中国大模型 DeepSeek 作为一款革命性的大型语言模型&#xff0c;以其卓越的自然语言处理能力和创新性成本控制引领行业前沿。该模型不仅在性能上媲美 OpenAI-o1&#xff0c;而且在推理模型的成本优化上实现了突破…

mac下dify+deepseek部署,实现私人知识库

目前deepseek 十分火爆&#xff0c;本地部署实现私有知识库&#xff0c;帮助自己日常工作&#xff0c;上一篇使用工具cherry studio可以做到私人知识库。今天学习了一下&#xff0c;使用Dify链接deepseek&#xff0c;实现私人知识库&#xff0c;也非常不错&#xff0c;这里分享…

react概览webpack基础

react概览 课程介绍 webpack 构建依赖图->bundle 首屏渲染&#xff1a; 减少白屏等待时间 数据、结构、样式都返回。需要服务器的支持 性能优化 ***webpack干的事情 模块化开发 优势&#xff1a; 多人团队协作开发 可复用 单例&#xff1a;全局冲突 闭包 模块导入的顺序 req…

常见的九种二极管

常见的九种二极管 文章目录 常见的九种二极管1、普通二极管2、光电二极管&#xff08;LED&#xff09;3、变容二级管4、发光二极管5、恒流二极管6、快恢复二极管&#xff08;FRD&#xff09;7、肖特基二极管8、瞬态电压抑制二极管(TVS)9、齐纳二极管&#xff08;稳压&#xff0…

LabVIEW在呼吸机测试气体容量计算

在呼吸机测试中&#xff0c;精确测量气体容量变化是评估设备性能的关键步骤。通过监测呼吸机气道内的压力变化&#xff0c;并结合流阻和肺顺应性等参数&#xff0c;可以计算出单位时间内的气体容量变化。本案例基于LabVIEW实现该计算过程&#xff0c;以确保测试数据的准确性和一…

本地部署DeepSeek R1 + 界面可视化open-webui

本地部署DeepSeek R1 界面可视化open-webui ollama是物理机本地安装 open-webui是容器启动 另外&#xff0c;用docker 部署ollama也很方便ollama docker 安裝部署ollama ollama官网 安装 Linux上安装: curl -fsSL https://ollama.com/install.sh | sh使用命令行管理 拉…

使用C语言实现MySQL数据库的增删改查操作指南

使用C语言与MySQL数据库进行交互,通常涉及使用MySQL提供的C API库。这套API允许开发者在C/C++程序中执行SQL查询,从而实现数据库的增删改查操作。下面,我将详细介绍如何在C语言中实现这些基本操作。 准备工作 安装MySQL开发库:确保你的系统上安装了MySQL服务器以及MySQL开发…

在CT107D单片机综合训练平台上实现外部中断控制LED闪烁

引言 在单片机开发中&#xff0c;外部中断是一个非常重要的功能&#xff0c;它可以让单片机在检测到外部信号变化时立即做出响应。本文将详细介绍如何在CT107D单片机综合训练平台上使用外部中断来控制LED灯的闪烁。我们将使用两种不同的方式来实现这一功能&#xff1a;一种是在…

重磅发布!AI 驱动的 Java 开发框架:Spring AI Alibaba

*本文作者系阿里云云原生微服务技术负责人&#xff0c;Spring AI Alibaba 发起人彦林&#xff0c;望陶和隆基对可观测和 RocketMQ 部分内容亦有贡献。 * 摘要 随着生成式 AI 的快速发展&#xff0c;基于 AI 开发框架构建 AI 应用的诉求迅速增长&#xff0c;涌现出了包括 Lang…

防御保护作业二

拓扑图 需求 需求一&#xff1a; 需求二&#xff1a; 需求三&#xff1a; 需求四&#xff1a; 需求五&#xff1a; 需求六&#xff1a; 需求七&#xff1a; 需求分析 1.按照要求进行设备IP地址的配置 2.在FW上开启DHCP功能&#xff0c;并配置不同的全局地址池&#xff0c;为…

MapReduce简单应用(三)——高级WordCount

目录 1. 高级WordCount1.1 IntWritable降序排列1.2 输入输出格式1.3 处理流程 2. 代码和结果2.1 pom.xml中依赖配置2.2 工具类util2.3 高级WordCount2.4 结果 参考 本文引用的Apache Hadoop源代码基于Apache许可证 2.0&#xff0c;详情请参阅 Apache许可证2.0。 1. 高级WordCo…

智慧机房解决方案(文末联系,领取整套资料,可做论文)

智慧机房解决方案-软件部分 一、方案概述 本智慧机房解决方案旨在通过硬件设备与软件系统的深度整合&#xff0c;实现机房的智能化管理与服务&#xff0c;提升机房管理人员的工作效率&#xff0c;优化机房运营效率&#xff0c;确保机房设备的安全稳定运行。软件部分包括机房管…

(五)Spring Boot学习——spring security +jwt使用(前后端分离模式)

一定要熟悉spring security原理和jwt无状态原理&#xff0c;理解了才知道代码作用。 在 Spring Security JWT 认证流程中&#xff0c;通常的做法是&#xff1a; 用户提交用户名和密码Spring Security 认证管理器 (AuthenticationManager) 进行认证如果认证成功&#xff0c;生…