c++ sizeof的实现
c++中的sizeof,可以通过以下宏定义实现。
#include <stdio.h> #define sizeof_T(T) ((size_t)((T*)0+1)) ///求类型的大小
#define sizeof_V(T) ((size_t)(&T+1)-(size_t)(&T)) ///求变量的大小 int main() {
int a=, b[]={};
printf("这个类型大小:%d \n这个类型单个变量的大小:%d \n这个类型数组变量的大小%d\n", sizeof_T(int), sizeof_V(a), sizeof_V(b));
return ;
}
那么为什么可以这样实现呢?
对于求类型大小的sizeof_T:
首先我们通过(T*)0得到一个指向00000000的指针,而且这个指针是int类型的,现在我们将这个指针+1。比如我们用一个int *p指针指向一块new int[10]的地址,那么此时很显然(p+1)-p==4而不是1,因为我们其实不是在地址上加1,而是让指针向前前进了一步,而这一步就是T这个类型的大小,也就是我们求的其实是指针步长。
可以通过以下程序发现这个特点,然后我们将00000000位置的指针向前移动一步,很显然,这个时候我们就得到了这个类型的大小。
#include <stdio.h>
#include <iostream>
using namespace std;
int main() {
char *p=new char[];
int *q=new int[];
printf("%p %p\n%p %p\n", p, p+, q, q+);
delete p;
delete q;
return ;
}
对于求变量大小的sizeof_V:
也是利用了指针步长的原理,这里值得注意的有两点.
一是因为这里我们不是类型,所以说不可能定义一个指向0的指针,只能将自己的地址拿来运算。
二是数组名有一个特性,对于int p[10];这个数组,&p+1的值并不是数组首地址加上指针步长,此时的步长是数组本身,也就是一步跨越了整个数组。
第二点可以通过以下程序来验证
#include <stdio.h>
int main() {
int p[];
printf("%p %p\n", p, &p+);
return ;
}
所以由以上特性我们就可以手动实现sizeof的功能了,说白了就是求指针步长。
我们既然知道了对数组来说&T+1相当于一步跨过整个数组,那么这是为什么呢,我由自己的做出相应的猜测,如有错误请在评论区指出。
对于int p[10];这个数组来说&p和什么相等呢?我测试的结果是&p==p[][10],也就是&p等于一个二维数组的数组名。也就是相当于将p提高了一个维度,原因就是如下的代码:
#include <stdio.h>
int main() {
int p[][], T[];
printf("%p %p\n%p %p\n", p, p+, T, &T+);
return ;
}
在运行了代码后你会发现p+1和&T+1的步长都是8。
那么其实就是对于数组,我们将他本身作为一个变量类型,就是相当于int [10]是一个变量类型。
再次感受到了那些大佬们的牛逼。
c++ sizeof的实现的更多相关文章
- 聊聊 C 语言中的 sizeof 运算
聊聊 sizeof 运算 在这两次的课上,同学们已经学到了数组了.下面几节课,应该就会学习到指针.这个速度的确是很快的. 对于同学们来说,暂时应该也有些概念理解起来可能会比较的吃力. 先说一个概念叫内 ...
- c/c++中关于sizeof、strlen的使用说明
sizeof: 一般指类型.变量等占用的内存大小(由于在编译时计算,因此sizeof不能用来返回动态分配的内存空间的大小) strlen: c字符串的长度(参数必须是字符型指针 char*,当数组名作 ...
- sizeof(转载)
原文地址:http://blog.sina.com.cn/s/blog_5da08c340100bmwu.html 转载至:http://www.cnblogs.com/wangkangluo1/ar ...
- C语言中的sizeof()
sizeof,一个其貌不扬的家伙,引无数菜鸟竟折腰,小虾我当初也没少犯迷糊,秉着"辛苦我一个,幸福千万人"的伟大思想,我决定将其尽可能详细的总结一下. 但当我总结的时候才发现,这个 ...
- 你必须知道的指针基础-4.sizeof计算数组长度与strcpy的安全性问题
一.使用sizeof计算数组长度 1.1 sizeof的基本使用 如果在作用域内,变量以数组形式声明,则可以使用sizeof求数组大小,下面一段代码展示了如何使用sizeof: ,,,,,}; int ...
- c++面试常用知识(sizeof计算类的大小,虚拟继承,重载,隐藏,覆盖)
一. sizeof计算结构体 注:本机机器字长为64位 1.最普通的类和普通的继承 #include<iostream> using namespace std; class Parent ...
- c语言 sizeof理解
1.基本数据类型 char :1 short:2 int 4 long 4 long long :8 float:4 double :8字节. 2.数组:对应的基本数 ...
- sizeof与strlen的区别
1 sizeof是操作符,而strlen是库函数: 2 sizeof的参数可以为任意变量或类型,而strlen必须以char*做参数,且字符串必须以‘/0’结尾: 3 数组名用作sizeof参数时不会 ...
- sizeof
一.sizeof使用的场合: 1.sizeof操作符的一个主要用途是与存储分配和I/O系统那样的例程进行通信.例如: void* malloc(size_t size); size_t fread(v ...
- strlen()和sizeof()求数组长度
在字符常量和字符串常量的博文里有提: 求字符串数组的长度 标准库函数strlen(s)可以返回字符串s的长度,在头文件<string.h>里. strlen(s)的判断长度的依据是(s[i ...
随机推荐
- 使用visual studio配置和运行《opengl圣经》的第一个案例
对vc++新手来说,想把opengl圣经里的教学案例运行起来还真不是一件容易的事情,而且并没有完整的操作流程教学,这里就总结一下吧: 先安装cmake,用于生成vs的工程文件,安装过程中选中“将目录添 ...
- B. Equal Rectangles
B. Equal Rectangles 给定4*N个数,是否能构成N个矩形 面积均相等 每次取两个大的,两个小的 #include<bits/stdc++.h> using namespa ...
- 安卓手机和ios手机上图片未设置宽度可能导致ios上图片贼小
处理方法: 设置固定宽度,高度自适应
- 学习日记17,、、通过反射获取model实体属性display的值
本来是想到网上直接找个用的,但是找的一些都不是我想要的,然后就参考自己摸索写了一个 这里的UserModel是我自己定义的一个实体类,代码就不用放出来了 var t = typeof(UserMode ...
- 运行job检验单元测试覆盖率
http://ns.jenkins.baidu.com/user/anyixing/my-views/view/Map_ut/job/poi-zhunru/ 1在http://ns.jenkins.b ...
- picker-view组件
picker-view组件,是一个页面上的滚动选择器: 如果想进行滚动:他的子元素必须是 picker-view-column 组件: picker-view-column组件:只是提供了一个可视 ...
- 剑指offer(2):字符串
C语言中的字符串 C语言中字符串的存储方式和数组类似,都是连续定长的内存块.字符串数组以\0结尾,所以会比正常数组多一位,char str3[5] = "1234"; //此处赋值 ...
- Vue Router 路由守卫:完整的导航解析流程
完整的导航解析流程 1 导航被触发. 2 在失活的组件里调用离开守卫. 3 调用全局的 beforeEach 守卫. 4 在重用的组件里调用 beforeRouteUpdate 守卫 (2.2+). ...
- gitee.ZC_blog快速方案
1. 1.1.改 hexo的配置文件中 gitee的路径 复制URL,到hexo的配置文件_config.yml …… deploy: type: git # type为git repo: https ...
- linux shell 中的数组的取值 遍历 替换 删除操作
引言 在Linux平台上工作,我们经常需要使用shell来编写一些有用.有意义的脚本程序.有时,会经常使用shell数组.那么,shell中的数组是怎么表现的呢,又是怎么定义的呢?接下来逐一的进行讲解 ...