拆分LinkedList

时间:2018-10-05 23:35:29

标签: javascript linked-list

我对以下函数有疑问,该函数将LinkedList分成两个大小相等的列表。我知道对于“慢”列表,我们如何遍历原始列表,直到“快速”为空(那时,“慢”将通过列表的一半)。但是,我不了解“头”如何仅成为列表的前半部分。我看不到直接修改head的代码中的任何地方。抱歉,这是一个幼稚的问题-LinkedLists的新功能!

function splitLL(head) {
        let prev = null;
        let slow = head;
        let fast = head;
        while(fast !== null && fast.next !== null) {
            prev = slow;
            slow = slow.next;
            fast = fast.next.next;
        }
        prev.next = null
        console.log("This is first half", head);
        console.log("This is second half", slow);
    }

2 个答案:

答案 0 :(得分:1)

不需要修改标头,因为原始列表的标头仍然是较短列表之一的标头。例如,如果原始列表为:

head -> node1 -> node2 -> node3 -> null

现在分手的列表将是

head  -> node1 -> null
node2 -> node3 -> null

原始头部不需要修改。有点像把绳子切成两半。一半的起点是整个绳索的原始起点。

答案 1 :(得分:0)

JavaScript正在传递对对象的引用。运行prev.next = null时,它将切断head的一半。 prev是对链接列表中对象的引用,编辑prev编辑head

这里是带注释的源,它们在值更改时逐步进行。

let ll = {
    id: 1,
    next: { id: 2, next: { id: 3, next: { id: 4, next: null } } }
};

function splitLL(head) {
    let prev = null;
    let slow = head; // <= slow is now a reference to node 1
    let fast = head; // <= fast is now a reference to node 1
    while (fast !== null && fast.next !== null) {
        prev = slow; // prev = node 1
                     // next loop prev = node 2
        slow = slow.next; // slow = node 2
                          // next loop slow = node 3
        fast = fast.next.next;  // fast = node 3
                                // next loop fast = node 4
    }
    // when fast is equal to node 4 the while loop ends

    prev.next = null; // this is now node 2, by setting this to null it edits head
    console.log("This is first half", head);
    console.log("This is second half", slow);
}
splitLL(ll);

在控制台中播放javascript对象。您会注意到,通过将一个对象分配给两个变量并编辑一个变量,您可以编辑原始对象。