日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問(wèn) 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) > 编程语言 > python >内容正文

python

python有序列表无序列表区别_用Python链表实现有序表与无序表

發(fā)布時(shí)間:2023/12/14 python 37 豆豆
生活随笔 收集整理的這篇文章主要介紹了 python有序列表无序列表区别_用Python链表实现有序表与无序表 小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

用Python鏈表實(shí)現(xiàn)有序表與無(wú)序表

《數(shù)據(jù)結(jié)構(gòu)與算法》MOOC(北大地空)課堂筆記

2020.4

by dlnb526

啥是鏈表

鏈表,顧名思義,顧名思義,鏈表像鎖鏈一樣,由一節(jié)節(jié)節(jié)點(diǎn)連在一起,組成一條數(shù)據(jù)鏈。

為什么要使用鏈表?

在之前用了python中的列表(list)來(lái)實(shí)現(xiàn)各種數(shù)據(jù)結(jié)構(gòu),然而有的語(yǔ)言可能并沒(méi)有提供像python的列表一樣強(qiáng)大的功能,我們必須要自己實(shí)現(xiàn)列表。

無(wú)序列表

概述

列表可以看作是一個(gè)無(wú)序的列表。

無(wú)序,也就是說(shuō)它里面的元素沒(méi)有一定的順序,比如這樣一個(gè)列表:

a = [1,2,'ads',54,32]

這里面的每個(gè)元素沒(méi)有按照一定的規(guī)則排序,所以就叫無(wú)序。

無(wú)序列表應(yīng)該有以下的方法

list() 創(chuàng)建一個(gè)新的空列表。它不需要參數(shù),而返回一個(gè)空列表。

add(item) 將新項(xiàng)添加到列表,沒(méi)有返回值。假設(shè)元素不在列表中。

remove(item) 從列表中刪除元素。需要一個(gè)參數(shù),并會(huì)修改列表。此處假設(shè)元素在列表中。

search(item) 搜索列表中的元素。需要一個(gè)參數(shù),并返回一個(gè)布爾值。

isEmpty() 判斷列表是否為空。不需要參數(shù),并返回一個(gè)布爾值。

size() 返回列表的元素?cái)?shù)。不需要參數(shù),并返回一個(gè)整數(shù)。

append(item) 在列表末端添加一個(gè)新的元素。它需要一個(gè)參數(shù),沒(méi)有返回值。假設(shè)該項(xiàng)目不在列表中。

index(item) 返回元素在列表中的位置。它需要一個(gè)參數(shù),并返回位置索引值。

此處假設(shè)該元素原本在列表中。

insert(pos,item) 在指定的位置添加一個(gè)新元素。它需要兩個(gè)參數(shù),沒(méi)有返回值。假設(shè)該元素在列表中并不存在,并且列表有足夠的長(zhǎng)度滿足參數(shù)提供的索引需要。

pop() 從列表末端移除一個(gè)元素并返回它。它不需要參數(shù),返回一個(gè)元素。假設(shè)列表至少有一個(gè)元素。

pop(pos) 從指定的位置移除列表元素并返回它。它需要一個(gè)位置參數(shù),并返回一個(gè)元素。假設(shè)該元素在列表中。

節(jié)點(diǎn)

為了實(shí)現(xiàn)無(wú)序列表,我們采用鏈表的方式。

鏈表最基本的元素是節(jié)點(diǎn)。

每個(gè)節(jié)點(diǎn)對(duì)象必須持有至少兩條信息。

首先,節(jié)點(diǎn)必須包含列表元素本身。我們將這稱(chēng)為該節(jié)點(diǎn)的“數(shù)據(jù)區(qū)”(data field)。

此外,每個(gè)節(jié)點(diǎn)必須保持到下個(gè)節(jié)點(diǎn)的引用。

如果沒(méi)有下一個(gè)節(jié)點(diǎn),那我們就記錄為None

class Node:#節(jié)點(diǎn)這個(gè)類(lèi)~

def __init__(self,initdata):

self.data = initdata

self.next = None#初始化的時(shí)候頭節(jié)點(diǎn)后面沒(méi)有節(jié)點(diǎn)了

def getData(self):

return self.data #節(jié)點(diǎn)可以獲取自身數(shù)據(jù)

def getNext(self):

return self.next #節(jié)點(diǎn)可以獲取指向的下一個(gè)節(jié)點(diǎn)

def setData(self,newdata):

self.data = newdata

def setNext(self,newnext):#節(jié)點(diǎn)可以對(duì)下一個(gè)節(jié)點(diǎn)進(jìn)行更新

self.next = newnext

上面我們就把一個(gè)節(jié)點(diǎn)建立起來(lái)了,那如何把節(jié)點(diǎn)連接起來(lái)呢。

無(wú)序表的鏈表實(shí)現(xiàn)

操作舉例

1. 添加數(shù)據(jù)項(xiàng)add

