鏈表是一系列數(shù)據(jù)元素,通過(guò)鏈接連接在一起。 每個(gè)數(shù)據(jù)元素都以指針的形式包含到另一個(gè)數(shù)據(jù)元素的連接。 Python在其標(biāo)準(zhǔn)庫(kù)中沒(méi)有鏈接列表。 我們使用前一章討論的節(jié)點(diǎn)概念來(lái)實(shí)現(xiàn)鏈表的概念。 我們已經(jīng)知道如何創(chuàng)建節(jié)點(diǎn)類(lèi)以及如何遍歷節(jié)點(diǎn)的元素。 在本章中,將學(xué)習(xí)鏈表的類(lèi)型:單鏈表。 在這種類(lèi)型的數(shù)據(jù)結(jié)構(gòu)中,任何兩個(gè)數(shù)據(jù)元素之間只有一個(gè)鏈接。 創(chuàng)建一個(gè)鏈表并使用一些方法來(lái)插入,更新和從列表中移除元素。
通過(guò)使用在上一章中學(xué)習(xí)的節(jié)點(diǎn)類(lèi)來(lái)創(chuàng)建鏈表。創(chuàng)建一個(gè)Node對(duì)象并創(chuàng)建另一個(gè)類(lèi)來(lái)使用這個(gè)節(jié)點(diǎn)對(duì)象。 通過(guò)節(jié)點(diǎn)對(duì)象傳遞適當(dāng)?shù)闹祦?lái)指向下一個(gè)數(shù)據(jù)元素。 下面的程序使用三個(gè)數(shù)據(jù)元素創(chuàng)建鏈接列表。 在下一節(jié)中,將學(xué)習(xí)如何遍歷鏈表。
class Node:
def __init__(self, dataval=None):
self.dataval = dataval
self.nextval = None
class SLinkedList:
def __init__(self):
self.headval = None
list1 = SLinkedList()
list1.headval = Node("Mon")
e2 = Node("Tue")
e3 = Node("Wed")
# Link first Node to second node
list1.headval.nextval = e2
# Link second Node to third node
e2.nextval = e3
從第一個(gè)數(shù)據(jù)元素開(kāi)始,單向鏈表只能在向前遍歷。 只需通過(guò)將下一個(gè)節(jié)點(diǎn)的指針指向當(dāng)前數(shù)據(jù)元素來(lái)打印下一個(gè)數(shù)據(jù)元素的值。
class Node:
def __init__(self, dataval=None):
self.dataval = dataval
self.nextval = None
class SLinkedList:
def __init__(self):
self.headval = None
def listprint(self):
printval = self.headval
while printval is not None:
print (printval.dataval)
printval = printval.nextval
list = SLinkedList()
list.headval = Node("Mon")
e2 = Node("Tue")
e3 = Node("Wed")
# Link first Node to second node
list.headval.nextval = e2
# Link second Node to third node
e2.nextval = e3
list.listprint()
執(zhí)行上面示例代碼,得到以下結(jié)果 -
Mon
Tue
Wed
在鏈表中插入元素涉及將指針從現(xiàn)有節(jié)點(diǎn)重新分配給新插入的節(jié)點(diǎn)。 取決于新數(shù)據(jù)元素是在鏈表的開(kāi)始位置還是在中間位置或末尾插入,有以下解決方案。
在鏈接列表的開(kāi)頭插入
這涉及到將新數(shù)據(jù)節(jié)點(diǎn)的下一個(gè)指針指向鏈表的當(dāng)前頭部。 因此,鏈表的當(dāng)前頭成為第二個(gè)數(shù)據(jù)元素,新節(jié)點(diǎn)成為鏈表的頭部。
class Node:
def __init__(self, dataval=None):
self.dataval = dataval
self.nextval = None
class SLinkedList:
def __init__(self):
self.headval = None
# Print the linked list
def listprint(self):
printval = self.headval
while printval is not None:
print (printval.dataval)
printval = printval.nextval
def AtBegining(self,newdata):
NewNode = Node(newdata)
# Update the new nodes next val to existing node
NewNode.nextval = self.headval
self.headval = NewNode
list = SLinkedList()
list.headval = Node("Mon")
e2 = Node("Tue")
e3 = Node("Wed")
list.headval.nextval = e2
e2.nextval = e3
list.AtBegining("Sun")
list.listprint()
執(zhí)行上面示例代碼,得到以下結(jié)果 -
Sun
Mon
Tue
Wed
在鏈表的末尾插入
這包括將鏈表的當(dāng)前最后一個(gè)節(jié)點(diǎn)的下一個(gè)指針指向新的數(shù)據(jù)節(jié)點(diǎn)。 因此鏈表的當(dāng)前最后一個(gè)節(jié)點(diǎn)成為倒數(shù)第二個(gè)數(shù)據(jù)節(jié)點(diǎn),新節(jié)點(diǎn)成為鏈表的最后一個(gè)節(jié)點(diǎn)。參考以下代碼實(shí)現(xiàn) -
class Node:
def __init__(self, dataval=None):
self.dataval = dataval
self.nextval = None
class SLinkedList:
def __init__(self):
self.headval = None
# Function to add newnode
def AtEnd(self, newdata):
NewNode = Node(newdata)
if self.headval is None:
self.headval = NewNode
return
laste = self.headval
while(laste.nextval):
laste = laste.nextval
laste.nextval=NewNode
# Print the linked list
def listprint(self):
printval = self.headval
while printval is not None:
print (printval.dataval)
printval = printval.nextval
list = SLinkedList()
list.headval = Node("Mon")
e2 = Node("Tue")
e3 = Node("Wed")
list.headval.nextval = e2
e2.nextval = e3
list.AtEnd("Thu")
list.listprint()
執(zhí)行上面代碼,得到以下結(jié)果 -
Mon
Tue
Wed
Thu
在兩個(gè)數(shù)據(jù)節(jié)點(diǎn)之間插入
這涉及到將指定節(jié)點(diǎn)的指針指向新節(jié)點(diǎn)。 這可以通過(guò)傳入新節(jié)點(diǎn)和現(xiàn)有節(jié)點(diǎn),然后插入新節(jié)點(diǎn)。 所以定義一個(gè)額外的類(lèi),將新節(jié)點(diǎn)的下一個(gè)指針改變?yōu)橹虚g節(jié)點(diǎn)的下一個(gè)指針。 然后將新節(jié)點(diǎn)分配給中間節(jié)點(diǎn)的下一個(gè)指針。參考以下代碼實(shí)現(xiàn) -
class Node:
def __init__(self, dataval=None):
self.dataval = dataval
self.nextval = None
class SLinkedList:
def __init__(self):
self.headval = None
# Function to add node
def Inbetween(self,middle_node,newdata):
if middle_node is None:
print("The mentioned node is absent")
return
NewNode = Node(newdata)
NewNode.nextval = middle_node.nextval
middle_node.nextval = NewNode
# Print the linked list
def listprint(self):
printval = self.headval
while printval is not None:
print (printval.dataval)
printval = printval.nextval
list = SLinkedList()
list.headval = Node("Mon")
e2 = Node("Tue")
e3 = Node("Thu")
list.headval.nextval = e2
e2.nextval = e3
list.Inbetween(list.headval.nextval,"Fri")
list.listprint()
執(zhí)行上面示例代碼,得到以下結(jié)果 -
Mon
Tue
Fri
Thu
可以使用該節(jié)點(diǎn)的鍵來(lái)刪除一個(gè)節(jié)點(diǎn)。 在下面的程序中,找到要?jiǎng)h除的節(jié)點(diǎn)的前一個(gè)節(jié)點(diǎn)。 然后將該節(jié)點(diǎn)的下一個(gè)指針指向要?jiǎng)h除的節(jié)點(diǎn)的下一個(gè)節(jié)點(diǎn)。
class Node:
def __init__(self, data=None):
self.data = data
self.next = None
class SLinkedList:
def __init__(self):
self.head = None
def Atbegining(self, data_in):
NewNode = Node(data_in)
NewNode.next = self.head
self.head = NewNode
# Function to remove node
def RemoveNode(self, Removekey):
HeadVal = self.head
if (HeadVal is not None):
if (HeadVal.data == Removekey):
self.head = HeadVal.next
HeadVal = None
return
while (HeadVal is not None):
if HeadVal.data == Removekey:
break
prev = HeadVal
HeadVal = HeadVal.next
if (HeadVal == None):
return
prev.next = HeadVal.next
HeadVal = None
def LListprint(self):
printval = self.head
while (printval):
print(printval.data),
printval = printval.next
llist = SLinkedList()
llist.Atbegining("Mon")
llist.Atbegining("Tue")
llist.Atbegining("Wed")
llist.Atbegining("Thu")
llist.RemoveNode("Tue")
llist.LListprint()
執(zhí)行上面示例代碼,得到以下結(jié)果 -
Thu
Wed
Mon