【数据结构】除去线性表中的重复数字

题目:写一个算法将单链表中值重复的结点删除,使所得的结果表中各结点值均不相同。

  刚看到这个题目给我第一个思路是冒泡排序,可以利用冒泡排序的两层循环找出相同的结点,然后free掉。第一层循环是控制循环的次数,第二层循环是控制第n个值和后面值的比较的次数。循环方面还比较好做,在删除结点的时候碰到了一些问题。因为删除结点的时候就相当于把指针指向的空间释放了,这个时候指针链就会断开,不再是一个连续的链表。为了连接链表,还需要额外定义一个变量,来记录释放结点的前一个节点,然后才可以把释放结点的前一个结点连接到释放结点的后一个结点(有点绕口,看代码就知道了)。

  线性表的定义,和创建线性表,读取线性表的代码就不解释了,本人在【数据结构】顺序线性表的构造和存储数据中有写过;

  现在直接贴上核心函数:

 1 //除去重复的值
 2 void deldou(LNode *l)
 3 {
 4     LNode *p,*h,*temp,*q;
 5     int i,j,n;
 6     n = 0;
 7     h = l->next;    
 8     p = h->next;    
 9     while(h->next !=NULL)        //第一层循环控制循环的次数
10     {
11         while(p!=NULL)            //第二层循环控制第i个数对比的次数
12         {
13             if(h->x == p->x)
14             {
15                 temp = p->next;        //为了使释放p的时候p所指向的指针不丢失,
16                 free(p);            //释放p对应的内存
17                 p = temp;        
18                 q->next = p;    //链接线性表,把释放结点的前一个结点和后一个结点连接到一起
19             }
20             else
21             {
22                 q = p;        //得到上一个p节点,为了链接释放结点的后一结点。    
23                 p = p->next;
24             }
25         }
26         h = h->next;
27         p = h->next;
28     }
29 }

代码中定义了*temp,*q;都是为了不让链表断裂而创建的;q记录了释放掉的p的上一个结点,temp记录了释放的p的下一个结点,然后把他们连在一起,整个线性表就不会断裂了;

附上完整代码:

View Code
 1 #include<stdio.h>
 2 #include<stdlib.h>
 3 
 4 typedef struct node
 5 {
 6     int x;
 7     struct node *next;
 8 }LNode;
 9 
10 
11 //函数声明
12 LNode *create_l();
13 void out_l(LNode *l);
14 void deldou(LNode *l);
15 
16 //主函数
17 void main()
18 {
19     LNode *l;
20     l = create_l();
21     out_l(l);
22     deldou(l);
23     out_l(l);
24 }
25 
26 //除去重复的值
27 void deldou(LNode *l)
28 {
29     LNode *p,*h,*temp,*q;
30     int i,j,n;
31     n = 0;
32     h = l->next;    
33     p = h->next;    
34     while(h->next !=NULL)        //第一层循环控制循环的次数
35     {
36         while(p!=NULL)            //第二层循环控制第i个数对比的次数
37         {
38             if(h->x == p->x)
39             {
40                 temp = p->next;        //为了使释放p的时候p所指向的指针不丢失,
41                 free(p);            //释放p对应的内存
42                 p = temp;        
43                 q->next = p;    //链接线性表,把释放结点的前一个结点和后一个结点连接到一起
44             }
45             else
46             {
47                 q = p;        //得到上一个p节点,为了链接释放结点的后一结点。    
48                 p = p->next;
49             }
50         }
51         h = h->next;
52         p = h->next;
53     }
54 }
55 
56 //创建链表
57 LNode *create_l()
58 {
59     LNode *h,*p,*l;
60     int x,n,i;
61     h = (LNode *)malloc(sizeof(LNode));
62     h->next = NULL;
63     p = h;
64     printf("请输入创建链表的长度:");
65     scanf("%d",&n);
66     for(i = 0; i < n; i++)
67     {
68         printf("请输入第%d个值:",i + 1);
69         scanf("%d",&x);
70         l = (LNode *)malloc(sizeof(LNode));
71         l->x = x;
72         l->next = NULL;
73         p->next = l;
74         p = l;
75     }
76     return(h);
77 }
78 
79 //读取链表
80 void out_l(LNode *l)
81 {
82     LNode *p;
83     p = l;
84     p = p->next;
85     while(p!=NULL)
86     {
87         printf("%5d",p->x);
88         p = p->next;
89     }
90     printf("\n");
91 }
posted @ 2012-09-25 21:28  net小伙  阅读(1745)  评论(0编辑  收藏  举报