准备:
// 链表的节点
typedef struct Node
{
TYPE data; // 数据域
struct Node* next; // 指针域,指向下一个节点
}Node;
// 创建节点
Node* create_node(TYPE data)
{
Node* node = malloc(sizeof(Node));
node->data = data;
node->next = NULL;
return node;
}
// 链表
typedef struct List
{
Node* head;
Node* tail;
}List;
// 创建链表
List* create_list(void)
{
List* list = malloc(sizeof(List));
list->head = NULL;
list->tail = NULL;
}
- 练习1:链表逆序,在原链表的基础上调整
void reverse_list(List* list)
{
if(list->head == list->tail)
return;
Node* n1 = NULL;
Node* n2 = list->head;
list->tail = n2;
while(n2)
{
Node* n3 = n2->next;
n2->next = n1;
n1 = n2;
n2 = n3;
}
list->head = n1;
}
- 练习2:显示链表的倒数第K个值
Node* show_list_k(List* list,int k)
{
/*
int len = size_list(list);
if(k <= 0 || k > len)
return NULL;
Node* node = list->head;
for(int i=0; i<len-k; i++)
{
node = node->next;
}
return node;
*/
if(0 >= k) return NULL;
Node* n1 = list->head;
for(int i=0; i<k-1; i++)
{
n1 = n1->next;
if(NULL == n1)
return NULL;
}
n1 = n1->next;
Node* n2 = list->head;
while(n1)
{
n2 = n2->next;
n1 = n1->next;
}
return n2;
}
- 练习3:合并两个有序链表,并依然保持有序
Node* _merge_list(Node* n1,Node* n2)
{
/*
if(NULL == n1) return n2;
if(NULL == n2) return n1;
if(n1->data < n2->data)
{
n1->next = _merge_list(n1->next,n2);
return n1;
}
else
{
n2->next = _merge_list(n1,n2->next);
return n2;
}
*/
}
List* merge_list(List* l1,List* l2)
{
/*
List* list = create_list();
list->head = _merge_list(l1->head,l2->head);
list->tail = l1->tail->next?l2->tail:l1->tail;
return list;
*/
List* list = create_list();
Node *n1 = l1->head ,*n2 = l2->head;
if(n1->data < n2->data)
{
list->head = list->tail = n1;
n1 = n1->next;
}
else
{
list->head = list->tail = n2;
n2 = n2->next;
}
while(n1&&n2)
{
if(n1->data < n2->data)
{
list->tail->next = n1;
n1 = n1->next;
}
else
{
list->tail->next = n2;
n2 = n2->next;
}
list->tail = list->tail->next;
}
if(n1)
{
list->tail->next = n1;
list->tail = l1->tail;
}
else
{
list->tail->next = n2;
list->tail = l2->tail;
}
return list;
}
- 练习4:判断链表中是否有环
bool is_ring(List* list)
{
Node* n1 = list->head;
Node* n2 = n1->next;
while(n2 && n2->next)
{
if(n1 == n2 || n1 == n2->next)
{
return true;
}
n1 = n1->next;
n2 = n2->next->next;
}
return false;
}
- 练习5:找出环形链表的入口
Node* in_ring(List* list)
{
for(Node* i=list->head->next; i!=NULL; i=i->next)
{
for(Node* j=list->head; j!=i; j=j->next)
{
if(j == i->next)
{
return j;
}
}
}
return NULL;
}
- 练习6:判断是否是Y型链表,如果是则返回入口
Node* is_Ylist(List* l1,List* l2)
{
int len1 = size_list(l1);
int len2 = size_list(l2);
Node *n1 = l1->head , *n2 = l2->head;
if(len1 < len2)
{
n1 = l2->head;
n2 = l1->head;
}
int i = abs(len1-len2);
while(i--)n1 = n1->next;
while(n1 && n2)
{
if(n1 == n2)
return n1;
n1 = n1->next;
n2 = n2->next;
}
return NULL;
}
- 练习7:删除链表中的重复节点
void del_repeat(List* list)
{
for(Node* i=list->head; NULL!=i->next; i=i->next)
{
for(Node* j=i; NULL!=j&&NULL!=j->next; j=j->next)
{
if(i->data == j->next->data)
{
Node* temp = j->next;
j->next = temp->next;
free(temp);
}
}
}
}