Python链表实现:print可访问属性,while循环报NoneType AttributeError
Let's break down why you're hitting that frustrating AttributeError: 'NoneType' object has no attribute 'next'—even though your initial print statement shows a valid value.
What's Breaking Your Code
First, let's look at your current implementation:
def delete(self , value): current = self.head #for debugging proposes print("the next value is: "+str(current.next.value)) #got an error here while current.next: if current.next.value == value: current.next = current.next.next current = current.next
Your print statement runs once, before the loop starts, so it only checks the very first current.next value. The problem creeps in during the loop:
- When you delete a node (e.g., setting
current.next = current.next.next), then immediately runcurrent = current.next, you might end up movingcurrenttoNone(if you deleted the last node in the list). - On the next loop iteration, you try to access
current.next—butcurrentis nowNone, hence the error. - Even if you don't delete a node, once
currentreaches the final node,current.nextisNone, socurrent = current.nextturnscurrentintoNone, and the next loop check crashes.
A Fixed, Robust Delete Function
Here's an improved version that handles edge cases (like deleting the head node, duplicate values, and the end of the list) without triggering the error:
def delete(self, value): # Handle the case where the head itself is the node to delete if self.head is not None and self.head.value == value: self.head = self.head.next return current = self.head # Loop only while current exists AND current has a valid next node while current is not None and current.next is not None: if current.next.value == value: # Remove the target node current.next = current.next.next # Stay at current to check for duplicate values in the next position continue # Only move current forward if we didn't delete a node current = current.next
Key Fixes Explained
- Head Node Handling: We first check if the head is the node to delete—your original code completely missed this scenario.
- Safer Loop Condition: Instead of just checking
current.next, we verify bothcurrent is not Noneandcurrent.next is not Noneto never accessnexton aNoneobject. - Conditional Current Movement: We only move
currentforward if we didn't delete a node. This lets us handle back-to-back duplicate values (e.g., if two consecutive nodes have the value you want to delete).
Example of Your Original Code Failing
Let's say your linked list is 1 -> 3 -> None:
- Initial
currentis1, print showscurrent.next.valueis3. - Enter loop:
current.nextexists, check if3matches the value to delete. - Set
current.next = current.next.next(nowcurrent.nextisNone). - Run
current = current.next—nowcurrentisNone. - Next loop iteration tries to check
current.next, which throws the AttributeError.
The fixed code avoids this by stopping the loop before current ever becomes None.
内容的提问来源于stack exchange,提问作者Abdullah Khalid