通過(guò)之前的方式建立了一個(gè)節(jié)點(diǎn),如果初始化它我們知道他是一個(gè)在開(kāi)頭的節(jié)點(diǎn),后面是None.由于無(wú)序表是從表頭開(kāi)始逐個(gè)向后查找,新數(shù)據(jù)所以插入到表頭是我們的最佳選擇。

def add(self,item):

temp = Node(item) #新的要插入的數(shù)據(jù)初始化為一個(gè)節(jié)點(diǎn)

temp.setNext(self.head)#但當(dāng)前節(jié)點(diǎn)的下一個(gè)指向?yàn)橹版湵淼念^部

self.head = temp#把插入的節(jié)點(diǎn)設(shè)為新鏈表的頭部

2. size()的實(shí)現(xiàn) 和 search()的實(shí)現(xiàn)

def size(self):

current = self.head

count = 0

while current != None:

count = count + 1

current = current.getNext()

return count

def search(self,item):

current = self.head

found = False

while current != None and not found:

if current.getData() == item:

found = True

else:

current = current.getNext()

return found

沒(méi)什么可說(shuō)的,設(shè)置一個(gè)計(jì)數(shù)器,然后遍歷元素。

3. remove(item)實(shí)現(xiàn)

我們需要先用類(lèi)似search的方法找到元素,然后它指向的后一個(gè)元素和前一個(gè)元素怎么連在一起呢?

這時(shí)就需要維護(hù)前一個(gè)節(jié)點(diǎn)的引用。

def remove(self,item):

current = self.head

previous = None

found = False

while not found:

if current.getData() == item:

found = True

else:

previous = current#不斷地往后找,然后把當(dāng)前的節(jié)點(diǎn)記作前一個(gè)結(jié)點(diǎn),這樣在找到后就可以對(duì)前一個(gè)結(jié)點(diǎn)進(jìn)行操作。

current = current.getNext()

if previous == None:

self.head = current.getNext()

else:

previous.setNext(current.getNext())

好了那下面我們來(lái)看無(wú)序表的完整實(shí)現(xiàn)

class Node:

def __init__(self,initdata):

self.data = initdata

self.next = None

def getData(self):

return self.data

def getNext(self):

return self.next

def setData(self,newdata):

self.data = newdata

def setNext(self,newnext):

self.next = newnext

class UnorderedList:

def __init__(self):

self.head = None

def isEmpty(self):

return self.head == None

def add(self,item):

temp = Node(item)

temp.setNext(self.head)

self.head = temp

def length(self):

current = self.head

count = 0

while current != None:

count = count + 1

current = current.getNext()

return count

def search(self,item):

current = self.head

found = False

while current != None and not found:

if current.getData() == item:

found = True

else:

current = current.getNext()

return found

def remove(self,item):

current = self.head

previous = None

found = False

while not found:

if current.getData() == item:

found = True

else:

previous = current

current = current.getNext()

if previous == None:

self.head = current.getNext()

else:

previous.setNext(current.getNext())

mylist = UnorderedList()

mylist.add(31)

mylist.add(77)

mylist.add(17)

mylist.add(93)

mylist.add(26)

mylist.add(54)

print(mylist.length())

print(mylist.search(93))

print(mylist.search(100))

mylist.add(100)

print(mylist.search(100))

print(mylist.length())

mylist.remove(54)

print(mylist.length())

mylist.remove(93)

print(mylist.length())

mylist.remove(31)

print(mylist.length())

print(mylist.search(93))

有序鏈表

概述

之前無(wú)序鏈表時(shí)我們就能推測(cè)出有序的意思,也就是排列過(guò)大小的唄~

有序表依據(jù)數(shù)據(jù)項(xiàng)的可比性質(zhì)(如整數(shù)大小,字母表前后)來(lái)決定數(shù)據(jù)項(xiàng)在列表中的位置。

比如下面我們要實(shí)現(xiàn)越小的越靠近列表頭的操作。

有序表中的操作:

OrderedList():創(chuàng)建一個(gè)新的空有序列表。它返回一個(gè)空有序列表并且不需要傳遞任何參數(shù)。

add(item):在保持原有順序的情況下向列表中添加一個(gè)新的元素,新的元素作為參數(shù)傳遞進(jìn)函數(shù)而函數(shù)無(wú)返回值。假設(shè)列表中原先并不存在這個(gè)元素。

remove(item):從列表中刪除某個(gè)元素。欲刪除的元素作為參數(shù),并且會(huì)修改原列表。假設(shè)原列表

中存在欲刪除的元素。

search(item):在列表中搜索某個(gè)元素,被搜索元素作為參數(shù),返回一個(gè)布爾值。

isEmpty():測(cè)試列表是否為空,不需要輸入?yún)?shù)并且其返回一個(gè)布爾值。

