一、变量的数据类型的含义
所有类型的数据存储在内存中,都是按照二进制格式存储的。内存中只知道有0和1,不知道它是什么类型的。
int、char、short属于整形,他们的存储方式(数转换为二进制往内存中放的方式)是相同的,只是内存格子大小不同(彼此叫二进制兼容格式);而float、double的存储方式彼此不同,和整形更不同。
#include <stdio.h>
int main(void)
{
int a=5;
printf("a=%d.\n",a); //5
printf("a=%f.\n",a); //奇怪的数字
}
int a=5; 时,编译器给a分配4个字节空间,并将5按照int类型的存储方式转化成二进制存到a所对应的内存空间去(a做左值);当printf去打印a的时候此时a做的是右值,printf内部的vsprintf函数会按照格式化字符串所代表的类型(%d,%f)去解析a所对应的内存空间,解析出的值用来输出。
总结
c 语言数据类型的本质是决定了这个数在内存中如何存储,决定了这个数如何转化为二进制。内存只是存储1010序列,而不管1010怎么解析。要求我们对数据类型不能瞎搞。
- 比如按照int类型存却按照float取 一定会出错。
- 按照int类型存却按照char类型取 有可能出错有可能不
- 按照short存却按照int类型取 有可能出错有可能不
- 按照float类型存却按照dobule类型取 一定会出错
int short char类型是兼容的 int float dobule数据类型是不兼容的。
二、指针的数据类型的含义
指针的本质是变量,指针就是指针变量。
一个指针涉及两个变量:一个是指针变量自己本身,一个是指针变量指向的那个变量。
int *p; :定义指针变量时,p是int 类型,p(p指向的那个变量)是int类型的。int *说白了就是指针类型,只要是指针类型都是占4个字节,解析方式都是按照地址方式来解释(意思是里面存的23个二进制加起来表示一个内存地址)的。
结论:所有指针类型(int *,double *,char *......)解析方式是相同的,都是地址。
对于指针所指向的那个变量来说,指针类型就很重要。指针指向的变量类型要取决于指针类型。
指针类型主要是为了其指向的变量所标记的。
#include <stdio.h>
int main(void)
{
int a=5;
float *p;
p=&a;
printf("*p=%f.\n",*p);
}
#include <stdio.h>
int main(void)
{
int a=5;
int *p1=&a;
float *p;
p=(float *)p1; //强制类型转换
printf("*p=%f.\n",*p);
}
指针的强制类型转换是有风险的
#include <stdio.h>
int main(void)
{
int a=5;
char *p1=&a;
printf("*p1=%d.\n",*p1);
short *p2=&a;
printf("*p2=%d.\n",*p2);
}
int和char类型都是整形,是兼容的,强制类型转换时有时候对有时候出错。int有两个字节char只有一个,int能表示的范围比int大,超过范围后int朝char转会出错。char往int就就不会出错(127)。short也有两个字节范围比char大还是比int小(65535)。
#include <stdio.h>
int main(void)
{
int a[2]={0x11223344,ox55667788,0};
int *p1=a;
char *p2=(char *)a;
printf("*p1=%x.\n",*p1);
printf("*p2=%x.\n",*p2);
printf("*p2=%x.\n",*(p2+1));
printf("*p2=%x.\n",*(p2+2));
}