Maison  >  Article  >  développement back-end  >  Utilisation de la fonction malloc

Utilisation de la fonction malloc

步履不停
步履不停original
2019-06-14 09:55:1443474parcourir

Utilisation de la fonction malloc

Le nom complet de malloc est l'allocation de mémoire, appelée allocation de mémoire dynamique en chinois. Elle est utilisée pour demander une zone de bloc de mémoire continue d'une taille spécifiée et renvoie la valeur. Adresse de la zone mémoire allouée de type void*. Lorsqu'il ne peut pas. Lorsque vous connaissez l'emplacement spécifique de la mémoire, si vous souhaitez lier l'espace mémoire réel, vous devez allouer dynamiquement de la mémoire. Le type

void* représente un pointeur non typé. C et C++ stipulent que le type void* peut être contraint en un pointeur de tout autre type via une conversion de type.

Doit généralement être associé à la fonction gratuite.

Définition de la fonction

Prototype

extern void *malloc(unsigned int num_bytes);

Fichier d'en-tête

#include <stdlib.h>

Déclaration de fonction

void *malloc(size_t size);

Remarques : void* Représente un pointeur d'un type indéterminé. void * peut pointer vers n'importe quel type de données Pour être plus précis, cela signifie que lors de la demande d'espace mémoire, on ne sait pas quel type de données l'utilisateur utilisera cet espace pour stocker (telles que). comme char ou int ou autre type de données).

Valeur de retour

Si l'allocation est réussie, le pointeur vers la mémoire allouée est renvoyé (la valeur initiale dans cette zone de stockage est incertaine), sinon le pointeur nul NULL est renvoyé. Lorsque la mémoire n'est plus utilisée, la fonction free() doit être utilisée pour libérer le bloc mémoire. Le pointeur renvoyé par la fonction doit être correctement aligné pour pouvoir être utilisé avec n'importe quel objet de données.

Explication

Concernant le prototype de cette fonction, malloc retournait auparavant un pointeur char. La nouvelle norme ANSIC stipule que cette fonction renvoie un pointeur vide, une conversion de type est donc requise si nécessaire. Il peut s'appliquer au système pour allouer un bloc de mémoire d'une longueur de num_bytes (ou size) octets.

Généralement, il doit être associé à la fonction gratuite. La fonction free peut libérer une adresse allouée dynamiquement, indiquant que cette mémoire allouée dynamiquement n'est plus utilisée, et renvoie la mémoire précédemment appliquée dynamiquement au système.

Fonctions associées

calloc, realloc, free, _alloca.

La différence entre new Pour une fonction implémentée dans celui-ci, si stdlib.h n'est pas inclus directement ou indirectement dans le code source, alors gcc signalera une erreur : 'malloc' n'a pas été déclaré dans ce portée. Si le fichier cible est généré (en supposant un malloc de lien dynamique), s'il n'y a pas de libc sur la plate-forme en cours d'exécution (pour la plate-forme Linux, spécifiez simplement manuellement LD_LIBRARY_PATH dans un répertoire vide), ou s'il n'y a pas de fonction malloc dans la libc, alors ce sera exécuté au moment de l'exécution (Run-time) Un problème s'est produit. New n'est pas le cas. C'est un mot-clé en C++ et ce n'est pas une fonction en soi. new ne dépend pas du fichier d'en-tête. Le compilateur c++ peut compiler new dans le code cible (g++4.6.3 insérera la fonction _Znwm dans la cible. De plus, le compilateur insérera également la structure correspondante en fonction du type de la fonction du paramètre).

En termes d'utilisation, malloc et new ont au moins deux différences : new renvoie un pointeur du type spécifié et peut calculer automatiquement la taille requise. Par exemple :

int *p;
p = new int;
//返回类型为int *类型(整数型指针),分配大小为sizeof(int);

ou :

int *parr;
parr = new int[100];
//返回类型为int *类型(整数型指针),分配大小为sizeof(int) * 100;

et malloc nous oblige à calculer le nombre d'octets et à forcer la conversion en un pointeur du type réel après le retour.

int *p;
p = (int*)malloc(sizeof(int) * 128);
//分配128个(可根据实际需要替换该数值)整型存储单元,
//并将这128个连续的整型存储单元的首地址存储到指针变量p中
double *pd = (double*)malloc(sizeof(double) * 12);
//分配12个double型存储单元,
//并将首地址存储到指针变量pd中

Tout d'abord, la fonction malloc renvoie le type void *.

Pour C++, si vous écrivez : p = malloc (sizeof(int)); alors le programme ne peut pas être compilé et un message d'erreur sera signalé : "void* ne peut pas être affecté à une variable de type int *" .