size():返回列表中元素的數(shù)量。不需要參數(shù),返回一個(gè)整數(shù)。

index(item):返回元素在列表中的位置。需要被搜索的元素作為參數(shù)輸入,返回此元素的索引值。假設(shè)這個(gè)元素在列表中。

pop():刪除并返回列表中的最后一項(xiàng)。不需要參數(shù),返回刪除的元素。假設(shè)列表中至少有一個(gè)元素。

pop(pos):刪除并返回索引 pos 指定項(xiàng)。需要被刪除元素的索引值作為參數(shù),并且返回這個(gè)元素。假設(shè)該元素在列表中。

有序鏈表的實(shí)現(xiàn)

其實(shí)大部分操作都和無(wú)序表相同

search()方法

在無(wú)序表中如果不存在,搜索的時(shí)候會(huì)遍歷整個(gè)表。

但是在有序表中,因?yàn)橛许樞?#xff0c;一旦當(dāng)前節(jié)點(diǎn)大于要查找的數(shù)據(jù),就直接宣判死刑可以返回False了。

def search(self,item):

current = self.head

found = False

stop = False# 加入了一個(gè)stop可以直接停住

while current != None and not found and not stop:#這里有三個(gè)條件

if current.getData() == item:

found = True

else:

if current.getData() > item:

stop = True

else:

current = current.getNext()

return found

add()方法

和無(wú)序表相比,改動(dòng)最大的方法是 add。回想一下在無(wú)序列表中的 add 方法,只需要在原列表頭加一個(gè)新的節(jié)點(diǎn)。然而在有序表里我們要找到大小合適的位置才行。

所以我們還是要定位一個(gè)previous(前一個(gè)元素)。

def add(self,item):

current = self.head

previous = None

stop = False

while current != None and not stop:

if current.getData() > item:

stop = True

else:

previous = current

current = current.getNext()

temp = Node(item)

if previous == None:

temp.setNext(self.head)

self.head = temp

else:

temp.setNext(current)

previous.setNext(temp)

有序表的完整實(shí)現(xiàn)如下:

class Node:

def __init__(self,initdata):

self.data = initdata

self.next = None

def getData(self):

return self.data

def getNext(self):

return self.next

def setData(self,newdata):

self.data = newdata

def setNext(self,newnext):

self.next = newnext

class OrderedList:

def __init__(self):

self.head = None

def search(self,item):

current = self.head

found = False

stop = False

while current != None and not found and not stop:

if current.getData() == item:

found = True

else:

if current.getData() > item:

stop = True

else:

current = current.getNext()

return found

def add(self,item):

current = self.head

previous = None

stop = False

while current != None and not stop:

if current.getData() > item:

stop = True

else:

previous = current

current = current.getNext()

temp = Node(item)

if previous == None:

temp.setNext(self.head)

self.head = temp

else:

temp.setNext(current)

previous.setNext(temp)

def isEmpty(self):

return self.head == None

def length(self):

current = self.head

count = 0

while current != None:

count = count + 1

current = current.getNext()

return count

def traverse(self):

current = self.head

while current != None:

print(current.getData())

current = current.getNext()

mylist = OrderedList()

mylist.add(31)

mylist.add(77)

mylist.add(17)

mylist.add(93)

mylist.add(26)

mylist.add(54)

print(mylist.length())

print(mylist.search(93))

print(mylist.search(100))

mylist.traverse()

總結(jié)分析

當(dāng)分析鏈表方法的復(fù)雜度時(shí),我們應(yīng)該考慮它們是否需要遍歷鏈表。考慮一個(gè)有 n 個(gè)節(jié)點(diǎn)的鏈表,isEmpty 方法復(fù)雜度是 O(1),因?yàn)樗恍枰獧z查鏈表的頭指針是否為 None。對(duì)于方法 size,則總需要 n 個(gè)步驟,因?yàn)槌吮闅v整個(gè)鏈表以外,沒(méi)有辦法知道鏈表的節(jié)點(diǎn)數(shù)。因此,size 方法的復(fù)雜度是 O(n)。無(wú)序列表的 add 方法的復(fù)雜度是 O(1),因?yàn)槲覀冇肋h(yuǎn)只需要在鏈表的頭部簡(jiǎn)單地添加一個(gè)新的節(jié)點(diǎn)。但是,search、remove 和在有序列表中的 add 方法,需要遍歷。盡管在平均情況下,它們可能只需要遍歷一半的節(jié)點(diǎn),但這些方法的復(fù)雜度都是 O(n),因?yàn)樵谧钤愀獾那闆r下需要遍歷整個(gè)鏈表。

參考資料:MOOC配套教材及代碼

《Python數(shù)據(jù)結(jié)構(gòu)與算法分析》 第2版

總結(jié)

以上是生活随笔為你收集整理的python有序列表无序列表区别_用Python链表实现有序表与无序表的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。

如果覺(jué)得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。