#include"list.h"
//买一个结点
pNode BuyNode(DataType d)
{
pNode tmp=(pNode)malloc(sizeof(Node));
if (tmp == NULL)
exit(0);
tmp->data = d;
tmp->next = NULL;
return tmp;
}
//销毁链表
void DestroyList(pList* pplist)
{
pList cur=*pplist;
pList del;
assert(pplist);
while (cur != NULL)
{
del = cur;
cur = cur->next;
free(del);
}
del = NULL;
*pplist = NULL;
}
//尾加 用cur指针找到最后一个结点 然后将新结点添加到cur后
void PushBack(pList* pplist, DataType d)
{
pList cur = *pplist;
pList tmp;
assert(pplist);
tmp = BuyNode(d);
if (*pplist == NULL)
{
*pplist = tmp;
}
else
{
while (cur->next)
{
cur = cur->next;
}
cur->next = tmp;
}
}
//尾删
void PopBack(pList* pplist)
{
assert(pplist);
if (*pplist == NULL)
{
return;
}
else if((*pplist)->next== NULL)
{
free(*pplist);
*pplist = NULL;
}
else
{
pList del = *pplist;
while (del->next->next)
{
del = del->next;
}
free(del->next);
del->next= NULL;
}
}
//头加
void PushFront(pList* pplist, DataType d)
{
pList tmp;
assert(pplist);
tmp = BuyNode(d);
if (*pplist == NULL)
{
*pplist = tmp;
}
else
{
tmp->next = (*pplist);
(*pplist) = tmp;
}
}
//头删
void PopFront(pList* pplist)
{
pList del = *pplist;
assert(pplist);
if (*pplist == NULL)
return;
else
{
del = *pplist;
(*pplist) = (*pplist)->next;
free(del);
del = NULL;
}
}
//打印
void PrintList(pList plist)
{
pList tmp=plist;
if (plist == NULL)
return;
else
{
while (tmp->next)
{
printf("%d->", tmp->data);
tmp = tmp->next;
}
printf("%d\n", tmp->data);
}
}
//得到链表长度
int GetListLength(pList plist)
{
pList cur = plist;
int ret=0;
if (plist != NULL)
{
while (cur)
{
ret++;
cur = cur->next;
}
}
return ret;
}
//按值查询,返回结点地址
pNode Find(pList plist, DataType d)
{
if (plist == NULL)
return NULL;
else
{
pList tmp = plist;
while (tmp&&tmp->data != d)
{
tmp = tmp->next;
}
return tmp;
}
}
//按地址插入
void Insert(pList* pplist, pNode pos, DataType d)
{
pList cur = *pplist;
assert(pplist);
if (pos == NULL)
{
return;
}
else
{
while (cur&&cur!= pos)
{
cur = cur->next;
}
if (cur == pos)
{
pList tmp = BuyNode(d);
tmp->next = pos->next;
pos->next=tmp;
}
}
}
//按地址删除
void Erase(pList *pplist, pNode pos)
{
pList cur = *pplist;
assert(pplist);
if (pos == NULL)
{
return;
}
else
{
if (*pplist == NULL)
return;
else
{
//删除第一个
if (*pplist == pos)
{
(*pplist) = (*pplist)->next;
free(pos);
pos = NULL;
}
else
{
while (cur->next&&cur->next != pos)
{
cur = cur->next;
}
if (cur->next == pos)
{
cur->next = cur->next->next;
free(pos);
pos = NULL;
}
}
}
}
}
//按值移除
void Remove(pList* pplist, DataType d)
{
pList cur=*pplist;
pList del;
assert(pplist);
if (*pplist == NULL)
return;
else
{
//删除第一个
if ((*pplist)->data == d)
{
del = *pplist;
(*pplist) = (*pplist)->next;
free(del);
del = NULL;
}
else
{
while (cur->next&&cur->next->data != d)
{
cur = cur->next;
}
if (cur->next != NULL)
{
del = cur->next;
cur->next = cur->next->next;
free(del);
del = NULL;
}
}
}
}
//移除所有这样的值
void RemoveAll(pList* pplist, DataType d)
{
pList cur ;
pList cur2 = *pplist;
pList del;
assert(pplist);
if (*pplist == NULL)
return;
while (cur2)
{
if ((*pplist)->data == d)
{
del = *pplist;
*pplist = (*pplist)->next;
//把头指针移动到新的头
cur2 = *pplist;
free(del);
del = NULL;
}
else
{
cur = cur2;
while (cur->next&&cur->next->data != d)
{
cur = cur->next;
}
if (cur->next != NULL)
{
del = cur->next;
cur->next = cur->next->next;
cur2 = cur;
free(del);
del = NULL;
}
else
{
//执行这条语句证明再没有需要删除的东西了,所以退出循环
cur2 = NULL;
}
}
}
}
//面试题
//逆序打印单项链表====非递归方法
void PrintTailToHead(pList plist)
{
pList tail = NULL;
pList cur=plist;
if (plist == NULL)
return;
else
{
while (cur != tail)
{
while (cur->next != tail)
{
cur = cur->next;
}
printf("%d ", cur->data);
tail = cur;
cur = plist;
}
}
}
//删除无头非尾结点
void DelNodeNotTail(pNode pos)
{
pList del;
if (pos == NULL)
return;
else
{
del = pos->next;
pos->data = pos->next->data;
pos->next = pos->next->next;
free(del);
del = NULL;
}
}
//插入结点
void InsertNode(pNode pos, DataType d)
{
pList tmp;
if (pos == NULL)
return;
else
{
tmp = BuyNode(pos->data);
tmp->next = pos->next;
pos->next = tmp;
pos->data = d;
}
}
//环
void JosephusCycle(pList* pplist, int k)
{
pList del;
pList cur = *pplist;
int count=0;
assert(pplist);
if (*pplist == NULL)
return;
else
{
while (cur != cur->next)
{
count++;
if (count == k)
{
del = cur->next;
cur->data = cur->next->data;
cur->next = cur->next->next;
free(del);
del = NULL;
count = -1;
}
cur = cur->next;
}
*pplist = cur;
}
}
//逆置链表
void ReverseList(pList* pplist)
{
pList tmp1;
pList tmp2;
pList tmp3;
assert(pplist);
if ((*pplist) == NULL || (*pplist)->next == NULL)
return;
else
{
tmp1 = *pplist;
tmp2 = tmp1->next;
tmp3 = tmp2->next;
tmp1->next = NULL;
while(tmp2!=NULL)
{
tmp2->next = tmp1;
tmp1 = tmp2;
tmp2 = tmp3;
if(tmp3!=NULL)
tmp3 = tmp3->next;
}
*pplist=tmp1;
}
}
//链表冒泡排序
void BubbleSort(pList plist)
{
pList cur;
pList cur_next ;
int n = GetListLength(plist);
int flag=0;
if (plist == NULL||plist->next==NULL)
{
return;
}
else
{
for (int i=0; i < n-1; i++)
{
for (int j = 0; j < n - 1 - i; j++)
{
int c = j;
cur = plist;
cur_next = cur->next;
while (c--)
{
cur=cur->next;
cur_next = cur->next;
}
if (cur->data < cur_next->data)
{
int tmp = cur->data;
cur->data = cur_next->data;
cur_next->data=tmp;
}
}
}
}
}
//合并有序链表
pList Merge(pList p1, pList p2)
{
pList ret=NULL,cur=NULL;
while (p1&&p2)
{
if (p1->data > p2->data)
{
if (ret == NULL)
{
ret = p2;
cur = ret;
}
else
{
cur->next = p2;
cur = cur->next;
}
p2 = p2->next;
}
else
{
if (ret == NULL)
{
ret = p1;
cur = ret;
}
else
{
cur->next = p1;
cur = cur->next;
}
p1 = p1->next;
}
}
if (p1 != NULL)
{
while (p1)
{
cur->next = p1;
cur = cur->next;
p1 = p1->next;
}
}
if (p2!= NULL)
{
while (p2)
{
cur->next = p2;
cur = cur->next;
p2 = p2->next;
}
}
return ret;
}
递归 合并有序链表(升序)
pList Merge_R(pList p1, pList p2)
{
pList MergeHead;
if (p1 == NULL)
return p2;
if (p2 == NULL)
return p1;
if (p1->data > p2->data)
{
MergeHead = p2;
MergeHead->next = Merge_R(p1, p2->next);
}
else
{
MergeHead = p1;
MergeHead->next = Merge_R(p1->next, p2);
}
return MergeHead;
}
//寻找中间结点
pNode FindMidNode(pList plist)
{
pList fast=plist;
pList slow=plist;
while (fast&&fast->next)
{
slow = slow->next;
fast = fast->next->next;
}
return slow;
}
//寻找倒数第K个结点
pNode FindLastKNode(pList plist, int k)
{
pList fast = plist;
pList slow = plist;
if (plist == NULL)
{
return NULL;
}
while (k--&&fast)
{
fast = fast->next;
}
while (fast)
{
fast = fast->next;
slow = slow->next;
}
return slow;
}
//判断是否是环
pNode IsCircle(pList plist)
{
pNode fast=plist;
pNode slow=plist;
if (plist==NULL)
{
return NULL;
}
while (fast&&fast->next)
{
slow = slow->next;
fast = fast->next->next;
if (fast == slow)
return fast;
}
return NULL;
}
//得到环的长度
int GetCircleLength(pNode meet)
{
pNode tmp;
int count = 1;
if (meet == NULL)
{
return 0;
}
tmp = meet->next;
while (tmp!=meet)
{
tmp = tmp->next;
count++;
}
return count;
}
//得到环的开始
pNode GetCycleEntryNode(pList plist, pNode meet)
{
pList cur1=plist;
pList cur2=meet;
if (meet == NULL || plist == NULL)
return NULL;
while (cur1 && cur2)
{
if (cur1 == cur2)
return cur1;
cur1 = cur1->next;
cur2 = cur2->next;
}
return NULL;
}
//判断是否交叉 交叉返回真 不交叉返回假
int CheckCross(pList p1, pList p2)
{
pList longlist = p1;
pList shortlist = p2;
int len1=0;
int len2=0;
int subb;
if (p1==NULL || p2==NULL)
return 0;
while (longlist)
{
len1++;
longlist = longlist->next;
}
while (shortlist)
{
len2++;
shortlist = shortlist->next;
}
subb = len1 - len2;
if (subb < 0)
{
subb = -subb;
longlist = p2;
shortlist = p1;
}
else
{
longlist = p1;
shortlist = p2;
}
while (subb--)
{
longlist = longlist->next;
}
while (longlist!=NULL && shortlist!=NULL)
{
if (longlist == shortlist)
{
return 1;
}
longlist = longlist->next;
shortlist = shortlist->next;
}
return 0;
}
//得到交叉点
pNode GetCrossNode(pList p1, pList p2)
{
pList longlist = p1;
pList shortlist = p2;
int len1 = 0;
int len2 = 0;
int subb;
if (p1 == NULL || p2 == NULL)
return 0;
while (longlist)
{
len1++;
longlist = longlist->next;
}
while (shortlist)
{
len2++;
shortlist = shortlist->next;
}
subb = len1 - len2;
if (subb < 0)
{
subb = 0 - subb;
longlist = p2;
shortlist = p1;
}
else
{
longlist = p1;
shortlist = p2;
}
while (subb--)
{
longlist = longlist->next;
}
while (longlist != NULL && shortlist != NULL)
{
if (longlist == shortlist)
{
return shortlist;
}
longlist = longlist->next;
shortlist = shortlist->next;
}
return NULL;
}
//升级版(复杂情况)====如果交叉返回交叉点 反正返回NULL
pNode ComplexSituation(pList p1, pList p2)
{
pList meet1 = IsCircle(p1);
pList meet2 = IsCircle(p2);
//有一个为空返回空
if (p1 == NULL || p2 == NULL)
return NULL;
//两个都是无环单链表
if (meet1 == NULL&&meet1 == NULL)
{
return GetCrossNode(p1, p2);
}
//两个都是环 可能相交,也可能不相交
else if (meet1!= NULL&&meet2 != NULL)
{
//先确定是否是同一个环内
pList cur = meet1->next;
while (cur != meet1&&cur!=meet2)
{
cur = cur->next;
}
//cur回到了原点,说明meet1和meet2不是在同一个环内 所以原p1和p2没有相交点
if (cur == meet1)
{
return NULL;
}
//反正p1和p2有相交点,且里面带有环
else
{
//在一个相遇的地方断开,然后形成了一个交叉的链表,然后得到交叉点,然后在重新连接起来
pList tmp = meet1->next;//保存下一个结点
meet1->next = NULL;//断开
pList ret = GetCrossNode(p1, p2);//得到交叉点
meet1->next = tmp;//重新连接结点
return ret;
}
}
else//一个环和一个无环单链表没有交点
{
return NULL;
}
}
//15. 求两个有序单链表交集(差集)。
void UnionSet(pList p1, pList p2)
{
if (p1 == NULL || p2 == NULL)
{
return;
}
while (p1&&p2)
{
if (p1->data == p2->data)
{
printf("%d ", p1->data);
p1 = p1->next;
p2 = p2->next;
}
else if (p1->data < p2->data)
{
p1 = p1->next;
}
else
{
p2 = p2->next;
}
}
}
//买一个复杂结点
ComplexNode* BuyComplexNode(DataType d)
{
ComplexNode* tmp = (ComplexNode*)malloc(sizeof(ComplexNode));
tmp->data = d;
tmp->next = NULL;
tmp->random = NULL;
return tmp;
}
//打印复杂链表
void PrintComplexList(ComplexNode* plist)
{
ComplexNode* cur = plist;
while (cur)
{
printf("%d:", cur->data);
if (cur->random==NULL)
{
printf("(NU)->");
}
else
{
printf("(%d)->", cur->random->data);
}
cur = cur->next;
}
printf("\n");
}
//复制复杂链表
ComplexNode* CopyComplexList(ComplexNode* plist)
{
ComplexNode* cur=plist;
ComplexNode* cur_R = plist;
ComplexNode* tmp=NULL;
ComplexNode* ret=NULL;
if (plist == NULL)
{
return NULL;
}
else
{
//创建复制结点,并插入到原链表,合并新老链表
while (cur)
{
tmp = (ComplexNode*)malloc(sizeof(ComplexNode));
tmp->data = cur->data;
tmp->next = cur->next;
cur->next = tmp;
cur = cur->next->next;
}
//根据老链表,建立新链表的随机指针的关系,随机指针的复制要在结点复制之后
cur = plist;
while (cur)
{
tmp = cur->next;
if (cur->random != NULL)
{
tmp->random = cur->random->next;
}
else
tmp->random = NULL;
cur = cur->next->next;
}
//从合并拆出新复制的结点,并连成链表
cur = plist;
ret = cur->next;
while (cur)
{
cur_R = cur->next;
cur->next = cur->next->next;
cur = cur->next;
if (cur!= NULL)
{
cur_R->next = cur->next;
cur_R = cur_R->next;
}
else
{
cur_R->next = NULL;
}
}
//返回已复制的新链表
return ret;
}
}
链表面试题大全
最新推荐文章于 2022-09-25 16:36:07 发布