js实现链表翻转以及检查是否有环

1.翻转一个链表

:input a->b->c->d
:output d->c->b->a

// 链表翻转
const reverseList = function(head) {
    
    
	let prev = null;
	let curr = head;
	while (curr) {
    
    
		[ curr.next, prev, curr ] = [ prev, curr, curr.next ];
	}
	return prev;
};
let a = {
    
    value:'a',next:null}
let b = {
    
    value:'b',next:null}
let c = {
    
    value:'c',next:null}
let d = {
    
    value:'d',next:null}
a.next = b,b.next = c ,c.next =d;
reverseList(a)

2.翻转链表的m节点到n节点

:input a->b->c->d->e->f m=2,n=5
:output a-e->d->c->b->f

const reverseListBetween = function (head, m, n) {
    
    
    let curr = head;
    let prev = null;

    for (let i = 1; i < m; ++i) {
    
    
        [prev, curr] = [curr, curr.next];
    }
    let curr2 = curr;//第m个节点
    let prev2 = prev;
    //开始翻转
    for (let i = m; i <= n; i++) {
    
    
        [curr.next, prev, curr] = [prev, curr, curr.next]
    }
    //prev:第n个节点 ,curr是第N+1个
    if (prev2) {
    
    
        prev2.next = prev;
    } else {
    
    
        head = prev;
    }
    curr2.next = curr;
    return head;
}

3.判断链表是否有环

利用快慢指针

const hasCycle = function (head) {
    
    
    let fast = head;
    let slow = head;

    while (fast.next && fast.next.next) {
    
    
        fast = fast.next.next;
        slow = slow.next;
        if (fast === slow) {
    
    
            return true
        }
    }
    return false;
}

4.如果有环,请返回环的入口

利用特性,fast指针走过的路程是slow指针的2倍
2slow = fast
假设head–>环入口的距离为a,环入口–>fast与slow相遇节点的距离为b,
此节点到环入口的节点距离为c(顺时针考虑)
根据两个指针各自走的路程 代入公式:2(a+b) = a + 2b+ c
=> a = c
表示在快慢指针相遇后,再走c步就能到环入口;从head开始走a步也能到环入口。
所以,在指针相遇后,slow指针继续走,再从头开始走一个新的slow指针,两者相遇时,就是环入口

const detectCycle = function (head) {
    
    
    let fast = head;
    let slow1 = head;
    let slow2 = head;
    let hasCycle = false;
    while (fast.next && fast.next.next) {
    
    
        fast = fast.next.next;
        slow = slow.next;
        if (fast === slow) {
    
    
            hasCycle = true;
            break;
        }
    }
    if (!hasCycle)
        return null;
    while (slow1 !== slow2) {
    
    
        slow1 = slow1.next;
        slow2 = slow2.next;
    }
    return slow1;
}

以上内容 学习自b站JS老毕

猜你喜欢

转载自blog.csdn.net/XIAOLONGJUANFENG/article/details/112801561