判断单链表是否存在环:使用快慢指针的方法,分别设一个slow和fast指针,slow指针每次遍历1个节点,而fast指针每次遍历2个节点,;若fast指针遍历到NULL,说明该链表没有环,当slow==fast(相遇处)指针时,说明该链表存在环。
若该链表存在环:设定一个start指针指向头结点,meet指针指向slow和fast指针相遇处,将start指针和meet指针遍历,start指针和meet指针相等时,则该地址为环的入口地址。
#include<stdio.h>
#include<stdlib.h>
typedef struct node
{
int data;
struct node *next;
}Node;
Node *CheckCycle(Node *head)//检测链表是否有环
{
Node *fast,*slow;
Node *start,*meet;
fast=head;
slow=head;
while(1)
{
fast=fast->next ? fast->next:NULL;
if(NULL==fast)
break;
fast=fast->next ? fast->next:NULL;//fast node move 2 steps each time
if(NULL==fast)
break;
slow=slow->next ? slow->next:NULL;//slow node move 1 step each time
if(fast==slow)
break;
}
if(fast==NULL)
return NULL;
//环的入口节点
start=head;
meet=fast;//meet=slow
while(start!=meet)//遍历指针,直到start指针和meet指针相等
{
start=start->next;
meet=meet->next;
}
return start;//return meet
}
Node *Creat()//创建链表
{
Node *head,*p,*s;
int n,flag=1;
head=(Node *)malloc(sizeof(Node));
p=head;
while(flag)
{
printf("please input the data:");
scanf("%d",&n);
s=(Node *)malloc(sizeof(Node));
s->data=n;
p->next=s;
p=s;
printf("continue inputing data?(1/0):");
scanf("%d",&flag);
}
head=head->next;
p->next=head->next;//与头节点的下一个节点构成环(第二个节点构成环)
//p->next=NULL;//无环
return head;
}
void main()
{
Node *head,*entrance;
head=Creat();
entrance=CheckCycle(head);
if(entrance==NULL)
printf("该链表无环\n");
else
printf("该链表有环,%d节点为环的入口节点\n",entrance->data);
}