python - 我不明白这些条件的必要性。链接列表如何以及何时可以为无?
问题描述
(在拆分功能中)我在没有这些条件的情况下运行它,它的工作方式与它们相同。当我们到达单节点链表时,merge_sort 函数的停止条件应该只是返回相同的单节点链表,然后可以继续。我在教程中看到了这一点,这被解释为“当具有单个节点的链接列表通过拆分传递时,链接列表可以是无”任何帮助将不胜感激
if linked_list == None or linked_list.head == None:
left_half = linked_list
right_half = None
这是整个程序
from linked_list import LinkedList
def merge_sort(linked_list):
"""
Sorts a linked list in ascending order
- Recursively divide the linked list into sublists containing a single node
- Repeatedly merge the sublists to produce sorted sublists until one remains
Returns a sorted linked list
Takes O(n log n) time
Takes O(n) space
"""
if linked_list.size() == 1 or linked_list.head is None:
return linked_list
left_half , right_half = split(linked_list)
left = merge_sort(left_half)
right = merge_sort(right_half)
return merge(left,right)
def split(linked_list):
"""
Divide the unsorted list at midpoint into sublists
Takes O(log n) time
"""
# linked_list can be none when a linked_list having a single node is passed through split
if linked_list == None or linked_list.head == None:
left_half = linked_list
right_half = None
return left_half,right_half
else:
size = linked_list.size()
mid = size//2
mid_node = linked_list.node_at_index(mid-1)
left_half = linked_list
right_half =LinkedList()
right_half.head = mid_node.next_node
mid_node.next_node = None
return left_half,right_half
def merge(left,right):
"""
Create a new list that contains the node from left and right
"""
merged = LinkedList()
#fake head to avoid guessing if there is a head in our new linked_list or not
merged.add(0)
current = merged.head
left_head = left.head
right_head = right.head
#iterate over left and right until we reach the tail node of both
while left_head or right_head:
#if the left_head is None, means we're past the tail node
# Add the tail node from right to the merged linked list
if left_head is None:
current.next_node = right_head
right_head = right_head.next_node
elif right_head is None:
# Add the tail node from left to the merged linked list
#if the right_head is None, means we're past the tail node
current.next_node = left_head
left_head = left_head.next_node
else:
#not at either tail node
#Obtain node data to perform comparison
left_data = left_head.data
right_data = right_head.data
if left_data < right_data:
current.next_node = left_head
left_head= left_head.next_node
else:
current.next_node = right_head
right_head = right_head.next_node
current= current.next_node
#discarding the fake head
head = merged.head.next_node
merged.head = head
return merged
这是我从中导入的 LinkedList 程序
class Node:
"""
An object for creating a Node
"""
def __init__(self,data,next_node=None):
self.data = data
self.next_node = next_node
def __repr__(self):
return "<Node: %s>"%self.data
class LinkedList:
"""
A (linear data structure)list to maintain the nodes created
The list refers to the first node as head and each node refers to the next node in the list
"""
def __init__(self):
self.head = None #an empty LinkedList
def is_empty(self):
return self.head is None
def size(self):
"""
if current is none, while loop doesn't run, size return 0
self.head = current, then we increase count and make current = self.next_node,
when next_node becomes none, which means current becomes 0, it is past the tail, in that case while loop breaks
"""
current = self.head
count = 0
while current:
count += 1
current = current.next_node
return count
def add(self,data):
"""
prepends the new date to the LinkedList
"""
new_node = Node(data)
new_node.next_node = self.head
self.head = new_node
def search(self,key):
"""
Searches the data by trasversing through the list. If not found, it returns None
"""
current = self.head
while current:
if current.data == key:
return current.data
current = current.next_node
return None
def insert(self,data,index):
"""
Inserts the data at a particular index by trasversing through the LinkedList.
Inserting is efficient as nothin needs to be shifted but finding and going to the index
makes it O(n)
"""
if index == 0:
self.add(data)
if index > 0:
new = Node(data)
pos = index
current = self.head
while pos > 1:
current = current.next_node
pos -= 1
prev_node = current
next_node = current.next_node
prev_node.next_node = new
new.next_node = next_node
def remove(self,key):
"""
Removes the first element matching the key in the LinkedList
returns None if the list is empty or if the key is not in the list
"""
current = self.head
prev = None
found = False
while current and not found:
if current.data == key and current is self.head: #if the key is at the head
found = True
self.head = current.next_node
elif current.data == key:
found = True
prev.next_node = current.next_node
else:
prev = current
current = current.next_node
return current
def remove_at_index(self,index):
current = self.head
pos = index
while pos > 0:
current = current.next_node
pos -= 1
self.remove(current.data)
def node_at_index(self,index):
"""
Returning the node at index by counting the number of times we used next_node on current.
if it becomes equal to the index, we return the current
"""
if index == 0:
return self.head
else:
current = self.head
pos = 0
while pos < index:
current = current.next_node
pos += 1
return current
def __repr__(self):
"""
returns a string representation of the list
"""
current = self.head
ls = []
while current:
if current is self.head:
ls.append('[Head: %s]'%current.data)
elif current.next_node is None:
ls.append('[Tail: %s]'%current.data)
else:
ls.append('[%s]'%current.data)
current = current.next_node
return '->'.join(ls)
如果有任何愚蠢的错误,请原谅,我只是一个初学者。
解决方案
你是对的,你不需要函数中的这些条件,split(linkedlist)
因为你正在检查merge_sort(linkedlist)
函数中的边缘情况。我想您提到的教程包含两次以使其split(linkedlist)
作为独立函数工作,即它可以在任何 LinkedList 上工作。
推荐阅读
- r - R - 使散点图看起来像一个点图,计数高于和低于零
- actionscript-3 - 将事件侦听器添加到多维数组
- asp.net-core - 填充 AspNetUserLogins 和 AspNetUserTokens
- r - 如何将多个excel文件中的多张工作表导入一个列表-readxl R
- python - 熊猫将框架的列与列名中的部分匹配合并
- html - form action="" HTML 处理表单的动作代码是什么?
- xml - XML - XSLT - 使用两个 XML 文件 - 对 XML 文件的补充咨询另一个 XML 文件
- visual-studio - eShopOnContainer - Docker:Visual Studio 在尝试加载 mvc 页面时出现异常
- c++ - 如果我在 decltype 中使用 std::string 模板参数替换失败
- python - 如何在 TensorFlow 程序运行时更改 TensorFlow 程序可以使用的 GPU?