資料結構+演算法=程式
所以乙個優秀的程式設計師應該是要懂一點資料機構和常見的演算法的哈(所以目前正在向乙個優秀的程式設計師努力)
# -*- coding:utf-8 -*-
""" 資料結構之單項鍊表(python實現)
特點:動態資料結構,合理利用記憶體空間,沒有大小限制,插入刪除方便,但是查詢較慢,需從煉表頭依次遍歷
描述:鍊錶中的每乙個元素都可以看作乙個節點物件,包含兩部分:元素本身的值和指向下乙個元素的指標
"""# 定義乙個節點物件,該物件由其本身的值value和指向下乙個物件的指標next構成
class node(object):
def __init__(self, value=none):
self.value = value
self.next = none
# 單項鍊表必須有乙個頭元素
class singlelinkedlist(object):
# 所以初始化時只需要定義乙個頭元素即可
def __init__(self, head):
self.head = head
#重寫__str__方法,返回乙個友好的顯示(預設顯示物件的記憶體位址)
def __str__(self):
return str(self.look())
# __str__方法是在程式中呼叫print()方法時呼叫,__repr__方法是在互動式環境中直接輸出物件時使用
__repr__ = __str__
# 遍歷鍊錶
def look(self):
p = self.head
lst =
while p:
p = p.next
return lst
# 獲取鍊錶長度方法
def length(self):
p = self.head
i = 1
while p.next:
i += 1
p = p.next
return i
# 新增元素方法
def add(self, value):
p = self.head
new_node = node(value)
while p:
if not p.next:
p.next = new_node
break
p = p.next
# 刪除元素方法(只刪除匹配到的第乙個元素)
def remove(self, value):
p = self.head
while p.next:
temp = p.next
if temp.value == value:
p.next = temp.next
del temp # 釋放記憶體空間
break
else:
p = p.next
# 刪除所有匹配的元素
def remove_all(self, value):
p = self.head
while p.next:
temp = p.next
if temp.value == value:
p.next = temp.next
del temp
else:
p = p.next
# 在指定位置插入元素(如果index大於等於鍊錶長度則插入末尾)
def insert(self, index, value):
p = self.head
if index >= self.length():
while p.next:
p = p.next
p.next = node(value)
i = 0
while p.next:
temp = p.next
i += 1
if i == index:
p.next = node(value)
p.next.next = temp
p = p.next
# 查詢指定位置的元素
def index(self, index):
p = self.head
if index >= self.length():
raise indexerror("查詢範圍超出鍊錶長度")
i = 0
while p:
if i == index:
return p.value
p = p.next
i += 1
# 查詢指定元素的位置(找不到返回-1)
def find(self, value):
p = self.head
i = 0
while p.next:
if p.value == value:
return i
p = p.next
i += 1
return -1
# 鍊錶反轉([none, 2, 3]--->[2, 3, none])
def reverse(self):
p = self.head
if p is none or p.next is none:
return p
q = p.next
p.next = none
while q:
r = q.next
q.next = p
p = q
q = r
return p # p是乙個node物件
if __name__ == '__main__':
s = singlelinkedlist(node()) # 煉表頭一般不存放值,即value為none,用來表明這是鍊錶的頭部
print(s, '長度為: %i' % s.length())
s.add(1) # 新增幾個value值相同的元素 用來檢視remove和remove_all方法的區別
s.add(2)
s.add(1)
s.add(3)
s.add(1)
print(s, '長度為: %i' % s.length())
s.remove(1)
print(s, '長度為: %i' % s.length())
s.remove_all(1)
print(s, '長度為: %i' % s.length())
s.insert(2, 222)
print(s, '長度為: %i' % s.length())
s.insert(8, 222)
print(s, '長度為: %i' % s.length())
try:
print(s.index(5)) # 丟擲indexerror異常,為了後續**的正常執行在該處捕獲異常並使程式繼續執行
except indexerror as e:
print(e)
print('第乙個value值為222的元素的位置是:\n%i' % s.find(222))
print('原煉表為:\n%s' % s)
s = singlelinkedlist(s.reverse()) # 將返回的node物件封裝成乙個鍊錶物件即為反轉後的鍊錶
print('反轉後的鍊錶為:\n%s' % s)
只要理解了資料結構的原理,其實用**很好實現的,該**的主要難點在於鍊錶的反轉,其思想是:
1.從頭元素開始,先取出頭元素(p)和它的下乙個元素(q),然後頭元素指向none變為最後乙個元素
2.從頭元素(p)中的下乙個元素(q)開始遍歷,同樣的,要想將第二個元素,也就是當前q元素放在倒數第二個位置上,那我們需要先取出它的下乙個元素,也就是**中的r元素,然後將q元素指標指向最後的乙個元素(p),此時,再下乙個元素就不是指向最後的p元素了,而是指向反轉後的倒數第二個元素,也就是q元素,所以需要將q賦值給p,然後r元素賦值給正向鍊錶的下乙個元素q繼續遍歷,一直到結束。
Python資料結構之單鏈表實現
鍊錶的定義 鍊錶 linked list 是由一組被稱為結點的資料元素組成的資料結構,每個結點都包含結點本身的資訊和指向下乙個結點的位址。由於每個結點都包含了可以鏈結起來的位址資訊,所以用乙個變數就能夠訪問整個結點序列。也就是說,結點包含兩部分資訊 一部分用於儲存資料元素的值,稱為資訊域 另一部分用...
python鍊錶中的單項鍊表概述,超級詳細!!
首先看一下順序表和煉表的區別 順序表 預先知道資料大小來申請連續的儲存空間,而在進行擴充時又需要進行資料的搬遷,所以使用起來不是很靈活?鍊錶 可以充分利用計算機記憶體空間,實現靈活的記憶體動態管理,可以通俗理解為手鍊,通過鍊子把珠子一顆一顆串起來,就是節點和節點之間靠繩子串起來,鍊錶和順序表統稱為線...
資料結構之單鏈表
date 08 07 06 descript 單鏈表的實現與應用 public class linlist public node gethead 定位函式 public void index int i throws exception if i 1 current head.next int j...