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)— 程序运行时由编译器自动分配,存放函数的参数值,局部变量的值等.其操作方式类似于数据结构中的栈.程序结束时由编译器自动释放 ...
随机推荐
- OpenStack: OVS安装
> OVS安装:1. Install the Open vSwitch plug-in and its dependencies:# apt-get install \neutron-plugi ...
- vs2010 开发过程中调试时 有错误不中断
出现这个的原因是调试的设置有问题,修改下设置就好了. 修改方法:点击上边工具栏中 调试--异常 出现以下页面,把引发那列复选框全部勾上,点击确定就好了.
- Thread系列——Thread.Sleep(0)
转载自:http://www.cnblogs.com/ATually/archive/2010/10/21/1857261.html 线程这一概念,可以理解成进程中的一个小单元.这个单元是一个独立的执 ...
- android NDK开发环境搭建
android NDK开发环境搭建 2012-05-14 00:13:58 分类: 嵌入式 基于 Android NDK 的学习之旅-----环境搭建 工欲善其事必先利其器 , 下面介绍下 Eclip ...
- Asp.Net Web API开发微信后台
如果说用Asp.Net开发微信后台是非主流,那么Asp.Net Web API的微信后台绝对是不走寻常路. 需要说明的是,本人认为Asp.Net Web API在开发很多不同的请求方法的Restful ...
- Android -- TabHost、Fragment、状态保存、通信
工程结构 TabAFm到Ta ...
- 设计模式 -- 单例模式(Java&&PHP)
所谓单例模式,简单来说,就是在整个应用中保证只有一个类的实例存在.就像是Java Web中的application,也就是提供了一个全局变量,用处相当广泛,比如保存全局数据,实现全局性的操作等. 能够 ...
- tomcat设置内存大小
-Xms256m -Xmx512m -XX:MaxNewSize=256m -XX:MaxPermSize=256m
- My97DatePicker控制开始时间和结束时间区间
开始时间: <input type="text" placeholder=" -请选择- " id="kssj" name=" ...
- Android开发-环境搭建以及HelloWorld
最近开始进行Android的开发,没有基础完全从0开始. 首先,知道Android开发的官方网站: http://developer.android.com/index.html 网站本身教程非常 ...