嵌入式C语言学习记录(一)——数据类型

嵌入式C语言学习记录(一)

C语言数据类型

C语言的基 本 数 据 类 型 由 11 个 关 键 字 组 成 : int 、 long 、 short 、unsigned、char、float、double、signed、_Bool、_Complex和_Imaginary。

short、int、long、long long

C标准对基本数据类型只规定了允许的最小大小,在不同位数的系统中可能有所不一样。本文的程序均是在32位系统(PC和STM32)中测试。
范围大小:shor t<= int <= long <= long long
默认有符号:int、short、long、long long

short:全称为short int, C语言规定了short占用的存储空间不能多于int,在不同位数的系统中所能表达的范围不一样。stm32中所能表示的最大范围是[-32768,32767]

int(4字节):取值范围为[-2147483648,2147483647]。[-232-1,232-1]

long:全称为long int,占用的存储空间可能比int多(可以表示的范围大于或大于[-32768,32767]),stm32中所能表示的最大范围是[-2147483648,2147483647](-232-1——232-1)

long long:全称为long long int, 占用的存储空间可能比long多,可以表示的范围大于或大于[-2147483648,2147483647],stm32中所能表示的最大范围是[-2147483648,2147483647](-232-1——232-1)

signed、unsigned修饰字符强调是否带符号
signed:强调是带符号类型,short、short int、signed short、signed short int都表示同一种类型。
unsigned:强调是无符号类型

不同数据类型的要使用对应的打印格式,否则会产生格式转换导致观察的数据有误
在这里插入图片描述

/测试代码如下/

#include <limits.h>//该头文件中定义了各个类型的取值范围

	/*short类型
   * 2byte(字节)= 16bit(位),表示范围,[-32768,32767]*/
  printf("short:%d byte,[%d,%d]",sizeof(short),SHRT_MIN,SHRT_MAX);

  /*int类型
   * 4byte(字节)=32bit(位),表示范围[-2147483648,2147483647]*/
  printf("int:%d byte,[%d,%d]\r\n",sizeof(int),INT_MIN,INT_MAX);

  /*long int类型
   * 4byte(字节)=32bit(位),表示范围[-2147483648,2147483647]*/
  printf("long int:%d byte,[%ld,%ld]\r\n",sizeof(long int),LONG_MIN,LONG_MAX);

  /*long long int类型
   * 8byte(字节)=64bit(位),理论是应该是64位,
   * 实际上由于STM32芯片限制最大值为32位
   * 表示范围大小与long int类型相同,[-2147483648,2147483647]*/
  printf("long long int:%d byte,[%lld,%lld]\r\n",sizeof(long long int),LLONG_MIN,LLONG_MAX);
  
  /*unsigned short类型
   * 2byte(字节)= 16bit(位),表示范围,[65535]*/
  printf("unsigned short:%d byte,[%d,%d]",sizeof(short),0,USHRT_MAX);

  /*unsigned int类型
   * 4byte(字节)=32bit(位),表示范围[0,4294967295]*/
  printf("unsigned int:%d byte,[%d,%u]\r\n",sizeof(unsigned int),0,UINT_MAX);

  /*unsigned long int类型
   * 4byte(字节)=32bit(位),表示范围[0,4294967295]*/
  printf("unsigned int:%d byte,[%d,%lu]\r\n",sizeof(unsigned long int),0,ULONG_MAX);

  /*unsigned long long int类型
   * 8byte(字节)=64bit(位),理论是应该是64位,
   * 实际上由于STM32芯片限制最大值为32位
   * 表示范围大小与long int类型相同,[0,4,294,967,295]*/
  printf("unsigned int:%d byte,[%d,%llu]\r\n",sizeof(unsigned long long int),0,ULLONG_MAX);
  

C语言只规定了以上几种数据类型,在stm32中常用到的uint8_t、uint16_t、uint32_t等都是基于上述类型利用typedef重定义构造成的。在库文件stdint.h中可以查到

typedef unsigned           char uint8_t;
typedef unsigned short     int uint16_t;
typedef unsigned           int uint32_t;

char

char:该类型用于储存字符,但是从本质上看,char类型实际上是用特定的整数表示特定的字符。这也就是所谓的ASCLL编码。C语言把1字节定义为char类型占用的位(bit)数,因此无论是16位还是32位系统,都可以使用char类型。
取值范围:[-128,127]或者[0,255]。不同的编译器不一样,有些C编译器把char实现为有符号类型,则char可表示的范围是-128~127。而有些C编译器把char实现为无符号类型,那么char可表示的范围是0~255。可跳转到limits.h头文件查看定义的内容。(在CUBEIDE中有好几个不同路径的limits.h头文件,不方便跳转到真正定义的地方。在Keil5可以直接跳转到最底层的文件)
在这里插入图片描述

浮点类型——float、double

float:有效数据为6~7位
double:有效数据为15~16位
测试代码如下

#include<stdio.h>

void main()
{
	float a = 1.0123456890;
	double b = 1.01234567890123456789;
	printf("a = %.10f,b = %.20f",a,b);
}
输出结果为:a = 1.0123456717,b = 1.01234567890123460000

由此处可以看出,当数据超过规定的小数位之后就会发生数据错误,如果想在程序中想要表示更高精度的数据可以采用定点数学的方式对数据进行处理。

浮点数在内存中的存储方式也和整数不一样。

  • float: 1bit(符号位)+ 8bits(指数位) + 23bits(尾数位)
  • double: 1bit(符号位)+11bits(指数位)+ 52bits(尾数位)

浮点数的转换步骤分为如下三步:

  1. 将浮点数转换成二进制
  2. 用科学计数法表示二进制浮点数
  3. 计算指数偏移后的值(float偏移量值为127,double偏移量值为1023)

实例:float型的浮点数8.25在内存中的转换和表示

  1. 先将8.25转换为二进制 -> 1000.01
  2. 将转换的二进制用科学计数法表示 -> 1.00001 * (2^3)
  3. 计算指数偏移后的值 -> 127 + 3 = 130 -> 100000010

经过以上三步,就可以得出:

  1. 符号位:0
  2. 指数:100000010
  3. 小数:00001
  4. 所以float型的8.25在内存中的表示为:0 100000010 00001 00000000000000000 (32位表示)
    相比于整数,浮点数存入内存中花费了更多的步骤和时间,如果利用浮点数进行运算,花费的时间就需要更多了。

一个优秀的嵌入式工程师要尽量避免浮点运算!

布尔类型与其他类型

_Bool:C99新增关键字,布尔类型。布尔类型是无符号 int类型,所占用的空间只能储存0或1,用于表示逻辑值 true和false。必须设置C99标准才能实现(keil5默认是C89标准)。
_Complex和_Imaginary:分别是复数类型和虚数类型,在嵌入式中几乎不会运用到这种类型。

定义准确的数据类型对程序十分重要,合格的开发者应该选择准确的数据格式!

  • 14
    点赞
  • 22
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值