我编写了一个代码来检查链表输入是否有循环,但是我的方法与Internet上的方法有些不同,这行得通吗?
/**
* Definition for singly-linked list.
* struct ListNode {
* int val;
* struct ListNode *next;
* };
*/
bool hasCycle(struct ListNode *head) {
struct ListNode *p1,*p2;
p1 = head;
if(p1 == NULL) return 0;
for(p1 = head;p1->next != NULL;p1 = p1->next){
for(p2 = p1->next;p2 != NULL;p2=p2->next){
if(p2 == p1) return 1;
if (p2 == NULL) return 0;
}
}
return 0;
}
答案 0 :(得分:0)
您回来太早了:
for(p2 = p1->next;p2 != NULL;p2=p2->next){
if(p2 == p1) return 1;
if (p2 == NULL) return 0;
}
当p2
变为NULL时,仅表示没有循环涉及p1
,根本没有任何循环。通过在此处返回0,您只需检查头节点是否存在一个循环。
摆脱多余的回报,所以搜索完所有内容后,您只会返回0。
for(p1 = head;p1->next != NULL;p1 = p1->next){
for(p2 = p1->next;p2 != NULL;p2=p2->next){
if(p2 == p1) return 1;
}
}
return 0;
编辑:
这仍然不起作用,因为如果循环不涉及第一个节点,它将进入无限循环。处理此问题的正确方法是对照找到的所有先前节点检查每个节点。这可以通过在访问节点时将其放入列表中来完成。如果在添加列表之前该列表中已经存在一个节点,则您发现了一个循环。
或者,您可以在初始化为0的每个节点中放置一个“ visited”标志。然后遍历设置该标志的列表。如果该标志已经设置,则您有一个循环。