C语言一些常用内存分配函数
首先看个问题程序(这里用的是TC编译器):
#include "stdlib.h"
#include "stdio.h"
void main()
{
int *i;
i=(int
*)malloc(sizeof(int));
*i=1;
*(i+1)=2;
printf("%x|%d\n",i,*i);
printf("%x|%d",i+1,*(i+1));
}
输出的结果是:
8fc|1
8fe|2
这个程序编译通过,运行正常,说它有问题,问题出在哪呢?
首先通过malloc,建了一个大小为2的堆,
i指向的地址是8fc,i+1指向的地址是8fc+sizeof(int)=8fe
但是地址8fe是不受保护的,因为它不是机器分配给i+1的,随时会被其他变量占用。
正确的做法是
#include "stdlib.h"
#include "stdio.h"
void main()
{
int *i;
i=(int
*)malloc(sizeof(int));
*i=1;
i=(int
*)realloc(i,2*sizeof(int));//这里用到了realloc函数,重新分配内存
*(i+1)=2;
printf("%x|%d\n",i,*i);
printf("%x|%d",i+1,*(i+1));
}
realloc
可以对给定的指针所指的空间进行扩大或者缩小,无论是扩张或是缩小,原有内存的中内容将保持不变。
当然,对于缩小,则被缩小的那一部分的内容会丢失。
realloc
并不保证调整后的内存空间和原来的内存空间保持同一内存地址。但是会尽量去在原来的基础上扩容。当原来的空间不足以容纳的时候会在新的内存扩容且把原来的数据迁移过去,但是要记得top指针的改变。
相反,realloc 返回的指针很可能指向一个新的地址。
所以,在代码中,我们必须将realloc返回的值,重新赋值给 p :
p = (int *) realloc (p, sizeof(int) *15);
甚至,你可以传一个空指针(0)给 realloc ,则此时realloc 作用完全相当于malloc。
int* p = (int *) realloc (0,sizeof(int) * 10);
//分配一个全新的内存空间,
这一行,作用完全等同于:
int* p = (int *) malloc(sizeof(int) * 10);
『附注:TC编译器里sizeof(int)=2,VC里面sizeof(int)=4;
char型在两个编译器里是一样的,都是1个字节(8位)』
calloc与malloc相似,参数nelem为申请地址的单位元素长度,elsize为元素个数,如:
char* p;
p=(char*)calloc(sizeof(char),20);
这个例子与上一个效果相同
realloc
可以对给定的指针所指的空间进行扩大或者缩小,无论是扩张或是缩小,原有内存的中内容将保持不变(free掉)。
当然,对于缩小,则被缩小的那一部分的内容会丢失。
realloc 并不保证调整后的内存空间和原来的内存空间保持同一内存地址。相反,realloc 返回的指针很可能指向一个新的地址。
所以,在代码中,我们必须将realloc返回的值,重新赋值给 p :
p = (int *) realloc (p, sizeof(int) *15);
个人总结起来其实realloc函数就两点:
- realloc 并不保证调整后的内存空间和原来的内存空间保持同一内存地址。但是会尽量去在原来的基础上扩容。当原来的空间不足以容纳的时候会在新的内存扩容且把原来的数据迁移过去,但是要记得top指针的改变。
- 原有内存的中内容将保持不变(free掉),也就是说不用手动去free掉
C语言一些常用内存分配函数的更多相关文章
- C语言之内存分配函数
#include <stdio.h> #include <stdlib.h> #include <string.h> int main() { /********* ...
- Linux内核中常见内存分配函数(二)
常用内存分配函数 __get_free_pages unsigned long __get_free_pages(gfp_t gfp_mask, unsigned int order) __get_f ...
- Linux内核中常见内存分配函数【转】
转自:http://blog.csdn.net/wzhwho/article/details/4996510 1. 原理说明 Linux内核中采用了一种同时适用于32位和64位系统的内存分页 ...
- Linux内核中常见内存分配函数
1. 原理说明 Linux内核中采用了一种同时适用于32位和64位系统的内存分页模型,对于32位系统来说,两级页表足够用了,而在x86_64系统中,用到了四级页表,如图2-1所示.四级页表分 ...
- C语言内存分配函数malloc——————【Badboy】
C语言中经常使用的内存分配函数有malloc.calloc和realloc等三个,当中.最经常使用的肯定是malloc,这里简单说一下这三者的差别和联系. 1.声明 这三个函数都在stdlib.h库文 ...
- C语言中的内存分配与释放
C语言中的内存分配与释放 对C语言一直都是抱着学习的态度,很多都不懂,今天突然被问道C语言的内存分配问题,说了一些自己知道的,但感觉回答的并不完善,所以才有这篇笔记,总结一下C语言中内存分配的主要内容 ...
- 【转】【C/C++】内存分配函数:malloc,calloc,realloc,_alloca
转自:http://www.cnblogs.com/particle/archive/2012/09/01/2667034.html#commentform malloc: 原型:extern voi ...
- Win内存分配函数(GlobalAlloc/HeapAlloc/LocalAlloc/VirtualAlloc)
Win内存分配函数(GlobalAlloc/HeapAlloc/LocalAlloc/VirtualAlloc) 来源:http://blog.csdn.net/chunyexiyu/article/ ...
- C语言数据在内存分配
一个由C/C++编译的程序占用的内存分为以下几个部分 1.栈区(stack)— 程序运行时由编译器自动分配,存放函数的参数值,局部变量的值等.其操作方式类似于数据结构中的栈.程序结束时由编译器自动释放 ...
随机推荐
- mac 系统开发android,真机调试解决方案
1.确保你的android设备真正链接到电脑上了,我在这里遇到过坑,弄了好久,才发现能充电的线,确无法传递数据过去.所以不要以为随便拿一根线,能充电,就可以传递数据了,我就是这么傻傻的拿了根不能用的数 ...
- swift 命令行工具初探
亲爱的同学们好,今天我们要介绍这么一个东西.相信有过解释型语言(PHP,Ruby,等)使用经验的同学会更加熟悉,就是 Swift 也为我们提供了命令行运行工具,俗称 REPL.好了,我们进入正题,在安 ...
- 在线演示平台 | Highcharts中文网 (曲线图、区域图、3D图等等)
http://www.hcharts.cn/ 在线演示平台 | Highcharts中文网
- 54.xilinx_modelsim仿真错误1
在仿真DDR3核时,用modelsim编译时会出现下面错误 Error:can't read "env(XILINX)":no such variable 原因:在.do文件中指定 ...
- 29.DDR2问题1仿真模型文件
在使用modelsim仿真DDR2时,一般我们会用美光网站上下载的DDR2仿真模型.仿真模型文件一般有ddr2_module.v,ddr2.v,ddr2_mcp.v,ddr2_parameters.v ...
- Linux 删除mysql数据库失败的解决方法
使用命令:drop database xxx:删除本数据库时却删除失败,系统提示出现了错误,错误代码为: ERROR 1010 (HY000): Error dropping database(can ...
- 20145129 《Java程序设计》第5周学习总结
20145129 <Java程序设计>第5周学习总结 教材学习内容总结 语法与继承架构 使用try.catch Java中所有错误都会被打包为对象,可以尝试(try)捕捉(catch)代表 ...
- 或许你不知道(2):LinkedList
一,基本的存储结构及数据存取 LinkedList与ArrayList同属List的范畴,ArrayList实现了RandomAccess接口,通过索引随机访问效率较高,而LinkedList提供了直 ...
- 用PHP对数据库数据进行删除
显示页面: <body> <table width="100%" border="1" cellpadding="0" c ...
- yield curve
1. A yield curve can be built using deposit rates, swap rates, and future/forward rates 2. A par-cou ...