返回顶部
首页 > 资讯 > 后端开发 > 其他教程 >C++深入分析数据在内存中的存储形态
  • 379
分享到

C++深入分析数据在内存中的存储形态

C++数据在内存中的存储C++数据存储 2023-01-06 09:01:24 379人浏览 薄情痞子
摘要

目录一.整形在内存中的存储1.原码-反码-补码2.大小端介绍二.浮点型在内存中的存储1.浮点型的存储2.浮点型的读取一.整形在内存中的存储 1.原码-反码-补码 计算机中的整数有三种

一.整形在内存中的存储

1.原码-反码-补码

计算机中的整数有三种2进制表示方法,即原码、反码和补码。

三种表示方法均有符号位和数值位两部分,符号位都是用0表示“正”,用1表示“负”。

(1)正数的原反补码

将原码转为二进制得到的就是该正数的原码

例:

int a=10;
//00000000 00000000 00000000 00001010 --原码

正数的原反补码都相同,所以:

int a=10;
//00000000 00000000 00000000 00001010 --原码
//00000000 00000000 00000000 00001010 --反码
//00000000 00000000 00000000 00001010 --补码

(2)负数的原反补码

负数的符号位(最高位)用‘1’来表示,所以将负数转为二进制后加上符号位‘1’就是负数的原码

例:

int a=-10;
//10000000 00000000 00000000 00001010 --原码

反码:符号位不变,其他位按位取反

int a=-10;
//11111111 11111111 11111111 11110101 --反码

补码:反码加一

int a=-10;
//11111111 11111111 11111111 11110110 --补码

综合:

int a=-10;
//10000000 00000000 00000000 00001010 --原码
//11111111 11111111 11111111 11110101 --反码(符号位不变,按位取反)
//11111111 11111111 11111111 11110110 --补码(反码加一)

对于整形来说:数据存放内存中其实存放的是补码。为什么呢?

在计算机系统中,数值一律用补码来表示和存储。原因在于:

1.使用补码,可以将符号位和数值域统一处理;

2.同时,加法和减法也可以统一处理(CPU只有加法器)此外,补码与原码相互转换,其运算过程是相同的,不需要额外的硬件电路。

2.大小端介绍

我们可以通过编译器(本篇采用vs2022)来查看一下在内存中的数据

引例:

#include <stdio.h>
int main()
{
    int a = 10;
    return 0;
}
//a=10;
//00000000 00000000 00000000 00001010 --原码
//00000000 00000000 00000000 00001010 --反码
//00000000 00000000 00000000 00001010 --补码
//00 00 00 0a --16进制

步骤:

  • 按F11键逐步调试到a变量创建完成;
  • 单击“调试”菜单,选择“窗口”命令,在子菜单中选择“内存”命令。
  • 最后,在打开的“内存”窗口中搜索框输入“&a”,即可查看。

可以看到a的地址是倒着存放的,但有不完全倒着放,这是为什么呢?

这就和大小端存储模式有关系了

大端存储模式:是指数据的低位保存在内存的高地址中,而数据的高位,保存在内存的低地址中;

小端存储模式:是指数据的低位保存在内存的低地址中,而数据的高位,,保存在内存的高地址中。

为什么会有大小端呢?

这是因为在计算机系统中,我们是以字节为单位的,每个地址单元都对应着一个字节,一个字节为8 bit。但是在C语言中除了8 bit的char之外,还有16 bit的short型,32 bit的long型(要看具体的编译器),另外,对于位数大于8位的处理器,例如16位或者32位的处理器,由于寄存器宽度大于一个字节,那么必然存在着一个如何将多个字节安排的问题。因此就导致了大端存储模式和小端存储模式。

二.浮点型在内存中的存储

我们先来看一段代码,来猜下结果:

引例:

#include <stdio.h>
int main()
{
	int a = 9;
	float* p = (float*)&a;
	printf("a的值为:%d\n", a);
	printf("*p的值为:%f\n", *p);
	*p = 9.0;
	printf("a的值为:%d\n", a);
	printf("*p的值为:%f\n", *p);
	return 0;
}

答案:

是不是很出乎意料?下面跟我一起来解开心中的奥秘吧!

1.浮点型的存储

根据国际标准IEEE(电气和电子工程协会) 754,任意一个二进制浮点数V可以表示成下面的形式:

  • (-1)^S * M * 2^E
  • (-1)^s表示符号位,当s=0,V为正数;当s=1,V为负数。
  • M表示有效数字,大于等于1,小于2。
  • 2^E表示指数位。

例:

(1)十进制的9.0,写成二进制是 1001.0 ,相当于 1.001×2^3。S=0,M=1.001,E=3。

(2)十进制的-5.0,写成二进制是 -101.0 ,相当于 -1.01×2^2 。S=1,M=1.01,E=2

IEEE 754规定:

对于32位的浮点数,最高的1位是符号位s,接着的8位是指数E,剩下的23位为有效数字M。

对于64位的浮点数,最高的1位是符号位S,接着的11位是指数E,剩下的52位为有效数字M。

