「这是我参与11月更文挑战的第16天,活动详情查看:2021最后一次更文挑战」
上一篇文章中,我们介绍了如何用PHP实现单链表和循环链表,链表实现
今天说一下用PHP判断链表是否有环。
同时这也是LeetCode的141题环形链表
快慢指针的思路
在操场跑步时,有人跑的块,有人跑的慢,如果两人一直没有相遇过,就说明跑道不是一个环形。如果是一个环形,跑的快的人,肯定是可以追上跑得慢的人,然后两人相遇。
如果把跑道比作链表环,跑步的人比作不断移动的指针,根据这个思路,我们可以把两个指针从头节点出发,一个慢指针每次移动1步,一个快指针每次移动两步,如果链表有环的话,快指针肯定是可以追到慢指针的。
下面我们看下代码:
第29-30行代码,我们首先判断链表是否为空,和链表头节点的下一个节点是否为空,这时候链表只有一个节点,是不能有环的。
第32、33行代码,为慢指针和快指针赋初始值,为什么两个指针不在同一个起始位置呢?因为我们是判断两个指针相等时,即为链表有环,如果我们把两个指针放在同一个起始位置,那么刚开始循环时,就会判定两个指针相等,就会退出循环。
第35-37行代码,如果链表没有环的话,那么某一个节点的next指针就会指向null,所以我们需要不断移动的指针是否为null的情况。我们通过判断快指针当前的信息,和快指针下一个节点的信息,就可以知道链表中是否存在指向null的情况。
第38、39行代码,为快慢指针移动,慢指针每次移动一次,快指针每次移动两次。
就这样不断循环,直到判断出链表是否有环。
时间复杂度:O(N),空间复杂度:O(1)。