C 无限循环链表
在我的代码中,似乎有一个无限循环,打印出同一个名为search的class_t变量,尽管我试图将该变量向前移动到下一个class_t。所有类结构要么指向(class_t*)0(因为我在比较class_t*和void*)时使用NULL会收到编译器警告),要么指向下一个适当的类结构。我做错了什么,或者我应该找其他地方来解决我的问题C 无限循环链表,c,linked-list,structure,infinite-loop,C,Linked List,Structure,Infinite Loop,在我的代码中,似乎有一个无限循环,打印出同一个名为search的class_t变量,尽管我试图将该变量向前移动到下一个class_t。所有类结构要么指向(class_t*)0(因为我在比较class_t*和void*)时使用NULL会收到编译器警告),要么指向下一个适当的类结构。我做错了什么,或者我应该找其他地方来解决我的问题 class_t *search = (students + i)->class_p;//students is a seperate structure where
class_t *search = (students + i)->class_p;//students is a seperate structure where class_p is a pointer to a class_t structure
while(search != (class_t*)0)
{
fprintf(output,": %s%d %d %d\n", search->name, search->number, search->section, search->credits);
search = search->nextClass;
}
这是一个输出示例,看看它,它是类中最后一次读取文件
: CS521 1 4
: CS521 1 4
: CS521 1 4
: CS521 1 4
: CS521 1 4
: CS521 1 4
: CS521 1 4
: CS521 1 4
: CS521 1 4
: CS521 1 4
: CS521 1 4
: CS521 1 4
下面是课堂创作:
class_t newClass;
newClass.number = classid;
newClass.section = section;
newClass.credits = credits;
newClass.nextClass = (class_t*)0;
添加节点时:
void addNode(student_t students[], class_t addClass, int ref)
{
int found = 0;
if((students + ref)->class_p == (class_t*)0)//no classes yet
{
(students + ref)->class_p = &addClass;
found = 1;
}
else if((*((students + ref)->class_p)).number > addClass.number && found == 0)//checks first class
{
class_t *temp = (students + ref)->class_p;
(students + ref)->class_p = &addClass;
addClass.nextClass = temp;
found = 1;
}
else//works way through the class linked list to find where it goes
{
class_t *beforesearch = (students + ref)->class_p;
class_t *search = beforesearch->nextClass;
while(search != (class_t*)0 && found == 0)
{
if(search->number < addClass.number)
{
beforesearch->nextClass = &addClass;
addClass.nextClass = search;
found = 1;
}
else
{
beforesearch = search;
search = search->nextClass;
}
}
if(found == 0)
{
beforesearch->nextClass = &addClass;
found = 1;
}
}
这是一个非常微妙的错误:
void addNode(student_t students[], class_t addClass, int ref)
{
int found = 0;
if((students + ref)->class_p == (class_t*)0)//no classes yet
{
(students + ref)->class_p = &addClass;
您正在通过值传递addClass
(即我假定的结构的完整副本),然后使用其地址将其链接到列表中。这是错误的,因为您使用的是属于调用堆栈的函数参数的地址
如果您得到一个列表循环,则意味着您遇到了这样的情况:对addNode
的每次调用都会将结构复制到堆栈中的同一地址。但是这很幸运,这段代码中有太多可能出错的地方,我不会一一解释
正确的解决方案是在堆上分配class\u t
节点(即使用malloc()
)并向它们传递指针。或在链接之前分配一份副本:
void addNode(student_t students[], class_t addClass_param, int ref)
{
class_t *addClass = malloc(sizeof(class_t)); /* Check for NULL return skipped */
memcpy(addClass, &addClass_param, sizeof(class_t));
/* ... */
这是一个非常微妙的错误:
void addNode(student_t students[], class_t addClass, int ref)
{
int found = 0;
if((students + ref)->class_p == (class_t*)0)//no classes yet
{
(students + ref)->class_p = &addClass;
您正在通过值传递addClass
(即我假定的结构的完整副本),然后使用其地址将其链接到列表中。这是错误的,因为您使用的是属于调用堆栈的函数参数的地址
如果您得到一个列表循环,则意味着您遇到了这样的情况:对addNode
的每次调用都会将结构复制到堆栈中的同一地址。但是这很幸运,这段代码中有太多可能出错的地方,我不会一一解释
正确的解决方案是在堆上分配class\u t
节点(即使用malloc()
)并向它们传递指针。或在链接之前分配一份副本:
void addNode(student_t students[], class_t addClass_param, int ref)
{
class_t *addClass = malloc(sizeof(class_t)); /* Check for NULL return skipped */
memcpy(addClass, &addClass_param, sizeof(class_t));
/* ... */
在添加/删除节点时,我会评估您如何处理头部/尾部。很可能你正在引入一个循环。需要看看你是如何构建列表的。里面有一个循环!请添加一个输出样本,这样我们就可以看到是否有一个模式-如果Slaks是正确的-它可能会显示在输出样本中。当您使用NULL时,您收到了什么样的投诉?编译器或主管的投诉?您可能需要查找。我会评估您在添加/删除节点时如何处理头部/尾部。很可能你正在引入一个循环。需要看看你是如何构建列表的。里面有一个循环!请添加一个输出样本,这样我们就可以看到是否有一个模式-如果Slaks是正确的-它可能会显示在输出样本中。当您使用NULL时,您收到了什么样的投诉?编译器或主管的抱怨?你可能想查一下。我接受了你的建议,但没什么区别。我在堆上给了它空间,并确保所有的东西都被复制到新的地点。但是,它现在不向输出文件打印任何内容,并且仍然卡在某种循环中。@Setzra:这种情况下,调试器很方便。我接受了你的建议,但没有什么区别。我在堆上给了它空间,并确保所有的东西都被复制到新的地点。但是,它现在不向输出文件打印任何内容,并且仍然卡在某种循环中。@Setzra:这种情况下调试器很方便。