【问题标题】:Inserting same node twice in LinkedList triggers infinite loop在 LinkedList 中两次插入同一个节点会触发无限循环
【发布时间】:2021-03-16 05:53:52
【问题描述】:

我试图理解为什么在单链表中两次插入同一个节点会导致无限循环。

我试图插入最后一个节点作为新的头节点。但是当我运行代码时,它开始了一个我可以看到的无限循环,因为我在最后调用了一个打印节点的方法。这是我的代码。

class Node:
    def __init__(self, data):
        self.data = data
        self.next = None


class LinkedList:
    def __init__(self):
        self.head = None

    def insertLast(self, newNode):
        if self.head is None:
            self.head = newNode
        else:
            lastNode = self.head
            while True:
                if lastNode.next is None:
                    break
                lastNode = lastNode.next
            lastNode.next = newNode

    def insertHead(self, newNode):
        # x, y ,z. => new head, x,y,z
        if self.head is None:
            print("List is empy please call inserlast()")
        else:

            currentHead = self.head
            self.head = newNode
            self.head.next = currentHead

    def printList(self):
        if self.head is None:
            print("EMPTY List. No Data found!")
            return
        else:
            currentNode = self.head
            while True:
                print(currentNode.data)
                currentNode = currentNode.next
                if currentNode is None:
                    break


node1 = Node("Head")
node2 = Node("Some Data")
node3 = Node("Some More Data")

# I am adding this node at the end of the list
newnode1 = Node("New Head")

linkedList = LinkedList()

# create a new linked list by inserting at end
linkedList.insertLast(node1)
linkedList.insertLast(node2)
linkedList.insertLast(newnode1)

# using a node i have already added in the list as New head of the list
linkedList.insertHead(newnode1)
linkedList.printList()

【问题讨论】:

    标签: python linked-list singly-linked-list


    【解决方案1】:

    简而言之,根据您的代码,您面临的无限循环是由于The linked list does not arrange the nodes physically, it just tells each node which node is next.

    让我们详细解释一下:

    如图所示,每个节点都有一个next 属性,该属性由LinkedList 设置为下一个。

    启动节点后

    node1.next mentions to None
    node2.next mentions to None
    newnode1.next mentions to None
    

    创建链表后

    node1.next mention to Node2
    node2.next mention to Newnode1
    newnode1.next mention to None
    

    再次插入Newnode1作为头部后,链表集合Nownode1.next提到Node1,孔图变为:

    node1.next mention to Node2
    node2.next mention to Newnode1
    newnode1.next mention to Node1
    

    因此,它变成了一个闭环

    The linked list does not arrange the nodes physically, it just tells each node which node is next.
    

    这就是你面临的无限循环的解释。

    祝你好运

    【讨论】:

      【解决方案2】:

      当您将现有节点重新添加到列表中时,您不会对已引用重新添加节点的现有节点执行任何操作。在您的情况下,您现在在列表末尾有一个节点,其 next 指向刚刚成为 head 的节点,所以现在您的列表是循环的,这将导致任何尝试尝试的函数遍历列表到 infaloop。

      我能想到三种方法来解决这个问题,我会把最好的留到最后:

      1. 添加循环检测逻辑,以防止您在列表变为循环时发生 infalooping(即打破循环或在您回到您已经去过的某个地方后停止遍历)。这是不平凡的,IMO 不是一个很好的解决方案;最好从一开始就防止列表被破坏,而不是不断检查它是否需要修复。

      2. 添加removeNode 函数以确保给定节点已从列表中完全删除(即通过扫描整个列表以查看其他节点(如果有)引用给定节点,并调整指针以跳过它)。然后,您可以通过首先删除它来安全地重新插入节点。注意:如果调用者传递给你一个属于不同列表的节点,你仍然会遇到麻烦,因为你无法找到另一个列表!通过构建列表,然后将每个节点的节点插入另一个,循环结构仍然是可能的。

      3. 根本不允许列表类的调用者访问实际节点;让他们插入值(而不是节点),这样您就可以确保他们永远不会给您一个带有奇怪指针值的节点(一个属于另一个列表的节点,一个指向自身的节点等)。指针应该完全在您的链表类内部,而不是调用者可能搞砸的东西。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2021-07-24
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2016-01-16
        • 2016-11-21
        • 1970-01-01
        相关资源
        最近更新 更多