我在此程序:
錯誤值存儲和其他
LLIST:
typedef struct linked_list
{
int val;
int n;
struct linked_list *next;
}llist;
addelem功能:
void addelem(llist *list,int val)
{
llist *tmp=(llist *)malloc(sizeof(llist)); //create new element
tmp->val=val; //assign value to tmp
tmp->next=NULL; //set next to NULL
// printf("addelem entered\n");
if(list->next!=NULL) //if this is not the last element
{
addelem(list->next,val); //recursion
}
else
{
tmp->n=list->n + 1;
list->next=(llist *)malloc(sizeof(llist)); //allocate memory
list->next=tmp; //add to list
}
// printf("addelem exited\n");
free(tmp);
}
remelem功能:
void remelem(llist *list)
{
int f=0;
if(list->n==0 && list->next==NULL)
goto dontremove;
if(1)
{
if(list->next!=NULL)
{
if(list->next->next==NULL)
{
f=1;
}
remelem(list->next);
}
else
{
free(list);
}
if(f==1)
{
list->next=NULL;
}
}
else
{
dontremove:
printf("cant be removed even if the next message is 'Element removed.'\n");
}
//end
}
放映功能:
void show(llist *list)
{
printf("Element number: %d\nElement Value: %d\n",list->n,list->val);
if(list->next!=NULL)
{
show(list->next);
}
else
{
printf("\nTotal number of elems: %d\n",list->n);;
}
}
主要功能:
int main()
{
int i,n,ch;
llist *list=(llist *)malloc(sizeof(llist));
list->next=NULL;
list->n=0;
list->val=0;
menu: //menu label
printf("1.Add element.\n");
printf("2.Remove element.\n3.Show elements\n0.Exit.\n");
scanf("%d",&ch);
switch(ch)
{
case 1:
printf("\nEnter value.\n");
scanf("%d",&n);
addelem(list,n);
printf("Element added\n");
break;
case 2:
remelem(list);
printf("\nElement removed.\n");
break;
case 3:
show(list);
break;
case 0:
goto end; //end
break;
}
goto menu; //show menu again
end: //end label
return 0;
}
輸出:
1.Add element.
2.Remove element.
3.Show elements
0.Exit.
1
Enter value.
22
Element added
1.Add element.
2.Remove element.
3.Show elements
0.Exit.
1
Enter value.
4
Element added
1.Add element.
2.Remove element.
3.Show elements
0.Exit.
2
Element removed.
1.Add element.
2.Remove element.
3.Show elements
0.Exit.
3
Element number: 0
Element Value: 0
Element number: 1
Element Value: 161701936
Total number of elems: 1
的值是從鄰不同我輸入了。 我的第一個問題是,爲什麼會發生這種情況?(可能是一個愚蠢的錯誤),我如何修復它打印正確的值。
,這裏是另一個輸出:
1.Add element.
2.Remove element.
3.Show elements
0.Exit.
1
Enter value.
22
Element added
1.Add element.
2.Remove element.
3.Show elements
0.Exit.
1
Enter value.
23
Element added
1.Add element.
2.Remove element.
3.Show elements
0.Exit.
2
Element removed.
1.Add element.
2.Remove element.
3.Show elements
0.Exit.
1
Enter value.
22
Segmentation fault (core dumped)
在此,我首先添加元素,然後我刪除它,但如果我再添加的元素,我得到分段錯誤,誰能解釋爲什麼會發生這種情況,以及如何解決它?
如果起初我添加的元素,我刪除它,然後這是我得到什麼:
*** glibc detected *** ./llist: double free or corruption (fasttop): 0x0855b018 ***
======= Backtrace: =========
certain memory addresses
======= Memory map: ========
08048000-08049000 r-xp 00000000 08:01 1969473 /path/to/this/prog
08049000-0804a000 r--p 00000000 08:01 1969473 /path/to/this/prog
0804a000-0804b000 rw-p 00001000 08:01 1969473 /path/to/this/prog
0855b000-0857c000 rw-p 00000000 00:00 0 [heap]
b758e000-b75aa000 r-xp 00000000 08:01 3802036 /lib/i386-linux-gnu/libgcc_s.so.1
b75aa000-b75ab000 r--p 0001b000 08:01 3802036 /lib/i386-linux-gnu/libgcc_s.so.1
b75ab000-b75ac000 rw-p 0001c000 08:01 3802036 /lib/i386-linux-gnu/libgcc_s.so.1
b75c3000-b75c4000 rw-p 00000000 00:00 0
b75c4000-b7767000 r-xp 00000000 08:01 3805265 /lib/i386-linux-gnu/libc-2.15.so
b7767000-b7768000 ---p 001a3000 08:01 3805265 /lib/i386-linux-gnu/libc-2.15.so
b7768000-b776a000 r--p 001a3000 08:01 3805265 /lib/i386-linux-gnu/libc-2.15.so
b776a000-b776b000 rw-p 001a5000 08:01 3805265 /lib/i386-linux-gnu/libc-2.15.so
b776b000-b776e000 rw-p 00000000 00:00 0
b7782000-b7787000 rw-p 00000000 00:00 0
b7787000-b7788000 r-xp 00000000 00:00 0 [vdso]
b7788000-b77a8000 r-xp 00000000 08:01 3805277 /lib/i386-linux-gnu/ld-2.15.so
b77a8000-b77a9000 r--p 0001f000 08:01 3805277 /lib/i386-linux-gnu/ld-2.15.so
b77a9000-b77aa000 rw-p 00020000 08:01 3805277 /lib/i386-linux-gnu/ld-2.15.so
bf969000-bf98a000 rw-p 00000000 00:00 0 [stack]
Aborted (core dumped)
誰能告訴爲什麼這些錯誤已經發生?
我使用Ubuntu 12.04
謝謝
woho,那真的很長。 –
您可能會考慮使用valgrind運行您的程序。它會指出你一些討厭的問題。 – alk
使用'goto'總是引發討論。我有時會以結構化的方式使用它們,以便輕鬆地實現函數的出口點而不會擾亂源。但這個'dontremove'真的很難看。 – alk