void* 类型的链表
我正在尝试读取一个文本文件并将每一行存储在 void* 类型的链接列表的节点中。 这是列表的头文件。
#ifndef LINKEDL
#define LINKEDL
struct node_s {
void *data;
struct node_s *next;
};
struct node_s *node_create(void*);
struct node_s *list_insert_after(struct node_s*, void*);
struct node_s *list_insert_beginning(struct node_s*, void*);
int list_remove(struct node_s*, struct node_s*);
int list_foreach(struct node_s*, int(*)(void*));
int printstring(void *s);
#endif
所有的链表函数都经过了彻底的测试,所以我猜问题出在我如何使用它上。我想要实现的是每个节点中有一行,而我现在拥有的是每个节点中的最后一行。我想这与 char 指针有关,但已经花了两个小时,没有取得重大突破,所以也许有人可以提供帮助? 另外,我使用的列表是修改后的列表,如此处所示。
if (file == NULL)
{
perror("Error opening file");
}
else
{
char mystring[SIZE];
char temp[SIZE];
list = node_create((void*)mystring);
current = list;
while (fgets(mystring, SIZE, file) != NULL)
{
strcpy(temp, mystring);
printf("%d\t%s",counter++,temp);
current=list_insert_after(current, (void*)temp);
}
fclose(file);
}
更新: 谢谢大家。
I'm trying to read a text file and store each line in a node of a link list of type void*.
Here's the header file of the list.
#ifndef LINKEDL
#define LINKEDL
struct node_s {
void *data;
struct node_s *next;
};
struct node_s *node_create(void*);
struct node_s *list_insert_after(struct node_s*, void*);
struct node_s *list_insert_beginning(struct node_s*, void*);
int list_remove(struct node_s*, struct node_s*);
int list_foreach(struct node_s*, int(*)(void*));
int printstring(void *s);
#endif
All the linked list functions have been thoroughly tested, so I guess the problem is with how I use it. What I want to achieve is the have one line in each node and what I have now is last line in every node. I guess it has something to do with the char pointers but have already spent two hours on that without a spectacular breakthrough, so maybe someone could help?
Also the list I use is a modified list as seen here.
if (file == NULL)
{
perror("Error opening file");
}
else
{
char mystring[SIZE];
char temp[SIZE];
list = node_create((void*)mystring);
current = list;
while (fgets(mystring, SIZE, file) != NULL)
{
strcpy(temp, mystring);
printf("%d\t%s",counter++,temp);
current=list_insert_after(current, (void*)temp);
}
fclose(file);
}
UPDATE:
Thank you All.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
您使用单个数组 temp 创建每个节点。每次读取一行时,都会将 temp 的内容替换为您读取的最后一行。这就是为什么每个节点上都有最后一行(您指的是每个节点中的相同内存位置)。
您应该做的是使用 malloc 为每一行动态分配内存。因此,您应该将指向新分配的内存的指针传递给list_insert_after,而不是传递temp。
You are creating each node using a single array, temp. Every time you read a line, you replace the contents of temp with the last line you read. That's why you have the last line on every node (you are referring to the same memory location in every node).
What you should do, is to allocate memory dynamically for each line using malloc. Thus, you should pass the pointer to the newly allocated memory to list_insert_after instead of passing temp.
删除行:
并更改行:
至
Remove the line:
And change the line:
To
考虑一下 - 堆栈上有一个临时 char 数组,该数组在退出范围(
else
块)时会被销毁,并且您正在将指向该数组的指针插入到列表中。所以毕竟,列表最终将具有指向已损坏/不正确数据的指针。该行为是未定义的。您必须为每个字符串动态分配内存(并且不要忘记清理它)。
strdup
在这里很有用。只是不要忘记拨打免费
从该列表中删除/删除字符串时。Think about this - you have a temporary char array on stack which is getting destroyed upon exiting out of the scope (of
else
block) and you are inserting pointer to that array into a list. So after all, the list will end up having pointers to destroyed/incorrect data. The behavior is undefined.You have to allocate memory dynamically for each string (and not forget to clean it up). The
strdup
can be useful here. Just don't forget to callfree
when removing/dropping string from that list.