Der Unterschied und die Verbindung zwischen Listen und Tupeln in Python

Schauen Sie sich zuerst an, was eine Liste ist. Was ist ein Tupel?

Listen und Tupel sind beide eine geordnete Sammlung eines beliebigen Datentyps. In den meisten Programmiersprachen müssen die Datentypen der Sammlungen konsistent sein. Es gibt jedoch keine solche Anforderung für Python-Listen und -Tupel.

Liste:

l = [1, 2, 'hello', 'world'] 
l

[1, 2, 'hello', 'world']

Tupel:

tup = ('jason', 22)
tup

('jason', 22)

der Unterschied

Die Liste ist dynamisch, die Länge ist nicht festgelegt und die Elemente können nach Belieben hinzugefügt, gelöscht oder geändert werden (veränderbar).

Tupel sind statisch, haben eine feste Länge und können nicht hinzugefügt, gelöscht oder geändert werden (unveränderlich).

l = [1, 2, 3, 4]
l[3] = 40 # 和很多语言类似,python中索引同样从0开始,l[3]表示访问列表的第四个元素
l
[1, 2, 3, 40]

tup = (1, 2, 3, 4)
tup[3] = 40
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
TypeError: 'tuple' object does not support item assignment

Aber was ist, wenn Sie Änderungen an den vorhandenen Tupeln vornehmen möchten? Dann können Sie nur ein Stück Speicher wieder öffnen und ein neues Tupel erstellen.

tup = (1, 2, 3, 4)
new_tup = tup + (5, ) # 创建新的元组new_tup,并依次填充原元组的值
new _tup
(1, 2, 3, 4, 5)

l = [1, 2, 3, 4]
l.append(5) # 添加元素5到原列表的末尾
l
[1, 2, 3, 4, 5]

Gleiche Punkte

Beide unterstützen einen negativen Index, -1 bedeutet das letzte Element, -2 bedeutet das vorletzte Element und so weiter.

l = [1, 2, 3, 4]
l[-1]
4

tup = (1, 2, 3, 4)
tup[-2]
3

Alle Support-Slicing-Vorgänge

l = [1, 2, 3, 4]
l[1:3] # 返回列表中索引从1到2的子列表
[2, 3]

tup = (1, 2, 3, 4)
tup[1:3] # 返回元组中索引从1到2的子元组
(2, 3) 

Kann nach Belieben verschachtelt werden

l = [[1, 2, 3], [4, 5]] # 列表的每一个元素也是一个列表

tup = ((1, 2, 3), (4, 5, 6)) # 元组的每一个元素也是一个元组

Kann über die Funktionen list () und tuple () ineinander konvertiert werden

list((1, 2, 3))
[1, 2, 3]

tuple([1, 2, 3])
(1, 2, 3)

Einige häufig verwendete integrierte Funktionen für Listen und Tupel

l = [3, 2, 3, 7, 8, 1]
l.count(3) 
2
l.index(7)
3
l.reverse()
l
[1, 8, 7, 3, 2, 3]
l.sort()
l
[1, 2, 3, 3, 7, 8]

tup = (3, 2, 3, 7, 8, 1)
tup.count(3)
2
tup.index(7)
3
list(reversed(tup))
[1, 8, 7, 3, 2, 3]
sorted(tup)
[1, 2, 3, 3, 7, 8]
  • count (item) gibt die Anzahl der Vorkommen von Elementen in der Zählliste / dem Tupel an.
  • index (item) repräsentiert den Index des ersten Auftretens eines Elements in der zurückgegebenen Liste / dem zurückgegebenen Tupel.
  • list.reverse () und list.sort () repräsentieren die In-situ-Listenumkehr bzw. -sortierung (beachten Sie, dass Tupel diese beiden integrierten Funktionen nicht haben).
  • reverse () und sorted () bedeuten auch, die Liste / das Tupel umzukehren und zu sortieren. reverse () gibt einen umgekehrten Iterator zurück (im obigen Beispiel wird die Funktion list () verwendet, um ihn in eine Liste zu konvertieren); sorted () gibt eine neue sortierte Liste zurück .

Unterschiede in der Speicherung von Listen und Tupeln

Listen sind dynamisch und veränderlich, während Tupel statisch und unveränderlich sind. Dieser Unterschied wirkt sich unweigerlich auf die Speichermethoden der beiden aus.

l = [1, 2, 3]
l.__sizeof__()
64
tup = (1, 2, 3)
tup.__sizeof__()
48

Die Liste ist dynamisch, daher muss ein Zeiger gespeichert werden, der auf das entsprechende Element zeigt (im obigen Beispiel für den Typ int 8 Byte). Da die Liste variabel ist, ist außerdem ein zusätzlicher Speicher der zugewiesenen Länge (8 Byte) erforderlich, damit die Nutzung des Listenbereichs in Echtzeit verfolgt werden kann und zusätzlicher Speicherplatz rechtzeitig zugewiesen werden kann, wenn der Speicherplatz nicht ausreicht .

Beschreiben Sie anhand eines Beispiels den Prozess der Zuweisung von Listenbereichen.

l = []
l.__sizeof__() // 空列表的存储空间为40字节
40
l.append(1)
l.__sizeof__() 
72 // 加入了元素1之后,列表为其分配了可以存储4个元素的空间 (72 - 40)/8 = 4
l.append(2) 
l.__sizeof__()
72 // 由于之前分配了空间,所以加入元素2,列表空间不变
l.append(3)
l.__sizeof__() 
72 // 同上
l.append(4)
l.__sizeof__() 
72 // 同上
l.append(5)
l.__sizeof__() 
104 // 加入元素5之后,列表的空间不足,所以又额外分配了可以存储4个元素的空间

