C 在链表中保留所有数字的一个匹配项
我想找到一种算法,使用递归在链表中保持每个数字只出现一次 ,我知道递归根本不是解决这个问题的好选择,但我想尝试一下 如需更多校准:C 在链表中保留所有数字的一个匹配项,c,recursion,linked-list,C,Recursion,Linked List,我想找到一种算法,使用递归在链表中保持每个数字只出现一次 ,我知道递归根本不是解决这个问题的好选择,但我想尝试一下 如需更多校准: input : 1->2->1->3->3->2->1->4 output : 1->2->3->4 这是我制作的一个程序,使用递归只保留给定数字的一次出现,但我无法开发它来解决整个问题。我能得到一些帮助吗?提前谢谢 list* wipe(list* head,int val) { if(hea
input : 1->2->1->3->3->2->1->4
output : 1->2->3->4
这是我制作的一个程序,使用递归只保留给定数字的一次出现,但我无法开发它来解决整个问题。我能得到一些帮助吗?提前谢谢
list* wipe(list* head,int val)
{
if(head==NULL) return head;
static int occ=1;
if(head->data == val)
{
if(occ-- < 1)
{
list* temp=head;
head=head->next;
free(temp);
return wipe(head,val);
}
}
head->next=wipe(head->next,val);
return head;
}
list*擦除(list*head,int val)
{
如果(head==NULL)返回head;
静态int occ=1;
如果(头部->数据==val)
{
如果(occ--<1)
{
列表*温度=头部;
头部=头部->下一步;
免费(临时);
返回擦拭(头部,val);
}
}
头部->下一步=擦拭(头部->下一步,val);
回流头;
}
occ仅在您执行函数时设置为1,因此从第二次(head->data==val)
为真,无论测试(occ--<1)
为真,这不是正确的方法
您可以执行类似操作,将列表修改为仅包含唯一编号:
#include <stdio.h>
#include <stdlib.h>
typedef struct List {
struct List * next;
int data;
} List;
/* remove from l all the cells having data equals to v */
List * wipe(int v, List * l)
{
if (l == NULL)
return l;
else if (l->data != v) {
l->next = wipe(v, l->next);
return l;
}
else {
List * n = l->next;
free(l);
return wipe(v, n);
}
}
/* modify the argument to not have duplicated numbers */
void simplify(List * l)
{
while (l != NULL) {
l->next = wipe(l->data, l->next);
l = l->next;
}
}
/* helper function to construct a list */
List * mk(int v, List * n) {
List * l = malloc(sizeof(*l));
l->data = v;
l->next = n;
return l;
}
/* print the list */
void pr(List * l)
{
while (l != NULL) {
printf("%d ", l->data);
l = l->next;
}
putchar('\n');
}
int main()
{
List * l = mk(1, mk(2, mk(1, mk(3, mk(3, mk(2, mk(1, mk(4, NULL))))))));
pr(l);
simplify(l);
pr(l);
/* free the rest of the list */
while (l) {
List * n = l->next;
free(l);
l = n;
}
return 0;
}
这样就有了O(n2)的复杂性
一种更快的方法是首先对列表中的元素进行排序,然后删除重复的元素,从而允许具有排序的复杂性,因此可能是O(n*log(n))(可能使用临时数组进行排序)如果我理解正确,您需要一个递归函数,该函数仅在列表中没有数字时才将数字附加到列表中 如果是这样的话,那么递归函数可以如下所示
int append( list **head, int val )
{
if ( *head == NULL )
{
*head = malloc( sizeof( **head ) );
int success = *head != NULL;
if ( success )
{
( *head )->data = val;
( *head )->next = NULL;
}
return success;
}
else if ( ( *head )->data != val )
{
return append( &( *head )->next, val );
}
else
{
return 0;
}
}
append( &head, val );
如果你有这样的声明
list *head = NULL;
然后可以调用该函数,例如
int append( list **head, int val )
{
if ( *head == NULL )
{
*head = malloc( sizeof( **head ) );
int success = *head != NULL;
if ( success )
{
( *head )->data = val;
( *head )->next = NULL;
}
return success;
}
else if ( ( *head )->data != val )
{
return append( &( *head )->next, val );
}
else
{
return 0;
}
}
append( &head, val );
或者
if ( append( &head, val ) )
{
printf( "The value %d is appended to the list.\n", val );
}
遍历并执行某种修改的插入排序,以将数字插入到新的链表中。修改为t不会插入重复的数字。@学习者整个问题是什么?occ仅在您执行该函数时设置为1,因此从第二次开始
(head->data==val)
无论测试值(occ--<1)
将为真=>无法work@VladfromMoscow整个问题是保持所有数字只出现一次,我只找到了保持一个给定数字出现一次的解决方案,我想对链接列表中的所有数字做同样的处理。解决方案很简单,请参见答案