IEEE 754对有效数字M和指数E,还有一些特别规定。

前面说过, 1≤M<2 ,也就是说,M可以写成 1.xxxxxx 的形式,其中xxxxxx表示小数部分。

IEEE 754规定,在计算机内部保存M时,默认这个数的第一位总是1,因此可以被舍去,只保存后面的xxxxxx部分。比如保存1.01的时候,只保存01,等到读取的时候,再把第一位的1加上去。这样做的目的,是节省1位有效数字。以32位浮点数为例,留给M只有23位,将第一位的1舍去以后,等于可以保存24位有效数字。

至于指数E,情况就比较复杂。

首先,E为一个无符号整数(unsigned int)

这意味着,如果E为8位,它的取值范围为0~255;如果E为11位,它的取值范围为0~2047。但是,我们知道,科学计数法中的E是可以出现负数的,所以IEEE 754规定,存入内存时E的真实值必须再加上一个中间数,对于8位的E,这个中间数是127;对于11位的E,这个中间

数是1023。比如,2^10的E是10,所以保存成32位浮点数时,必须保存成10+127=137,即

10001001

例如:

float a = -9.5;

-9.5(十进制)--1001.1(二进制)--1.0011*2^3

S=1, M=1.0011, E=3

a = -9.5;
//s=1,M=1.0011,E=3;
//1 10000010     00110000000000000000000
//S E=3+127=130  M=1.0011 最前面的1被舍弃

2.浮点型的读取

浮点型的读取根据指数E的不同分三种情况:

(1)E不全为0或不全为1

这时,浮点数就采用下面的规则表示,即指数E的计算值减去127(或1023),得到真实值,再将

有效数字M前加上第一位的1。就是将存储步骤反过来执行。

(2)E全为0

这时,浮点数的指数E等于1-127=-126(或者1-1023=-1022)即为真实值,

有效数字M不再加上第一位的1,而是还原为0.xxxxxx的小数。这样做是为了表示±0,以及接近于0的很小的数字。

(3)E全为1

这时,如果有效数字M全为0,表示±无穷大(正负取决于符号位s)。

最后,讲解一下引例:

#include <stdio.h>
int main()
{
	int a = 9;  --1001(二进制序)
    //整形数据:a以补码存储在内存中:
    //00000000 00000000 00000000 00001001 --补码
	float* p = (float*)&a;
    //打印结果为9
	printf("a的值为:%d\n", a);  
    //以浮点型打印时,读取整形数据a的地址
    //S=0 E=00000000 M=000000……000001001 E全为0,是一个无限接近于0的数,所以打印结果为0.000000
	printf("*p的值为:%f\n", *p);
	*p = 9.0;   --1001(二进制序)
    //a的内存发生改变,由整形变为浮点型:
    //S=0,E=3 M=00100……0000
    //以浮点型存储在内存中:0 10000010 0010000……000000
	printf("a的值为:%d\n", a);  //以整形读取a,打印结果为1091567616
	printf("*p的值为:%f\n", *p);  //打印结果为9.000000
	return 0;
}

到此这篇关于c++深入分析数据在内存中的存储形态的文章就介绍到这了,更多相关C++数据在内存中的存储内容请搜索编程网以前的文章或继续浏览下面的相关文章希望大家以后多多支持编程网!

--结束END--

本文标题: C++深入分析数据在内存中的存储形态

本文链接: https://lsjlt.com/news/176903.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