Es ist ersichtlich, dass Python jedes Mal, wenn es Speicherplatz zuweist, mehr Speicherplatz zuweist, um den Overhead der Speicherplatzzuweisung bei jedem Erhöhungs- / Löschvorgang zu verringern. Dieser Mechanismus (Überzuweisung) stellt die Effizienz seines Vorgangs sicher: Erhöhen / Die Zeit Komplexität der Löschung ist O (1) O (1)O ( 1 )

Bei Tupeln ist die Situation anders. Die Länge des Tupels ist festgelegt, und die Elemente sind unveränderlich, sodass der Speicherplatz festgelegt ist.

Leistung von Listen und Tupeln

Tupel sind leichter als Listen, sodass die Leistungsgeschwindigkeit von Tupeln insgesamt etwas besser ist als die von Listen.

Python führt im Hintergrund ein Ressourcen-Caching für statische Daten durch. Im Allgemeinen wird Python aufgrund des Garbage Collection-Mechanismus, wenn einige Variablen nicht verwendet werden, den von ihnen belegten Speicher zurückfordern und an das Betriebssystem zurückgeben, damit andere Variablen oder andere Anwendungen verwendet werden können.
Bei einigen statischen Variablen, z. B. Tupeln, wird dieser Teil des Speichers vorübergehend zwischengespeichert, wenn er nicht verwendet wird und wenig Speicherplatz beansprucht. Auf diese Weise kann Python beim nächsten Erstellen eines Tupels derselben Größe das Betriebssystem nicht mehr auffordern, Speicher zu finden, sondern den zuvor zwischengespeicherten Speicherplatz direkt zuweisen, was die Ausführungsgeschwindigkeit des Programms erheblich beschleunigen kann.

Im folgenden Beispiel wird die Zeit berechnet, die zum Initialisieren einer Liste und eines Tupels desselben Elements erforderlich ist. Wir können sehen, dass die Initialisierungsgeschwindigkeit von Tupeln fünfmal schneller ist als die von Listen.

python3 -m timeit 'x=(1,2,3,4,5,6)'
20000000 loops, best of 5: 9.97 nsec per loop
python3 -m timeit 'x=[1,2,3,4,5,6]'
5000000 loops, best of 5: 50.1 nsec per loop

Wenn es sich jedoch um eine Indexoperation handelt, ist der Geschwindigkeitsunterschied zwischen den beiden sehr gering und nahezu vernachlässigbar.

python3 -m timeit -s 'x=[1,2,3,4,5,6]' 'y=x[3]'
10000000 loops, best of 5: 22.2 nsec per loop
python3 -m timeit -s 'x=(1,2,3,4,5,6)' 'y=x[3]'
10000000 loops, best of 5: 21.9 nsec per loop

Elemente hinzufügen, löschen oder ändern, dann ist die Liste offensichtlich besser. Denn für Tupel müssen Sie ein neues Tupel erstellen, das definitiv teurer ist.

Anwendungsfälle für Listen und Tupel

  1. Wenn die gespeicherten Daten und Mengen gleich bleiben, z. B. wenn Sie eine Funktion haben, die den Breiten- und Längengrad eines Standorts zurückgeben und dann direkt an das Front-End-Rendering übergeben muss, ist es besser, Tupel zu verwenden .
def get_location():
    ..... 
    return (longitude, latitude)
  1. Wenn die gespeicherten Daten oder Mengen gespeichert sind, z. B. eine Protokollfunktion auf einer sozialen Plattform, um zu zählen, welche Benutzerbeiträge ein Benutzer innerhalb einer Woche gelesen hat, ist eine Liste besser geeignet.
viewer_owner_id_list = [] # 里面的每个元素记录了这个viewer一周内看过的所有owner的id
records = queryDB(viewer_id) # 索引数据库,拿到某个viewer一周内的日志
for record in records:
    viewer_owner_id_list.append(record.id)

Kleine Zusammenfassung

Unterschied:

  • Die Liste ist dynamisch, die Länge ist nicht festgelegt und die Elemente können nach Belieben hinzugefügt, gelöscht oder geändert werden (veränderbar). Das Tupel ist statisch, die Länge ist fest und es kann nicht hinzugefügt, gelöscht oder geändert werden (unveränderlich).
  • Der Speicherplatz der Liste ist etwas größer als der des Tupels und seine Leistung ist etwas schlechter als die des Tupels. Im Vergleich zur Liste ist das Tupel leichter und weist eine etwas bessere Leistung auf.

Gemeinsamkeiten

  • Sowohl Listen als auch Tupel in Python unterstützen eine negative Indizierung. -1 bedeutet das letzte Element, -2 bedeutet das vorletzte Element.
  • Sowohl Listen als auch Tupel unterstützen Slicing-Vorgänge.
  • Sowohl Listen als auch Tupel können nach Belieben verschachtelt werden.
  • Sowohl Listen als auch Tupel sind geordnet und können Sammlungen eines beliebigen Datentyps speichern.

Ich denke du magst

Origin blog.csdn.net/qq_41485273/article/details/114030018
Empfohlen
Rangfolge