user-0 提问: 单链表删除不对劲

回复:
user: user-1
content: void delelist_all(list *&L, int n) { 	list *p1, *p2; 	list *head; 	head = L; 	p1 = head; 	list* head_temp = head;    //作为临时头结点 	while (p1 != NULL) 	{ 		p1 = findlist_single(head_temp, n);  //从临时头结点开始查找第一个D为n的结点 											//如果没有找到则p1为NULL，循环结束 		p2 = p1->next; 		p1->next = p2->next; 		free(p2);  		/*p1 = p1->next; 		p2 = p1; 		if (p2->D == n) 		{ 			delelist_single(head, n); 		}*/ 	} }  我对删除全部做了修改，这个编译并没有通过，你可以根据这个思路自己再改改。 不过今晚我没有时间了，明早有事要早睡，明天下午我帮你再看看。

user: user-2
content: read stl list source code. and slist a plus

user: user-3
content: 楼主这样操作看上去每次删除之后链表就断了，因为你把中间的节点删了之后没有把前后的节点再连起来。

user: user-1
content: void delelist_all(list *&L, int n) { 	list *p1, *p2; 	list *head; 	head = L; 	p1 = head;  	while (p1->next != NULL)  //尾结点之前判断 	{ 		p2 = p1->next;		 		if (p2->D == n){ 			p1->next = p2->next; 			free(p2); 		} 		else 			p1 = p1->next; 	} 	if (p1->D == n){    //判断尾结点 		p1->next = NULL; 		free(p1); 	} }  严谨的说应该这样处理，才会覆盖所有的输入情况。

user: user-0
content: void delelist_single(list *&L,int n)//has been done { 	list *p1,*p2,*head; 	head=L; 	p1=findlist_single(head,n); 	if(p1!=NULL) 	{ 		p2=p1->next; 		p1->next=p2->next;//这里应该将前一元素的next指向跳过删除的元素 		free(p2); 	} }  void delelist_all(list *&L,int n) { 	list *p1,*p2,*p3; 	list *head; 	head=L; 	p1=head; 	while(p1!=NULL) 	{ 		p1=p1->next; 		p2=p1; 		if(p2->D==n) 		{ 			delelist_single(head,n); 		} 	} }   这是我修改后的例程 到底哪里不对哇→_→

user: user-0
content: 引用 1 楼 Falleyes 的回复:#include "stdio.h" #include "stdlib.h" #include "malloc.h"  typedef struct node { 	int D; 	node *next;//to back }list;  //单链表例程 void init_single(list *&L); void creatlist_single(list *&L, int n); void printlist_single(list *&L); list* findlist_single(list *&L, int n);//用于发现一个节点的前驱元.n为要发现的节点 void delelist_single(list *&L, int n);//删除为n的 void delelist_all(list *&L, int n);//删除所有为n的 void cutlist_single(list *&L, int n);//插入例程  int main() { 	int n, m; 	list *L;//相当于head指针 	scanf("%d", &n);//确定链表长度 	creatlist_single(L, n); 	printlist_single(L); 	scanf("%d", &m);//要删除的数 	delelist_single(L, m); 	printlist_single(L); 	//delelist_all(L,m); 	//printlist_single(L); 	return 0; }   void init_single(list *&L)//has been done { 	L = (list*)malloc(sizeof(list)); 	L->next = NULL; }  void creatlist_single(list *&L, int n)//has been done { 	list *s, *r; 	init_single(L); 	r = L; 	while (n--) 	{ 		s = (list*)malloc(sizeof(list)); 		scanf("%d", &s->D); 		r->next = s; 		r = r->next;//important!   is right!!! 	} 	r->next = NULL; }  void printlist_single(list *&L)//has been done { 	list *p; 	p = L->next; 	while (p != NULL) 	{ 		printf("%d", p->D); 		p = p->next; 	} 	printf("\n"); }  list* findlist_single(list *&L, int n)//此例程用于寻找一个节点的前驱元 { 	list *head; 	list *p1, *p2; 	int tag = 0;//if find,tag=1,else tag=0,return NULL; 	head = L; 	p1 = head;    //注意这里，初始化不应该是p1=head->next,因为循环中一开始就p1=p1->next; 	while (p1 != NULL) 	{ 		p1 = p1->next; 		p2 = p1; 		p2 = p2->next; 		if (p2->D == n) 		{ 			tag = 1; 			break; 		} 	} 	if (tag == 1) 		return p1; 	else 		return NULL; }  void delelist_single(list *&L, int n)//has been done { 	list *p1, *p2, *head; 	head = L; 	p1 = findlist_single(head, n); 	if (p1 != NULL) 	{ 		/*p1 = p1->next; 		p2 = p1; 		p1 = p2->next;*/  		p2 = p1->next;     		p1->next = p2->next;   //这里应该将前一元素的next指向跳过删除的元素  		free(p2); 	} }  void delelist_all(list *&L, int n) { 	list *p1, *p2, *p3; 	list *head; 	head = L; 	p1 = head->next; 	while (p1 != NULL) 	{ 		p2 = findlist_single(head, n); 		if (p2 != NULL) 		{ 			p2 = p2->next; 			p3 = p2; 			p2 = p3->next; 			free(p3); 		} 		p1 = p1->next; 	} }  还有些问题额，第一个删除例程都弄好了，但是删除全部为n的例程还是不对，可以继续求教下嘛？

user: user-1
content: #include "stdio.h" #include "stdlib.h" #include "malloc.h"  typedef struct node { 	int D; 	node *next;//to back }list;  //单链表例程 void init_single(list *&L); void creatlist_single(list *&L, int n); void printlist_single(list *&L); list* findlist_single(list *&L, int n);//用于发现一个节点的前驱元.n为要发现的节点 void delelist_single(list *&L, int n);//删除为n的 void delelist_all(list *&L, int n);//删除所有为n的 void cutlist_single(list *&L, int n);//插入例程  int main() { 	int n, m; 	list *L;//相当于head指针 	scanf("%d", &n);//确定链表长度 	creatlist_single(L, n); 	printlist_single(L); 	scanf("%d", &m);//要删除的数 	delelist_single(L, m); 	printlist_single(L); 	//delelist_all(L,m); 	//printlist_single(L); 	return 0; }   void init_single(list *&L)//has been done { 	L = (list*)malloc(sizeof(list)); 	L->next = NULL; }  void creatlist_single(list *&L, int n)//has been done { 	list *s, *r; 	init_single(L); 	r = L; 	while (n--) 	{ 		s = (list*)malloc(sizeof(list)); 		scanf("%d", &s->D); 		r->next = s; 		r = r->next;//important!   is right!!! 	} 	r->next = NULL; }  void printlist_single(list *&L)//has been done { 	list *p; 	p = L->next; 	while (p != NULL) 	{ 		printf("%d", p->D); 		p = p->next; 	} 	printf("\n"); }  list* findlist_single(list *&L, int n)//此例程用于寻找一个节点的前驱元 { 	list *head; 	list *p1, *p2; 	int tag = 0;//if find,tag=1,else tag=0,return NULL; 	head = L; 	p1 = head;    //注意这里，初始化不应该是p1=head->next,因为循环中一开始就p1=p1->next; 	while (p1 != NULL) 	{ 		p1 = p1->next; 		p2 = p1; 		p2 = p2->next; 		if (p2->D == n) 		{ 			tag = 1; 			break; 		} 	} 	if (tag == 1) 		return p1; 	else 		return NULL; }  void delelist_single(list *&L, int n)//has been done { 	list *p1, *p2, *head; 	head = L; 	p1 = findlist_single(head, n); 	if (p1 != NULL) 	{ 		/*p1 = p1->next; 		p2 = p1; 		p1 = p2->next;*/  		p2 = p1->next;     		p1->next = p2->next;   //这里应该将前一元素的next指向跳过删除的元素  		free(p2); 	} }  void delelist_all(list *&L, int n) { 	list *p1, *p2, *p3; 	list *head; 	head = L; 	p1 = head->next; 	while (p1 != NULL) 	{ 		p2 = findlist_single(head, n); 		if (p2 != NULL) 		{ 			p2 = p2->next; 			p3 = p2; 			p2 = p3->next; 			free(p3); 		} 		p1 = p1->next; 	} }