猜你喜欢
  • C++深入分析数据在内存中的存储形态
    目录一.整形在内存中的存储1.原码-反码-补码2.大小端介绍二.浮点型在内存中的存储1.浮点型的存储2.浮点型的读取一.整形在内存中的存储 1.原码-反码-补码 计算机中的整数有三种...
    99+
    2023-01-06
    C++数据在内存中的存储 C++数据存储
  • C语言数据在内存中的存储流程深入分析
    目录前言类型的基本分类整型浮点数自定义类型整型在内存中的存储原码、反码、补码大端和小端如何判断编译器是大端还是小端浮点数在内存中的存储总结前言 C语言中有char、short、int...
    99+
    2022-11-13
    C语言数据在内存中的存储 C语言数据存储
  • C++浅析数据在内存中如何存储
    目录一、数据类型二、原码反码补码三、大小端整型提升一、数据类型 数据类型有7种:    char         ...
    99+
    2022-11-13
    C++数据存储 C++数据在内存中存储
  • C语言数据在内存中的存储
    这篇文章主要介绍了C语言数据在内存中的存储,具有一定借鉴价值,感兴趣的朋友可以参考下,希望大家阅读完这篇文章之后大有收获,下面让小编带着大家一起了解一下。数据类型详细介绍在前面C语言基础概览中,已经提到过了基本的C语言内置类型,但C语言的数...
    99+
    2023-06-15
  • C语言详细分析浮点数在内存中的储存
    目录浮点数的储存格式初步了解深入探究E不全为0或不全为1E全为0E全为1浮点数的储存格式 初步了解 首先让我们通过一段代码来认识一下浮点型和整型的区别: int main() { ...
    99+
    2024-04-02
  • C#指针内存控制Marshal内存数据存储原理分析
    目录了解内存的原理了解指针的原理1、通过指针修改 值类型 的变量数据2、通过指针修改 引用类型 的变量数据3、通过指针修改 数组对象 的成员数据4、通过指针修改 类对象 的字段数据5...
    99+
    2023-02-26
    C#指针 指针Marshal C#内存数据存储原理
  • C语言数据在内存中的存储详解
    目录文章摘要一、C语言的数据类型数据类型基本分为: 二、隐式类型转换1.什么是隐式类型转换2.整型提升 3.类型转换三、机器大小端1.什么是大小端2.大小端在截断的应用3....
    99+
    2024-04-02
  • C语言中数据在内存如何存储
    目录数据类型类型的基本归类整形有符号数和无符号数是否char 等于signed char呢?浮点型构造类型(自定义类型)指针类型空类型整形在内存中的存储原码,反码,补码正整数负整数大...
    99+
    2024-04-02
  • 深度解析C语言中数据的存储
    目录前言数据类型介绍类型的基本归类整型家族浮点数家族构造类型指针类型空类型前言 在VS编译器里有release和debug两种形式,debug包含调试信息,release不包含调试信...
    99+
    2024-04-02
  • 深入了解C语言中的动态内存分配
    目录什么是动态内存分配如何进行动态内存分配首先我要介绍两个函数 malloc 和 free第二个开辟空间的动态内存分配的函数 calloc大小修改函数realloc今天我们来学习一下...
    99+
    2024-04-02
  • C语言数据在内存中是怎样存储的
    这篇文章主要介绍“C语言数据在内存中是怎样存储的”,在日常操作中,相信很多人在C语言数据在内存中是怎样存储的问题上存在疑惑,小编查阅了各式资料,整理出简单好用的操作方法,希望对大家解答”C语言数据在内存中是怎样存储的”的疑惑有所帮助!接下来...
    99+
    2023-06-08
  • C语言中数据是如何存储在内存中的
    目录前言‍数据类型介绍‍整形数据在内存中存储‍浮点型数据在内存存储前言 在计算机内存中,数据的存储方式都是以0和1的形式存储,也就是二进制的形式,数据是如何向...
    99+
    2024-04-02
  • C语言中数据在内存中是怎么存储的
    本篇文章为大家展示了C语言中数据在内存中是怎么存储的,内容简明扼要并且容易理解,绝对能使你眼前一亮,通过这篇文章的详细介绍希望你能有所收获。数据类型常见的数据类型常见的数据类型字节char字符数据类型1short短整型2int整形4long...
    99+
    2023-06-22
  • C语言数据(整数、浮点数)在内存中的存储
    本篇主要讨论:整数、浮点数在内存中是怎么保存的! 数据类型详细介绍 在前面C语言基础概览中,已经提到过了基本的C语言内置类型,但C语言的数据类型有无数种~ 但是可以把这些类型分为几个...
    99+
    2024-04-02
  • C语言编程数据在内存中的存储详解
    目录变量在计算机中有三种表示方式,原码反码,补码原码反码补码总结一下浮点数在内存的储存C语言中,有几种基本内置类型。 int unsigned int signed int cha...
    99+
    2024-04-02
  • 关于C语言中数据在内存中的存储详解
    目录前言一、数据类型介绍1.类型的基本归类1.整形家族2.浮点型家族3.构造类型4.指针类型5.空类型二、整型在内存中的存储1.原码、反码、补码2.内存中怎样存储3.大小端字节序1....
    99+
    2024-04-02
  • C++浮点数在内存中的存储详解
    目录前言:浮点数的表示形式浮点数存储模型有效数字M指数E例题讲解总结前言: 我们在码代码的时候,经常遇到过以整数形式存入,浮点数形式输出;或者浮点数形式存入整数形式输出。输出的结果往...
    99+
    2024-04-02
  • C语言中数据的存储举例分析
    这篇文章主要介绍“C语言中数据的存储举例分析”,在日常操作中,相信很多人在C语言中数据的存储举例分析问题上存在疑惑,小编查阅了各式资料,整理出简单好用的操作方法,希望对大家解答”C语言中数据的存储举例分析”的疑惑有所帮助!接下来,请跟着小编...
    99+
    2023-06-25
  • C语言中数据存储的示例分析
    这篇文章主要介绍了C语言中数据存储的示例分析,具有一定借鉴价值,感兴趣的朋友可以参考下,希望大家阅读完这篇文章之后大有收获,下面让小编带着大家一起了解一下。(壹)大端小端藏端倪1.1  什么是大端小端大端(存储)模式,是指数据的低...
    99+
    2023-06-29
  • C++虚函数表与类的内存分布深入分析理解
    目录不可定义为虚函数的函数将析构函数定义为虚函数的作用虚函数表原理继承关系中虚函数表结构多重继承的虚函数表多态调用原理对齐和补齐规则为什么要有对齐和补齐资源链接不可定义为虚函数的函数...
    99+
    2022-11-13
    C++ 虚函数表 C++ 类的内存分布
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作