具体请参考 深入理解c指针 第二章
Some base to know
声明时 * 两边的空白无关紧要
指针在声明后如果不初始化,指向的内容不合法,不能使用。
指针类型指示了指针在 + - 的时候的行为
* 号是重载的运算符,在声明的时候 代表指针 例如 int *
还用于指针 dereference 乘法
地址操作符 & 可用于初始化指针。
null
NULL
被赋值给指针意味着指针不指向任何东西。
许多库中定义:
#define NULL ((void *)0)
null
概念指指针包含了一个特殊的值,和别的指针不一样,它没有指向任何内存区域,两个 null
指针总是相等的。每一种指针类型,都可以有对应的null
指针类型。
指针操作符
#include <stdlib.h>
#include <stdio.h>
int main()
{
// 创建一个 char* 的数组
char *titles[] = {
"A Tale of Two Cities",
"Wuthering Heights",
"Don Duixote",
"Odyssey",
"Moby-Dick",
"Hamlet",
"Gulliver's Traverls"
};
// 声明一个 char** 的数组
char **bestBooks[3];
char **englishBooks[4];
bestBooks[0] = &titles[0];
printf("%s\n", *bestBooks[0]);
englishBooks[1] = &titles[1];
printf("%s\n", *englishBooks[1]);
return 1;
}
指向常量的指针
将指针定义为指向常量,意味着不能通过指针修改它所引用的值。
const int *pci
c的动态内存管理
内存泄漏
丢失地址
动态内存分配函数
要不要强制类型转换
malloc
返回的是 void *
calloc
会在分配的同时清空内存
void *calloc(size_t numElements, size_t elementSize)
举个例子:假设你用malloc需要申请100字节,实际是申请了104个字节。把前4字节存成该块内存的实际大小,并把前4字节后的地址返回给你。 free释放的时候会根据传入的地址向前偏移4个字节 从这4字节获取具体的内存块大小并释放。(实际上的实现很可能使用8字节做为头部:其中每四个字节分别标记大小和是否正在使用)实际的内存管理比这个要复杂的多,但一般手段都是如上通过记录头或者叫做cookie来存储大小以及是否正在使用来确定以后到底要回收多少和是否可以复用。内存管理比较复杂的主要原因是内存管理程序会缓存和合并已经申请的内存块并且去复用,或者申请超大的一个块,自己省着点用 ,这样不必每次都想操纵系统要。
作者:寻寒
链接:https://www.zhihu.com/question/23196195/answer/23879529
来源:知乎
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。
malloc和free其实并不是直接向操作系统申请或者释放内存的,而是维护了一个空闲内存块的链表
链表中内存不够的时候,才向操作系统申请内存
malloc返还给你的地址的前面一小段是存在链表中的,留有你这一块多大的信息
https://stackoverflow.com/questions/1518711/how-does-free-know-how-much-to-free