C 再次出现分段错误-使用链表实现堆栈

C 再次出现分段错误-使用链表实现堆栈,c,data-structures,linked-list,stack,C,Data Structures,Linked List,Stack,今天早些时候,我发布了一个分段错误链接: 我得到的答案是惊人的,我在给出答案后摆脱了错误……但后来它又回来了 这是我的新代码(我添加到main()): #包括 #包括 类型定义结构链接{ int值; 结构链接*下一步; }链接; 类型定义结构1{ 整数大小; 链接*头; }LIST1; typedef结构LListStack{ LIST1*LIST; }利斯塔克; LListStack*初始LListStack(无效) { LListStack*堆栈=(LListStack*)malloc(si

今天早些时候,我发布了一个分段错误链接:

我得到的答案是惊人的,我在给出答案后摆脱了错误……但后来它又回来了

这是我的新代码(我添加到main()):

#包括
#包括
类型定义结构链接{
int值;
结构链接*下一步;
}链接;
类型定义结构1{
整数大小;
链接*头;
}LIST1;
typedef结构LListStack{
LIST1*LIST;
}利斯塔克;
LListStack*初始LListStack(无效)
{
LListStack*堆栈=(LListStack*)malloc(sizeof(LListStack));
stack->llist=(LList1*)malloc(sizeof(LList1));
堆栈->列表->大小=0;
stack->llist->head=NULL;
返回(堆栈);
}
void removefront(LList1*llist)
{
如果(LIST->head!=NULL){
LIST->head=LIST->head->next;
llist->size--;
}
}
Link*FindLastLink(LList1*llist,Link*Link)
{
if(link=NULL){
返回(空);
}
else if(链接->下一步==NULL){
返回(链接);
}
否则{
返回(FindLastLink(llist,link->next));
}
}
Link*FindSecondLastLink(LList1*llist,Link*Link)
{
if(link=NULL){
返回(空);
}
else if(链接->下一步->下一步==NULL){
返回(链接);
}
否则{
返回(FindSecondLastLink(llist,link->next));
}
}
void removelast(LList1*llist)
{
Link*secondlastlink=(Link*)malloc(sizeof(Link));
secondlastlink=FindSecondLastLink(llist,llist->head);
secondlastlink->next=NULL;
llist->size--;
}
void prepend(int newValue,LList1*templast)
{
Link*node=(Link*)malloc(sizeof(Link));
节点->值=新值;
节点->下一步=模板->头部;
圣殿骑士->头=节点;
圣堂武士->大小++;
}
void append(int newValue,LList1*templast)
{
Link*node=(Link*)malloc(sizeof(Link));
Link*lastlink=(Link*)malloc(sizeof(Link));
lastlink=FindLastLink(templist,templist->head);
节点->值=新值;
lastlink->next=节点;
节点->下一步=空;
圣堂武士->大小++;
}
void prepush(int值,LListStack*堆栈)
{
前置(值,堆栈->列表);
}
void apppush(int值,LListStack*堆栈)
{
追加(值,堆栈->列表);
}
int PREPP(LListStack*堆栈)
{
int结果;
如果((!isEmpty(stack)))
{
removefront(堆栈->llist);
结果=1;
}
否则{
结果=0;
}
返回(结果);
}
int isEmpty(liststack*堆栈)
{
int空;
如果(堆栈->列表->头部==NULL)
申报表(1);
其他的
返回(0);
}
int-apppop(LListStack*堆栈)
{
int结果;
如果((!isEmpty(stack)))
{
removelast(堆栈->llist);
结果=1;
}
其他的
结果=0;
返回(结果);
}
无效打印列表(LIST1*LIST,Link*Link){
如果(链接->下一步!=NULL){
printf(“%d\n”,链接->值);
打印列表(列表,链接->下一步);
}
}
//*******主要**********//
int main()
{
LListStack*堆栈=(LListStack*)malloc(sizeof(LListStack));
stack=initLListStack();//如果我去掉这个,我就可以运行程序了
int-pre,app,i,n=10;
对于(i=0;i0;i--){
apppush(i,stack);//这也是
预推(i,堆栈);
}
打印列表(堆栈->李斯特,堆栈->李斯特->头部);
返回(0);
}
现在查看main(),当我调用'prepush()'或'prepull()' 一切都很好。但是,如果调用'apppush()'或'apppull()',则会出现分段错误。通过跟踪函数,我认为罪魁祸首是函数
FindLastLink()
FindSecondLastLink()
,因为它们都包含递归。我不知道为什么,因为我对这个很陌生,所以任何解决这个问题的帮助都会很棒


再次感谢各位

我认为您的问题在于FindSecondLastLink函数。您忘记检查指向NULL的第二个指针。当您访问link->next->next时,如果link->next==NULL,则会导致segfault

Link *FindSecondLastLink(LList1 *llist, Link *link)
{
if(link = NULL){ // One more problem is that you assigning NULL value to link variable instead of compare it. It should be link == NULL
    return(NULL);
}
else if(link->next->next == NULL){ // The problem is here. You forgot to check if link->next == NULL
    return(link);
}
else{
    return(FindSecondLastLink(llist, link->next));
}
}

有两个问题:调用
removefront
时,可能存在内存泄漏。不要强制转换
malloc
的返回值。
LListStack
结构中的成员
llist
不一定是指针。而且内存泄漏更多,例如在
removelast
中,分配内存并将其分配给
secondlastlink
,然后立即重新分配该指针,从而丢失刚才分配的内存。程序的其他部分也存在更多类似的泄漏。最后,如果程序崩溃,您应该使用调试信息构建它(将
-g
标志添加到gcc),并在调试器中运行程序。调试器随后将在崩溃现场停止。如果它不在您的代码中,那么您可以沿着函数调用堆栈一直走到您的代码,在那里您可以检查变量的值。您知道如果(link=NULL)会做什么吗?正确的函数,但这段代码中的bug远远不止一个。这在
FindLastLink
,btw.Ooops中重复。错过了。谢谢你,@WhozCraig,我已经编辑了答案。
Link *FindSecondLastLink(LList1 *llist, Link *link)
{
if(link = NULL){ // One more problem is that you assigning NULL value to link variable instead of compare it. It should be link == NULL
    return(NULL);
}
else if(link->next->next == NULL){ // The problem is here. You forgot to check if link->next == NULL
    return(link);
}
else{
    return(FindSecondLastLink(llist, link->next));
}
}