C语言sizeof的实战例子
实战例子1
经过这些例子,可以加深对sizeof,数组,数组名,取数组地址,地址加一,指针,指针加一的理解,一定要特别注意数组名在不同场景下的含义
一:数组名是数组首元素的地址
但是有2个例外
- sizeof(数组名):数组名表示整个数组,计算的是整个数组的大小,单位是字节
- &数组名:数组名表示整个数组,取出的是整个数组的地址,如&arr,当&arr+1时,打印的是相隔arr数组大小的地址
除此之外,所有的数组名都是数组首元素的地址
二:指针的大小:32位平台下都是4字节,64位平台下都是8字节
三: strlen -函数:求字符串长度的,找’\0’之前出现的字符个数;sizeof -操作符:算变量/类型所占内存大小,单位是字节
strlen函数原型:size_t strlen ( const char * str ); 参数是指向字符类型的指针
记住上面的规则后,让我们开始吧~
int a[ ] = { 1,2,3,4 }; //4*4=16
printf( "%d\n", sizeof(a)) ; //16 整个数组的大小是16printf("%d\n", sizeof(a + 0)); /*4或8 a + 0是第一个元素的地址,sizeof(a + 0)计算的是地址的大小,sizeof后面跟的不是单 个a,就不是一整个数组*/printf ("%d\n", sizeof(*a)); //4 *a是数组的第一个元素,sizeof(*a)计算的是第一个元素的大小printf ("%d\n", sizeof(a + 1)); //4或8 a + 1是第二个元素的地址,sizeof(a+1)计算的地址的大小printf ( "%d\n", sizeof(a[1])); //4 计算的是第二个元素的大小
printf ("%d\n", sizeof(&a)); //4/8 &a取出的是整个数组的地址,但也是地址,计算的是一个地址的大小printf ( "%d\n", sizeof(*&a)); //16 先取出整个数组的地址,再解引用,得到的还是整个数组,计算的数组的大小printf ("%d\n", sizeof(&a + 1)); /*4/8 &a得到一整个数组的地址,+1后跳过一整个数组,是数组最后一个元素后面的 空间的地址*/
printf ( "%d\n", sizeof(&a[0])); //4/8 第一个元素的地址printf ( "%d\n", sizeof(&a[0] + 1)); //4/8 第二个元素的地址
char arr[ ]= { ‘a’, ‘b’,‘c’, ‘d’ , ‘e’, ‘f’ };
printf ("%d\n", sizeof(arr)); //6 整个数组的大小为6printf ("%d\n", sizeof(arr + 0)); //4/8 首元素地址+0还是地址printf ("%d\n", sizeof(*arr)); //1 首元素地址解引用得到字符a,大小是1printf ("%d\n", sizeof(arr[1])); //1 第二个数组元素的大小printf ("%d\n", sizeof(&arr)); //4/8 一整个数组的地址printf ("%d\n", sizeof(&arr + 1)); //4/8 跳过一整个数组后的地址printf ("%d\n", sizeof(&arr[0]+ 1)); //4/8 &arr[0]是第一个元素的地址,+1后是第二个元素的地址
printf("%d\n",strlen(arr)); //随机值,从首元素地址开始找,strlen会一直找到'\0'为止printf ("%d\n", strlen(arr + 0)); //随机值,首元素地址加0还是首元素地址printf ("%d\n", strlen(*arr)); /*error,首元素地址解引用得到的是字符'a',ASCII码值是97,而strlen函数的参数是(char* str),接收的是地址*/printf ("%d\n", strlen(arr[1])); //error,同理,把字符'b'传过去也是出错printf ("%d\n", strlen(&arr)); /*随机值,取一整个数组的地址传给strlen函数时,也会被强制类型转换为char*类型,也是从首 元素地址开始找起*/printf ("%d\n", strlen(&arr + 1)); /*随机值-6,取一整个数组地址后+1,就跳到了该数组最后一个元素的后一个地址,相比从首元素开始找,此时直接跳过了数组的长度,所以要-6,但找的结果仍然是随机值*/printf ("%d\n", strlen(&arr[0]+ 1)); /*随机值-1,取首元素的地址后+1,得到第二个元素的地址,跳过了一个元素长度,所以要-1;*/
char arr[ ]= “abcdef” ;
内存存放形式:[a b c d e f \0]
printf ("%d\n", sizeof(arr)); //7 双引号""默认在最后加上'\0',sizeof会把'\0'也算上printf ("%d\n", sizeof(arr + 0)); //4/8 首元素地址+0还是地址printf ("%d\n", sizeof(*arr)); //1 首元素地址解引用得到字符'a','a'的大小printf ("%d\n", sizeof(arr[1])); //1 字符'b'的大小printf ("%d\n", sizeof(&arr)); //4/8 取一整个数组的地址printf ("%d\n", sizeof(&arr + 1)); //4/8 跳过一整个数组后还是地址printf ("%d\n", sizeof(&arr[0]+ 1)); //4/8 第二个元素的地址
printf ("%d\n", strlen(arr)); //6 strlen从首元素开始向后检索字符,遇到'\0'就停下,不包括'\0'printf ("%d\n", strlen(arr + 0)); //6 首元素地址+0还是从首元素开始检索printf ("%d\n", strlen(*arr)); //errorprintf ("%d\n", strlen(arr[1])); //errorprintf ("%d\n", strlen(&arr)); //6 一整个数组的地址,传给strlen也是从首地址开始printf ("%d\n", strlen(&arr + 1)); //随机值 取出一整个数组的地址后+1,跳过一整个数组,跳到'\0'的后一个地址,开始检索时不知什么时候会找到'\0'printf ("%d\n", strlen(&arr[0] + 1)); //5 从第二个元素开始找
实战例子2
char* p = “abcdef” ;
指针p指向一块连续的常量空间,[a b c d e f \0]
printf ("%d\n", sizeof(p)); //4/8 求的是p指针的大小printf ("%d\n", sizeof(p + 1)); //4/8 p指向的是字符a的地址,+1就指向字符b的地址,终究还是地址printf ("%d\n", sizeof(*p)); //1 p指针解引用得到字符a,大小为1printf ("%d\n", sizeof(p[0])); //1 p[0] == *(p+0),得到字符a,大小为1printf ("%d\n", sizeof(&p)); //4/8 取指针p自己的地址printf("%d\n", sizeof(&p + 1)); //4/8 跳过一个p的地址,即指针p的后一块地址空间printf("%d\n", sizeof(&p[0] + 1)); //4/8 &p[0]得到第一个元素的地址,+1得到第二个元素的地址
printf("%d \n", strlen(p)); //6 printf ("%d \n", strlen(p + 1)); //5 p指向第一个字符地址,+1后指向第二个字符地址printf ("%d\n", strlen(*p)); //errorprintf ("%d\n", strlen(p[0])); //errorprintf ("%d\n", strlen (&p)); //随机值 取p指针自身的地址,因为p占4/8个字节,从首字节开始找,不知何时才找到'\0'printf ("%d \n", strlen (&p + 1)); //随机值 从p指针最后一个字节的后一个地址开始找,也不知何时找到'\0',因为不确定p指针中有没有'\0',所以这个随机值并没有-1,跟上一个随机值没有联系printf ("%d\n", strlen ( &p[0] + 1)); //5 从第二个元素开始找
int a[ 3] [4]={ 0 };
a[0]:第一行一维数组的数组名
a[1]:第二行一维数组的数组名
a[2]:第三行一维数组的数组名
printf ("%d\n", sizeof(a)) ; //48 3*4*sizeof(int),sizeof里是单独的二维数组名,就表示一整个二维数组的大小printf ("%d\n", sizeof(a[0][0])); //4 第一行第一个元素值,整型元素大小是4printf ("%d\n", sizeof(a[0])); //16 a[0]表示整个第一行,数组名a[0]单独放在sizeof内部,sizeof(a[0])计算的就是第一行一维数组的大小!printf ("%d\n", sizeof(a[0]+ 1)); //4/8 a[0]作为数组名并没有单独出现在sizeof内,也没取地址,所以a[0]就是第一行第一个元素的地址,a[0]+1就是第一行第二个元素的地址printf ("%d\n", sizeof(*(a[0] + 1))); //4 第一行第二个元素值printf ("%d\n", sizeof(a + 1)) ; //4/8 a是二维数组的数组名,并没有取地址,也没有单独放在sizeof内,所以表示的是二维数组首元素的地址,即第一行的地址,a+1就是二维数组第二行的地址printf ("%d\n", sizeof(*(a + 1))); //16 因为*(a+1) == a[1],a[1]表示的是第二行的地址,由因为sizeof(a[1])是单独放在sizeof内部的,表示第二行一整个一维数组的地址,所以求的是一整个一位数组的大小printf ("%d\n", sizeof(&a[0] + 1)); //4/8 &a[0]+1 == a+1 a[0]是第一行的数组名,&a[0]取出的是第一行整个一维数组的地址,+1后就是第二行整个一维数组的地址printf ("%d\n", sizeof(*(&a[0]+ 1))); //16 *(&a[0]+1) == *(a+1) &a[0]+1得到的就是第二行整个一维数组的地址,解引用得到一整个第二行一维数组,所以大小是16printf ("%d\n", sizeof(*a)); //16 *a == *(a+0) == a[0],a是二维数组的数组名,并没有取地址,也没有单独放在sizeof内,表示第一行的地址,等于第一行数组名单独放到sizeof中,相当于求第一行整个一维数组的大小printf ("%d\n", sizeof(a[3])); //16 a[3]的类型是 int [4],其实是第四行的数组名(如果有的话),此时sizeof并不会真正去访问a[3]的地址,只是根据其类型计算出大小,sizeof()内部的表达式是不算的! 比如表达式:3+5 具有:1.值属性 -> 8 2.类型属性 -> int,sizeof就是推测出类型属性从而计算大小的
C语言sizeof的实战例子相关推荐
- C语言 sizeof 函数 - C语言零基础入门教程
目录 一.sizeof 函数简介 二.sizeof 函数实战 三.猜你喜欢 零基础 C/C++ 学习路线推荐 : C/C++ 学习目录 >> C 语言基础入门 一.sizeof 函数简介 ...
- C语言 sizeof 和 strlen 函数区别 - C语言零基础入门教程
目录 一.sizeof 函数与 strlen 函数区别 1.获取字符串长度 – 针对字符串 2.获取指针/数组长度 – 针对指针/数组 3.sizeof 获取内存大小 4.经典案例 二.猜你喜欢 零基 ...
- Go语言入门到实战——14.Go语言的协程机制以及并发机制
Go语言入门到实战--00主目录 在上一讲中我们学习了Go语言的包的知识已经依赖管理. 协程(groutine)是一种更加轻量级的线程(thread). 一.协程与线程得到比较 1.对于java而言, ...
- C语言sizeof的用法及注意事项
C语言sizeof的用法及注意事项 求普通变量的大小 #include <stdio.h> int main() {int a = 5;printf ("%d\n", ...
- 编程思想之c语言课程设计--管理系统例子
文章目录 前言 思路--用计算机"模拟世界" c语言 数据结构 算法 总结 例子--学生管理系统(控制台) 考虑 需求 分析 1.提供菜单 2.接收命令 3.添加学生信息 4.打印 ...
- R语言单变量分析实战:汇总统计(Summary Statistics)、频率表(Frequency Table)、图表(charts: boxplot、histogram、density)
R语言单变量分析实战:汇总统计(Summary Statistics).频率表(Frequency Table).图表(charts: boxplot.histogram.density) 目录
- R语言Box-Cox变换实战(Box-Cox Transformation):将非正态分布数据转换为正态分布数据、计算最佳λ、变换后构建模型
R语言Box-Cox变换实战(Box-Cox Transformation):将非正态分布数据转换为正态分布数据.计算最佳λ.变换后构建模型 目录
- R语言Goldfeld-Quandt检验实战:检验回归模型中是否存在异方差性(heteroscedasticity)、发生了异常差(heteroscedasticity)问题如何解决
R语言Goldfeld-Quandt检验实战:检验回归模型中是否存在异方差性(heteroscedasticity).发生了异常差(heteroscedasticity)问题如何解决 目录
- R语言NaN函数实战(计数、替换、删除)
R语言NaN函数实战(计数.替换.删除) 目录 R语言NaN函数实战(计数.替换.删除) #NA.NaN.Null区别?
最新文章
- 从hook007学习dll劫持自启动方式
- 从零入门 FreeRTOS操作系统之信号量
- Cannot add or update a child row: a foreign key constraint fails (`university`.`instructor`, CONSTRA
- mapreduce简单的gzip压缩
- mysql中的正向工程_Hibernate系列之正向工程
- win10偶然无法使用任务栏的问题解决办法
- mysql中的事务_mysql中的事务,你理解嘛?
- linux tcp自动重连,LabVIEW TCP/IP 断开重连问题
- [poj] 1236 networks of schools
- 31.go 函数式编程
- 1.ESP32c3 移植lvgl核心组件教程
- windows系统搭建图像识别开发环境
- WinRAR下载官方免费版
- 电子信息类包含计算机科学与技术么,电子信息类和计算机类有什么区别
- Rimworld Mod制作教程2 创建数据定义
- 基于Python的微信好友男女比例,区域排名,签名情感分析
- Windows 10 Version 2004 新功能盘点
- robocup3d 发布比赛版本
- 张丽俊最新演讲:要像竹子一样扎根,你终会一飞冲天
- Dijkstra算法讲解(通过边实现松弛)