C++Primer 基本类型

欢迎阅读我的 【C++Primer】专栏

专栏简介:本专栏主要面向C++初学者,解释C++的一些基本概念和基础语言特性,涉及C++标准库的用法,面向对象特性,泛型特性高级用法。通过使用标准库中定义的抽象设施,使你更加适应高级程序设计技术。希望对读者有帮助!

在这里插入图片描述
在这里插入图片描述

目录

    • 2.1基本内置类型
      • 算术类型
      • 带符号类型和无符号类型
      • 类型转换
      • 含有无符号类型的表达式
      • 字面值常量
      • 字符和字符串字面值
      • 转义序列
      • 指定字面值的类型
      • 布尔字面值和指针字面值

2.1基本内置类型

C++定义了一套包括算术类型(arithmetic type〉和空类型(void)在内的基本数据类型。其中算术类型包含了字符、整型数、布尔值和浮点数。空类型不对应具体的值,仅用于一些特殊的场合,例如最常见的是,当函数不返回任何值时使用空类型作为返回类型。

算术类型

算术类型分为两类:整型(integral type,包括字符和布尔类型在内)和浮点型。算术类型的尺寸(也就是该类型数据所占的比特数)在不同机器上有所差别。表2.1列出了C++标准规定的尺寸的最小值,同时允许编详器赋予这些类型更大的尺寸。某一类型所占的比特数不同,它所能表示的数据范围也不一样。

表2.1: C++:算术类型

类型含义最小尺寸
boo1布尔类型未定义
char字符8位
wchar_t宽宇符16位
char16_tUnicode字符16位
char32_tUnicode字符32位
short短整型16位
int整型16位
long长整型32位
long long长整型64位
float单精度浮点6位有效数字
double双精度浮点10位有效数字
long double扩展精度浮点数10位有效数字

布尔类型(bool)的取值是真(true)或者假(false)。

C++提供了几种字符类型,其中多数支持国际化。基本的字符类型是char,一个char的空间应确保可以存放机器基本字符集中任意字符对应的数字值。也就是说,一个char的大小和一个机器字节一样。

其他字符类型用于扩展字符集,如wchar_t、char16_t、char32_Et。wchart类型用于确保可以存放机器最大扩展字符集中的任意一个字符,类型char16_t和
char32_t则为Unicode字符集服务(Unicode是用于表示所有自然语言中字符的标准)。

除字符和布尔类型之外,其他整型用于表示(可能不同尺寸的整数。C++语言规定-个int至少和一个short一样大,一个long至少和一个int一样大,一long 1ong
至少和一个long一样大。其中,数据类型longlong是在C++II中新定义的。

浮点型可表示单精度、双精度和扩展精度值。C++标准指定了一个浮点数有效位数的最小值,然而大多数编译器都实现了更高的精度。通常,float以1个字(32比特来表示,double以2个字(64比特来表示,long double以3或4个字(96或128比特)来表示。一般来说,类型float和double分别有7和16个有效位;类型long
double则常常被用于有特殊浮点需求的硬件,它的具体实现不同,精度也各不相同。

带符号类型和无符号类型

除去布尔型和扩展的字符型之外,其他整型可以划分为带符号的(signed)和无符号的(unsigned)两种。带符号类型可以表示正数、负数或0,无符号类型则仅能表示大于等于0的值。

类型int、short、long和long long都是带符号的,通过在这些类型名前添加unsigned就可以得到无符号类型,例如unsignedLong。类型unsignedint可以
缩写为unsigned。

与其他整型不同,字符型被分为了三种:char、signed char和unsigned char。

特别需要注意的是:类型char和类型signed char并不一样。尽管字符型有三种,但是字符的表现形式却只有两种,带符号的和无符号的。类型char实际上会表现为上述两种形式中的一种,具体是哪种由编译器决定。

无符号类型中所有比特都用来存储值,例如,8比特的unsignedchaz可以表示0至255区间内的值。

C++标准并没有规定带符号类型应如何表示,但是约定了在表示范围内正值和负值的量应该平衡。因此,8比特的signedchar理论上应该可以表示-127至127区间内的值,大多数现代计算机将实际的表示范围定为-128至127。

类型转换

对象的类型定义类对象能包含的数据和能参与的运算,其中一种运算被大多数类型支持,就是将对象从一种给定的类型转换(convert)为另一种类型。

当在程序的某处我们使用了一种类型而其实对象应该取另一种类型时,程序会自动进行类型转换。

当我们像下面这样把一种算术类型的值赋给另外一种类型时:

bool b = 42;// b为真
int i= b;//i的值为1
i = 3.14;
double pi = i;// pi的值为3.0
unsigned char c = -1; // 假设char 占 8 比特,c的值为 255
signed char c2 = 256// 假设char 占 8比特,c2的值是未定义的

类型所能表示的值的范围决定了转换的过程:

  • 当我们把一个非布尔类型的算术值赋给布尔类型时,初始值为0则结果为false,否则结果为true。
  • 当我们把一个布尔值赋给非布尔类型时,初始值为false则结果为0,初始值为true则结果为1。
  • 当我们把一个浮点数赋给敲数类型时,进行了近似处理。结果值将仅保留浮点数中小数点之前的部分。
  • 当我们把一个整数值赋给浮点类型时,小数部分记为0。如果该整数所占的空间超过了浮点类型的容量,精度可能有损失。
  • 当我们赋给无符号类型一个超出它表示范围的值时,结果是初始值对无符号类型表示数值总数取模后的余数。例如,8比特大小的unsignedchaz可以表示0至
    255区间内的值,如果我们赋了一个区间以外的值,则实际的结果是该值对256取模后所得的余数。因此,把-1赋给8比特大小的hnsignedchar所得的结果
    是255。
  • 当我们赋给带符号类型一个超出它表示范围的值时,结果是未定义的(undefined)。此时,程序可能继续工作、可能崩溃,也可能生成垃圾数据。

当在程序的某处使用了一种算术类型的值而其实所需的是另一种类型的值时,编译器同样会执行上述的类型转换。例如,如果我们使用了一个非布尔值作为条件,那么它会被自动地转换成布尔值,这一做法和把非布尔值赋给布尔变量时的操作完全一样:

int =42;
if(i)//i5条件的值将为true
    i = 0;

如果i的值为0,则条件的值为false;i的所有其他取值(非0)都将使条件为true。

以此类推,如果我们把一个布尔值用在算术表达式里,则它的取值非0即1,所以一般不宜在算术表达式里使用布尔值。

含有无符号类型的表达式

尽管我们不会故意给无符号对象赋一个负值,却可能(特别容易)写出这么做的代码。例如,当一个算术表达式中既有无符号数又有int值时,那个int值就会转换成无符号数。把int转换成无符号数的过程和把int直接赋给无符号变量一样:

unsigned u=10;
int i=  - 42;
std::cout<<i+i<<std::endl;//输出-84
std::cout<<u十i<<std::endl;//如果int占32位,输出4294967264

在第一个输出表达式里,两个(负)整数相加并得到了期望的结果。在第二个输出表达式里,相加前首先把整数-42转换成无符号数。把负数转换成无符号数类似于直接给无符号数赋一个负值,结果等于这个负数加上无符号数的模。

当从无符号数中减去一个值时,不管这个值是不是无符号数,我们都必须确保结果不能是一个负值:

unsigned u1=42,u2=10;
std::cout<<u1-u2<<estd::endl;//正确:输出32
std::cout<<u2-u1<<std::endl;//正确:不过,结果是取模后的值

无符号数不会小于0这一事实同样关系到循环的写法。

//错误:变量u永远也不会小于0,徨环条件一直成立
for(unsigned u = 10; u>=0;--u)
    std::cout<<u<<std::endl;

来看看当u等于0时发生了什么,这次迭代输出0,然后继续执行for语句里的表达式。表达式一u从u当中减去1,得到的结果-1并不满足无符号数的要求,此时像所有表示范围之外的其他数字一样,-1被自动地转换成一个合法的无符号数。假设int类型占32位,则当u等于0时,–u的结果将会是4294967295。

一种解决的办法是,用while语句来代典for语句,因为前者让我们能够在输出变量之前(而非之后)先减去1:

unsignedu=11;//确定要输出的最大数,从比它大1的数开始
while(u>0)
    --u;//先减1,这样最后一次选代时就会输出0
    std::cout<<u<<std::endl;
}

改写后的循环先执行对循环控制变量减1的操作,这样最后一次迭代时,进入循环的u值为1。此时将其减1,则这次迭代输出的数就是0:下一次再检验循环条件时,u的值等于0而无法再迹入循环。因为我们要先做减1的操作,所以初始化u的值应该比要输出的最大值大1。这里,u初始化为11,输出的最大数是10。

字面值常量

-个形如42的值被称作字面值常量(literal),这样的值一望而知。每个字面值常量都对应一种数据类型,字面值常量的形式和值决定了它的数据类型。整型和浮点型字面值我们可以将整型字面值写作十进制数、八进制数或十六进制数的形式。以0开头的整数代表八进制数,以0x或0X开头的代表十六进制数。例如,我们能用下面的任意一种形式来表示数值20:

20/*十进制*/024/*八进制+/0x14/*十六进制*/

整型字面值具体的数据类型由它的值和符号决定。默认情况下,十进制字面值是带符号数,八进制和十六进制字面值既可能是带符号的也可能是无符号的。十进制宇面值的类型是int、1long和longLong中尺寸最小的那个(例如,三者当中最小是int,当然前提是这种类型要能容纳下当前的值。八进制和十六进制字面值的类型是能容纳其数值的int、unsigned int、long、unsigned long、long long和unsigned long long中的尺寸最小者。如果一个字面值连与之关联的最大的数据类型都放不下,将产生错误。类型short没有对应的字面值。在表2.2(第37页中,我们将以后缀代表相应的字面值类型。

尽管整型字面值可以存储在带符号数据类型中,但严格来说,十进制字面值不会是负数。如果我们使用了一个形如-42的负十进制字面值,那个负号并不在字面值之内,它的作用仅仁是对字面值取负值而已。浮点型字面值表现为一个小数或以科学计数法表示的指数,其中指数部分用E或e标识:

3.14159 3.14159E0 0.0 e0 .001

默认的,浮点型字面值是一个double,我们可以使用表2.2中的后缀来表示其他浮点型。

字符和字符串字面值

由单引号括起来的一个字符称为chaz型字面值,双引号括起来的零个或多个字符则构成字符串型字面值。

'a' //字符字面值
“HelloWorld!““//字符定字面值

字符串字面值的类型实际上是由常量字符构成的数组(array)。编译器在每个字符串的结尾处添加一个空字符(“\0“),因此,字符略字面值的实际长度要比它的内容多1。例如,字面值「A“表示的就是单独的字符&,而字符串“A“则代表了一个字符的数组,该数组包含两个字符:一个是字母A、另一个是空字符。

如果两个字符串字面值位置紧邻且仅由空格、缩进和换行符分隔,则它们实际上是一个整体。当书写的字符串字面值比较长,写在一行里不太合适时,就可以采取分开书写的方式:

//分多行书写的字符定字面值
std::cout<<“areally,Feallylongstring1iteral“
“thatSpansEwo1ines“<<std::endl}

转义序列

有两类字符程序员不能直接使用:一类是不可打印(Cnonprintable)的字符,如退格或其他控制字符,因为它们没有可视的图符;另一类是在C++语言中有特殊含义的字符(单引号、双引号、问号、反斜线)。在这些情况下需要用到转义序列(escapesequence),转义序列均以反斜线作为开始,C++语言规定的转义序列包括:

描述符号描述符号描述符号
换行符\a横向制表符\t报警(响铃)符\a
纵向制表符\v退格符\b双引号"
反斜线\\问号?单引号
回车符\r进纸符 \f

在程序中,上述转义序列被当作一个字征使用:

std::cout << "\n";//转到新一行
std::cout << "\tHi!\n"; //输出一个制表符,输出“Hi!“,转到新一行

我们也可以使用泛化的转义序列,其形式是\x后紧跟1个或多个十六进制数字,或者\后紧跟1个、2个或3个八进制数字,其中数字部分表示的是字符对应的数值。假设使用的是Latin-1字符集,以下是一些示例:

\7(响铃) \12(换行符) \40(空格)
\0(空字符) \115(字符M) \x4d(字符M)

我们可以像使用普通字符那样使用C++语言定义的转义序列:

    std::cout<<“Hi \t x4dO\115!\n" ;//输出Hi MOM! ,转到新一行

std::cout<<‘\115’<<“\n"; //输出M,转到新一行

注意,如果反斜线\后面跟着的八进制数字超过3个,只有前3个数字与\构成转义序列。例如,“\x1234“表示2个字符,即八进制数123对应的字符以及字符4。相反,\x要用到后面跟着的所有数字,例如,“\x1234“表示一个16位的字符,该字符由这4个十六
进制数所对应的比特唯一确定。因为大多数机器的chaz型数据占8位,所以上面这个例子可能会报错。一般来说,超过8位的十六进制字符都是与表2.2中某个前缀作为开头的扩展字符集一起使用的。

指定字面值的类型

通过添加如表2.2中所列的前缀和后缀,可以改变整型、浮点型和字符型字面值的默认类型。

L'a'    // 宽字符型字面值,类型是wchar上
u8"hi!" //utf-8字符定字面值(utf-8用8位编码一个Unicode字符)
42ULL   //无符号整型字面值,类型是unsigned long long
1E-3F   //单精度浮点型字面值,类型是float
3.14159D//扩展精度浮点型字面值,类型是long double

表2.2:指定字面值的类型

字符串和字符字面值

前缓含义类型
uUnicode16宇律char16_t
UUnicode32字符char32_t
L宽字符wchar_t
u8UTF-8(仅用于字符串字面常量)char

整型字面值浮点型字面值

后缔最小匹配类型后级类型
u or Uunsignedf或Ffloat
l or Llongl 或 Llong double
ll or LLlong long

对于一个整型字面值来说,我们能分别指定它是否带符号以及占用多少空间。如果后缀中有U,则该宇面值属于无符号类型,也就是说,以U为后缀的十进制数、八进制数或十六进制数都将从unsigned int、unsigned long和unsigned long long中选择能匹配的空间最小的一个作为其数据类型,如果后缀中有L,则字面值的类型至少是long;如果后缀中有LL,则字面值的类型将是longlong和unsigned long long中的一种。显然我们可以将U与或LL合在一起使用。例如,以UL为后缀的字面值的数据类型将根据具体数值情况或者取unsigned 1ong,或者取unsigned long long。

布尔字面值和指针字面值

true和false是布尔类型的字面值:

bool test=false;

nullptr是指针字面值。

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

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

相关文章

纯前端实现将pdf转为图片(插件pdfjs)

需求来源 预览简历功能在移动端&#xff0c;由于用了一层iframe把这个功能嵌套在了app端&#xff0c;再用一个iframe来预览&#xff0c;只有ios能看到&#xff0c;安卓就不支持&#xff0c;查了很多资料和插件&#xff0c;原理基本上都是用iframe实现的。最终转换思路&#xf…

基于FPGA的出租车里程时间计费器

基于FPGA的出租车里程时间计费器 功能描述一、系统框图二、verilog代码里程增加模块时间增加模块计算价格模块上板视频演示 总结 功能描述 &#xff08;1&#xff09;&#xff1b;里程计费功能&#xff1a;3公里以内起步价8元&#xff0c;超过3公里后每公里2元&#xff0c;其中…

Unix 域协议汇总整理

Unix 域协议是一种用于同一台计算机上进程间通信&#xff08;IPC&#xff09;的技术。它提供了一种比基于网络的套接字更高效的方式来在本地进程中交换数据。Unix 域协议使用文件系统作为通信的媒介&#xff0c;并且只限于在同一台计算机上运行的进程之间进行通信。 Unix 域套接…

JVM学习:CMS和G1收集器浅析

总框架 一、Java自动内存管理基础 1、运行时数据区 运行时数据区可分为线程隔离和线程共享两个维度&#xff0c;垃圾回收主要是针对堆内存进行回收 &#xff08;1&#xff09;线程隔离 程序计数器 虚拟机多线程是通过线程轮流切换、分配处理器执行时间来实现的。为了线程切换…

1.C语言教程:历史、特点、版本与入门示例

目录 1.历史2.特点3.版本4.编译5.Hello World 示例 1.历史 本篇原文为&#xff1a;C语言教程&#xff1a;历史、特点、版本与入门示例。 更多C进阶、rust、python、逆向等等教程&#xff0c;可去此站查看&#xff1a;酷程网 C 语言的诞生源于 Unix 系统的开发需求。 1969 年…

lec7-路由与路由器

lec7-路由与路由器 1. 路由器硬件 路由器的硬件部分&#xff1a; 断电失去&#xff1a; RAM断电不失去&#xff1a;NVRAM&#xff0c; Flash&#xff0c; ROMinterface也算是一部分 路由器是特殊组件的计算机 console 口进行具体的调试 辅助口&#xff08;Auxiliary&…

spring防止重复点击,两种注解实现(AOP)

第一种&#xff1a;EasyLock 简介 为了简化可复用注解&#xff0c;自己实现的注解&#xff0c;代码简单随拿随用 使用方式 1.创建一个注解 Target(ElementType.METHOD) Retention(RetentionPolicy.RUNTIME) Documented public interface EasyLock {long waitTime() default …

Linux-Ubuntu之I2C通信

Linux-Ubuntu之I2C通信 一&#xff0c;I2C通信原理1.写时序2.读时序 二&#xff0c;代码实现三&#xff0c;显示 一&#xff0c;I2C通信原理 使用I2C接口驱动AP3216C传感器&#xff0c;该传感器能实现两个效果&#xff0c;一个是感应光强&#xff0c;另一个是探测物体与传感器…

音视频入门基础:MPEG2-PS专题(4)——FFmpeg源码中,判断某文件是否为PS文件的实现

一、引言 通过FFmpeg命令&#xff1a; ./ffmpeg -i XXX.ps 可以判断出某个文件是否为PS文件&#xff1a; 所以FFmpeg是怎样判断出某个文件是否为PS文件呢&#xff1f;它内部其实是通过mpegps_probe函数来判断的。从《FFmpeg源码&#xff1a;av_probe_input_format3函数和AVI…

框架模块说明 #09 日志模块_01

背景 日志模块是系统的重要组成部分&#xff0c;主要负责记录系统运行状态和定位错误问题的功能。通常&#xff0c;日志分为系统日志、操作日志和安全日志三类。虽然分布式数据平台是当前微服务架构中的重要部分&#xff0c;但本文的重点并不在此&#xff0c;而是聚焦于自定义…

【数据仓库】hadoop3.3.6 安装配置

文章目录 概述下载解压安装伪分布式模式配置hdfs配置hadoop-env.shssh免密登录模式设置初始化HDFS启动hdfs配置yarn启动yarn 概述 该文档是基于hadoop3.2.2版本升级到hadoop3.3.6版本&#xff0c;所以有些配置&#xff0c;是可以不用做的&#xff0c;下面仅记录新增操作&#…

算法题(25):只出现一次的数字(三)

审题&#xff1a; 该题中有两个元素只出现一次并且其他元素都出现两次&#xff0c;需要返回这两个只出现一次的数&#xff0c;并且不要求返回顺序 思路: 由于对空间复杂度有要求&#xff0c;我们这里不考虑哈希表。我们采用位运算的方法解题 方法&#xff1a;位运算 首先&#…

将机器学习预测模型融入AI agent的尝试(一)

将机器学习临床预测模型融入AI agent的尝试&#xff08;一&#xff09; 我主要是使用机器学习制作临床预测模型和相关的应用&#xff0c;最近考虑的事情是自己之前的的工作能不能和AI agent进行融合&#xff0c;将AI 对自然语言理解能力和预测模型的预测能力结合在一起&#x…

51单片机——按键实验

由于机械点的弹性作用&#xff0c;按键开关在闭合时不会马上稳定的接通&#xff0c;在断开时也不会一下子断开&#xff0c;因而在闭合和断开的瞬间均伴随着一连串的抖动。抖动时间的长短由按键的机械特性决定的&#xff0c;一般为 5ms 到 10ms&#xff0c;为了确保 CPU 对按键的…

电子邮件对网络安全的需求

&#xff08; 1&#xff09;机密性&#xff1a;传输过程中不被第三方阅读到邮件内容&#xff0c;只有真正的接收方才可以阅读邮件。&#xff08; 1.5 分&#xff09; &#xff08; 2&#xff09;完整性&#xff1a;支持在邮件传输过程中不被篡改&#xff0c;若发生篡改&#…

vue路由模式面试题

vue路由模式 1.路由的模式有哪些?有什么区别? history和hash模式 区别: 1.表现的形态不同: 在地址栏url中:hash模式中带有**#**号,history没有 2.请求错误时表现不同: 在hash模式中,对于404地址请求时,不会进行请求 但是在history模式中,对于404请求时,仍然会进行请求…

电子应用设计方案86:智能 AI背景墙系统设计

智能 AI 背景墙系统设计 一、引言 智能 AI 背景墙系统旨在为用户创造一个动态、个性化且具有交互性的空间装饰体验&#xff0c;通过融合先进的技术和创意设计&#xff0c;提升室内环境的美观度和功能性。 二、系统概述 1. 系统目标 - 提供多种主题和风格的背景墙显示效果&…

Python爬虫 - 豆瓣图书数据爬取、处理与存储

文章目录 前言一、使用版本二、需求分析1. 分析要爬取的内容1.1 分析要爬取的单个图书信息1.2 爬取步骤1.2.1 爬取豆瓣图书标签分类页面1.2.2 爬取分类页面1.2.3 爬取单个图书页面 1.3 内容所在的标签定位 2. 数据用途2.1 基础分析2.2 高级分析 3. 应对反爬机制的策略3.1 使用 …

西安电子科技大学初/复试笔试、面试、机试成绩占比

西安电子科技大学初/复试笔试、面试、机试成绩占比 01通信工程学院 02电子工程学院 03计算机科学与技术学院 04机电工程学院 06经济与管理学院 07数学与统计学院 08人文学院 09外国语学院 12生命科学与技术学院 13空间科学与技术学院 14先进材料与纳米科技学院 15网络与信息安…

多模态论文笔记——CogVLM和CogVLM2(副)

大家好&#xff0c;这里是好评笔记&#xff0c;公主号&#xff1a;Goodnote&#xff0c;专栏文章私信限时Free。本文详细介绍多模态模型的LoRA版本——CogVLM和CogVLM2。在SD 3中使用其作为captioner基准模型的原因和优势。 文章目录 CogVLM论文背景VLMs 的任务与挑战现有方法及…