如何在链接列表生成中使用malloc?我看不到它如何用于生成新链表,而不是为链表保留内存
提示:按Ctrl + F
并查找“ (***)
”(不带引号)以找到确切的代码位置
示例1:
#include <stdio.h>
#include <stdlib.h>
struct LinkedList {
int data; /* The data part of the linked list */
struct LinkedList *next; /* The pointer part of the linked list */
};
int main(void) {
/* Generate the 1st node ("head") */
struct LinkedList *head /* I am not sure what this pointer */
head = NULL; /* is doing to the struct*/
head = malloc(sizeof(struct LinkedList)); /* Head points to null. Now
* malloc() is being called
* and is assigned to head.
* Next line implies head is
* already pointing to a
* linked list, which means
* malloc() is making a new
* strucuture (***) */
/* Generate the second node */
head -> data = 1; // This implies head is already pointing to a linked list
head -> next = malloc(sizeof(struct LinkedList));
/* Generate the third node */
head -> next -> data = 2;
head -> next -> next = malloc(sizeof(struct LinkedList));
/* Generate the fourth node */
head -> next -> next -> data = 3;
head -> next -> next -> next = NULL;
return 0;
}
示例2:
#include<stdio.h>
#include<stdlib.h>
struct LinkedList {
int data;
struct LinkedList *next;
}; // notice the semi-colon!
int main(void) {
struct LinkedList *head = NULL; /* why is it doing this? */
struct LinkedList *second = NULL;
struct LinkedList *third = NULL;
// Generate the node structure:
/* how does (struct LinkedList*) affect malloc? (***) */
head = (struct LinkedList*)malloc(sizeof(struct LinkedList));
second = (struct LinkedList*)malloc(sizeof(struct LinkedList));
third = (struct LinkedList*)malloc(sizeof(struct LinkedList));
// Now fill the first node with info:
head->data = 1; /* assign data to the first node */
head->next = second; /* Link the first node ("head") with the second
* node ("second") */
// Now fill the second node with info:
second->data = 2; /* assign data to the second node */
second->next = third; /* Link the second node to the third node */
// Now fill the second node with info:
third->data = 3; /* assign data to the second node */
third->next = NULL; /* Since node 3 is our last node to the link list,
* we give it the value of NULL */
return 0;
}
教科书将链接列表描述为链结构。 Malloc()用于动态内存管理。但是,在这些示例中,使用malloc声明了新结构,我不明白为什么。我以为它只能保留内存
例如,在示例1中,malloc()保留了该结构的空间,但没有“创建”它(struct LinkedList var
将创建一个新的链表并将其存储在var
中)< / p>
例如,在示例2中,看起来malloc()受到(struct LinkedList*)
(即(struct LinkedList*)malloc(sizeof(struct LinkedList));
)的影响,但是我不确定
答案 0 :(得分:2)
您可以像在相互连接的盒子上一样查看链接列表:
______ ______ ______
| data | | data | | data |
|______| |______| |______|
| next | | next | | next |
|______|----->|______|----->|______|----->NULL
每个方框都在您的位置:
struct LinkedList
{
int data; /* The data part of the linked list */
struct LinkedList *next; /* The pointer part of the linked list */
};
您的“盒子”的大小(取决于拱门)让我们以x64 Linux机器等于 到16个字节。要创建链接列表数据类型,您需要将此框存储在内存中(堆栈/堆)并连接它们。
我注意到一个“盒子”的大小是16字节,应该存储在内存中。对于用户空间中的内存管理,您可以使用malloc()
,这里重要的事情是malloc()
没有“声明”任何内容 ,它 只为堆上的一个“盒子”分配一部分内存 ,而您使用sizeof()
运算符为“盒子”要求恰好16个字节。
struct LinkedList *head = malloc(sizeof(struct LinkedList));
它为您的“盒子”分配内存,现在看起来像这样:
______
| data |
|______|
| next |
|______|----->NULL
执行此操作时:
head->next = malloc(sizeof(struct LinkedList));
您为另一个“盒子”分配内存并连接它们:
______ ______
| data | | data |
|______| |______|
| next | | next |
|______|----->|______|
执行此操作时:
struct LinkedList *head = malloc(sizeof(struct LinkedList));
struct LinkedList *second = malloc(sizeof(struct LinkedList));
struct LinkedList *third = malloc(sizeof(struct LinkedList));
您在内存中的每个位置创建16个字节的三个“框”。而且他们暂时不连接,它们只位于内存中;
head second third
______ ______ _____
| data | | data | | data |
|______| |______| |______|
| next | | next | | next |
|______| |______| |______|
您将他们连接起来就是这样:
head->next = second;
second->next = third;
third->next = NULL;
head second third
______ ______ ______
| data | | data | | data |
|______| |______| |______|
| next | | next | | next |
|______|----->|______|----->|______|----->NULL
通常在函数中使用第二种方法,例如用于ex add_node_front()
void add_node_front(struct LinkedList **head_ref, int data)
{
/* 1. allocate node */
struct LinkedList *new_node = malloc(sizeof(struct LinkedList));
/* 2. put in the data */
new_node->a = data;
/* 3. Make next of new node as head */
new_node->next = (*head_ref);
/* 4. move the head to point to the new node */
(*head_ref) = new_node;
}
答案 1 :(得分:1)
在第二个示例中,您还可以静态分配内存:
struct LinkedList head;
struct LinkedList second;
struct LinkedList third;
然后您需要使用点运算符进行访问:
head.data = 1; //assign data to the first node
head.next = &second;
您还可以使用数组
struct LinkedList nodes[3];
node[0].data = 1;
node[0].next = &node[1];
以此类推。
因此,malloc命令对于链接列表的概念不是必需的。 但是对于您之前不知道的许多应用程序,您的链表将有多大。并且元素和顺序将在运行时更改。因此,在这种情况下,使用malloc / free进行动态内存分配确实很有帮助。
答案 2 :(得分:0)
如何在链接列表生成中使用malloc?
malloc
用于动态分配内存。创建链接列表时,可以使用malloc
为列表的节点分配内存。
了解有关malloc here的更多信息。
来自示例1:
head = malloc(sizeof(struct LinkedList));
来自示例2:
head = (struct LinkedList*)malloc(sizeof(struct LinkedList));
唯一的区别是,在示例2中,您显式强制转换malloc
结果。 malloc
的返回类型为void *
,并且void *
可以强制转换为所需的类型,但是无需这样做,因为它将被自动转换。因此,投射不是必需的。实际上,不强制转换malloc
。选中this。
除了内存分配顺序外,两个示例在功能上都是相同的。
在示例1中,您将分配内存给head
指针,然后分配给head -> next
指针,然后分配给head -> next -> next
指针。
在示例2中,您将内存分配给head
,second
和third
指针,然后将second
分配给head -> next
和third
到head -> next -> next
。
其他:
始终检查malloc的返回值,例如:
head = malloc(sizeof(struct LinkedList));
if (NULL == head) {
fprintf (stderr, "Failed to allocate memory");
exit(EXIT_FAILURE);
}
此外,一旦完成,请确保free
动态分配的内存。遵循良好的编程习惯。