Vous devez donc passer (int*) pour lancer. Pour le C, une telle exigence n'existe pas, mais afin de rendre les programmes C plus faciles à transplanter en C++, il est recommandé de développer l'habitude de la conversion forcée.

Deuxièmement, le paramètre réel de la fonction est sizeof(int), qui est utilisé pour spécifier la taille requise d'une donnée entière.

Vous devez faire attention à un cas particulier de malloc(0). La valeur de retour peut être une NULL ou une adresse valide (elle peut être libérée en toute sécurité, mais ne peut pas être déréférencée). Notez que malloc(-1) n'est pas interdit. Le paramètre est un type non signé. S'il s'agit d'un nombre négatif, il peut être converti en un très grand nombre positif. Au final, NULL est généralement renvoyé car il n'est pas grand. suffisamment de bloc de mémoire.

Dans les programmes standards, nous devons utiliser malloc et free dans ce format :

type *p;
if(NULL == (p = (type*)malloc(sizeof(type))))
/*请使用if来判断,这是有必要的*/
{
    perror("error...");
    exit(1);
}
.../*其它代码*/
free(p);
p = NULL;/*请加上这句*/

malloc peut également obtenir l'effet de new [] et demander une mémoire continue. La méthode n'est rien de plus. puis il spécifie la taille de mémoire dont vous avez besoin.

Par exemple, si vous souhaitez allouer 100 espaces de type int :

int *p = (int*)malloc(sizeof(int) * 100);
//分配可以放得下100个整数的内存空间。

Une autre différence qui ne peut pas être vue directement est que malloc alloue uniquement de la mémoire et ne peut pas initialiser la mémoire résultante, nous obtenons donc In un nouveau morceau de mémoire, sa valeur sera aléatoire.

À l'exception des différentes méthodes d'allocation et de publication finale, le pointeur est obtenu via malloc ou new, et les autres opérations sont cohérentes.

Ajoutez-y un cas spécial

char *ptr;
if((ptr = (char*)malloc(0)) == NULL)
    puts("Gotanullpointer");
else
    puts("Gotavalidpointer");

À ce stade, vous pouvez obtenir Vous avez un pointeur valide, ou vous pouvez obtenir Vous avez un pointeur nul.

Mécanisme de travail

malloc函数的实质体现在,它有一个将可用的内存块连接为一个长长的列表的所谓空闲链表。调用malloc函数时,它沿连接表寻找一个大到足以满足用户请求所需要的内存块。然后,将该内存块一分为二(一块的大小与用户请求的大小相等,另一块的大小就是剩下的字节)。接下来,将分配给用户的那块内存传给用户,并将剩下的那块(如果有的话)返回到连接表上。调用free函数时,它将用户释放的内存块连接到空闲链上。到最后,空闲链会被切成很多的小内存片段,如果这时用户申请一个大的内存片段,那么空闲链上可能没有可以满足用户要求的片段了。于是,malloc函数请求延时,并开始在空闲链上翻箱倒柜地检查各内存片段,对它们进行整理,将相邻的小空闲块合并成较大的内存块。如果无法获得符合要求的内存块,malloc函数会返回NULL指针,因此在调用malloc动态申请内存块时,一定要进行返回值的判断。

Linux Libc6采用的机制是在free的时候试图整合相邻的碎片,使其合并成为一个较大的free空间。

程序示例

正常程序

typedef struct data_type{
    int age;
    char name[20];
}data;
data*bob=NULL;
bob=(data*)malloc(sizeof(data));
if(bob!=NULL)
{
    bob->age=22;
    strcpy(bob->name,"Robert"); 
    printf("%s is %d years old.\n",bob->name,bob->age);
}
else
{
    printf("mallocerror!\n");
    exit(-1);
}  
free(bob);
bob=NULL;

输出结果:Robert is 22 years old.

内存泄漏实例

#include <stdio.h>
#include <malloc.h>
#define MAX 100000000int main(void)
{
    int *a[MAX] = {NULL};
    int i;
    for(i=0;i<MAX;i++)
    {
    a[i]=(int*)malloc(MAX);
    }
    return 0;
}

注:malloc申请之后没有检测返回值。

推荐教程:C#视频教程

Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!

Déclaration:
Le contenu de cet article est volontairement contribué par les internautes et les droits d'auteur appartiennent à l'auteur original. Ce site n'assume aucune responsabilité légale correspondante. Si vous trouvez un contenu suspecté de plagiat ou de contrefaçon, veuillez contacter admin@php.cn