Tuples en unpacking
Een lijst die niet kan veranderen, precies wat je wilt; unpacking zodat je namen gebruikt in plaats van indexen, verwisselen in één regel, en de valkuil (5) versus (5,).
Hoe wil je leren?
Het probleem dat we oplossen
Het weer van drie dagen moet vastgelegd worden — per dag de naam, de temperatuur en de luchtvochtigheid.
Een lijst doet de klus: ["monday", 31.5, 78]. Het werkt, en twee dingen knagen.
Ten eerste: die lijst kan veranderd worden. Als er per ongeluk iets aan het record van maandag wordt toegevoegd met append, zegt Python geen woord — terwijl een record nooit vier dingen had mogen bevatten. Iets dat niet mag veranderen in een container stoppen die wél kan veranderen, is een stil risico.
Ten tweede: de drie waarden weer terughalen betekent record[0], record[1], record[2] schrijven — op nummer, niet op naam. Zes maanden later weet niemand die record[1] leest nog of dat de temperatuur of de luchtvochtigheid is.
Een tuple beantwoordt beide: het is een lijst die niet veranderd kan worden — en het brengt een mogelijkheid die unpacking heet, waarmee je namen gebruikt in plaats van indexen.
Aan het einde van dit hoofdstuk kun je
- Een tuple maken, en zeggen wanneer een tuple past en een lijst niet
- Meerdere waarden in één keer in meerdere namen zetten met unpacking
- Twee variabelen in één regel verwisselen
- Het verschil zien tussen
(5)en(5,) - Uitleggen waarom
appendop een tuple eenAttributeErrorgeeft
Voorkennis: Lijsten sorteren, en de methoden die daarbij horen.
Een tuple — een lijst die niet veranderd kan worden
Ronde haken in plaats van vierkante:
point = (3, 7)
print(point)
print(point[0])
print(len(point))(3, 7)
3
2Lezen, indexeren, len, een slice maken, in, doorlopen met for — alles wat je met een lijst deed, werkt. Er is één verschil, en dat is het hele punt:
point = (3, 7)
point[0] = 5TypeError: 'tuple' object does not support item assignmentKomt die melding je bekend voor? Het is woord voor woord wat hoofdstuk zes gaf toen er een teken in een string veranderd werd, met 'str' in plaats van 'tuple'. Alle onveranderlijke dingen in Python klagen in dezelfde taal.
De methoden die dingen veranderen ontbreken ook:
point = (3, 7)
point.append(9)AttributeError: 'tuple' object has no attribute 'append'Een AttributeError betekent "dit object heeft niets met die naam". Een tuple kan niet veranderd worden, dus een tuple heeft helemaal geen methode die append heet. Python stopt al tijdens het opzoeken van point.append, nog voordat het probeert 9 toe te voegen. Vergelijk het met het vorige voorbeeld: point[0] = 5 vroeg om een bewerking die een tuple niet toestaat, dus dat was een TypeError; hier bestaat de methode zelf niet, dus is het een AttributeError.
Waarom dit een voordeel is en geen beperking
In het begin lijkt een tuple op een lijst waarvan de mogelijkheden eraf gehaald zijn. Draai het om: als iets niet mag veranderen, zet je het ergens neer waar het niet kán veranderen — dan stop je de fout vóórdat hij gebeurt.
Een derde getal toevoegen aan de coördinaat (3, 7) heeft geen zin. Een datum (2026, 9, 16) heeft geen vierde deel. In een tuple komen zulke ongelukken meteen als fouten naar voren, in plaats van later als bugs.
Als vuistregel: een vast aantal dingen, elk met een andere betekenis — tuple. Een onbekend aantal dingen, allemaal van hetzelfde soort — lijst.
Het weer van drie dagen bestaat dus uit tuples in een lijst: het aantal dagen is niet bekend (een lijst), maar elk record bevat precies drie dingen (een tuple).
Unpacking — waar het echte voordeel zit
point = (3, 7)
x, y = point
print(x)
print(y)3
7Twee namen en twee waarden op één regel. En nu is het y in plaats van point[1] — een naam die zichzelf uitlegt als je hem leest.
Er moeten net zoveel namen links staan als waarden rechts:
point = (3, 7)
x, y, z = pointValueError: not enough values to unpack (expected 3, got 2)Die melding is opvallend behulpzaam — hij zegt je zowel hoeveel er verwacht werden als hoeveel er aankwamen.
Unpacking beperkt zich niet tot tuples; het werkt ook op lijsten. Het is het handigst bij tuples, want daar is het aantal waarden vooraf bekend.
Verwisselen, in één regel
Andere talen hebben een tijdelijke derde variabele nodig om twee waarden te ruilen. Python niet:
a = 1
b = 2
a, b = b, a
print(a, b)2 1Het is de moeite waard om te begrijpen hoe de regel werkt: Python berekent eerst de hele rechterkant, bouwt daarmee een tuple (2, 1), en daarna unpackt hij die naar links. Dus hoewel a verandert, is de oude waarde van b al opgevangen in die tuple, en gaat er niets verloren.
De haken zijn eigenlijk niet nodig
point = 3, 7
print(point)
print(type(point))(3, 7)
<class 'tuple'>Wat een tuple maakt, is de komma, niet de haken. De haken staan er voor de leesbaarheid. Als je dat weet, is a, b = b, a geen magie meer — b, a rechts is gewoon een tuple.
En daar komt meteen een valkuil uit:
one = (5)
really = (5,)
print(type(one))
print(type(really))
print(len(really))<class 'int'>
<class 'tuple'>
1(5) is geen tuple — het is een getal tussen haken, precies zoals (2 + 3). Een tuple van één waarde maken vereist de komma: (5,). Het lijkt op een typfout, en die komma is het hele verschil.
Tuples in een lus
people = [("rafi", 22), ("ahmed", 35)]
for name, age in people:
print(f"{name} is {age}")rafi is 22
ahmed is 35for name, age in people unpackt elke tuple rechtstreeks in twee namen. Geen person[0] en person[1] — en de code zegt wat hij bedoelt als je hem leest.
Je hebt dit al gebruikt zonder het te weten:
stock = ["pen", "bag"]
for pair in enumerate(stock):
print(pair)(0, 'pen')
(1, 'bag')enumerate geeft tuples terug. for position, item in enumerate(...) schrijven in hoofdstuk twaalf was het unpacken van die tuples — we hadden alleen nog geen naam voor.
Omzetten tussen de twee
as_list = [3, 7]
as_tuple = (3, 7)
as_list.append(9)
print(as_list)
print(as_tuple)
print(list(as_tuple))
print(tuple(as_list))[3, 7, 9]
(3, 7)
[3, 7]
(3, 7, 9)list() en tuple() bouwen het een uit het ander — elke keer iets nieuws, waarbij het origineel onaangeroerd blijft. Zo "verander" je een tuple: maak een lijst, verander die, maak er weer een tuple van.
Een compleet voorbeeld
weather.py:
# A tuple is the right shape for a record that must not change
readings = [
("monday", 31.5, 78),
("tuesday", 33.0, 71),
("wednesday", 29.5, 85),
]
print("Day Temp Humidity")
for day, temp, humidity in readings:
print(f"{day:<10} {temp:>5} {humidity:>5}")
hottest = readings[0]
for reading in readings:
if reading[1] > hottest[1]:
hottest = reading
day, temp, humidity = hottest
print()
print(f"Hottest was {day} at {temp}")
temps = []
for _, temp, _ in readings:
temps.append(temp)
print("Temps :", temps)
print("Average :", round(sum(temps) / len(temps), 2))Day Temp Humidity
monday 31.5 78
tuesday 33.0 71
wednesday 29.5 85
Hottest was tuesday at 33.0
Temps : [31.5, 33.0, 29.5]
Average : 31.33Vier dingen die het vermelden waard zijn.
Aan de buitenkant een lijst, aan de binnenkant tuples. Het aantal dagen kan groeien, dus het buitenste is een lijst. Elk record bevat precies drie dingen, dus de binnenste zijn tuples. Dit is de vorm waarin echte data het vaakst voorkomt.
f"{day:<10}" en f"{temp:>5}" houden de kolommen recht. < lijnt links uit, > rechts, en het getal zegt hoeveel breedte het inneemt. Net als :.2f uit hoofdstuk zes is alles na de kolon opmaak.
Om de heetste dag te vinden was reading[1] nodig, want tijdens de vergelijking heb je de hele tuple in handen in plaats van een uitgepakte. Zodra hij gevonden is, wordt hij uitgepakt — daarom heeft de volgende regel geen indexen.
for _, temp, _ in readings — de underscore is een afspraak die betekent "deze heb ik niet nodig". Voor Python is het een gewone naam; voor een lezer zegt hij welke delen er bewust weggegooid worden.
Wanneer het misgaat
TypeError: 'tuple' object does not support item assignment Een poging om een waarde binnen een tuple te veranderen. Tuples kunnen niet veranderd worden — gebruik vanaf het begin een lijst, of zet om met list(...), verander die, en maak er weer een tuple van.
AttributeError: 'tuple' object has no attribute 'append' Dezelfde oorzaak in een ander jasje. Er bestaat geen enkele veranderende methode — append, remove, sort — op een tuple. sorted(my_tuple) werkt wel, want hij geeft een nieuwe lijst terug en laat de tuple met rust.
ValueError: not enough values to unpack (expected 3, got 2) Er staan meer namen links dan waarden rechts. print(len(record)) laat zien hoeveel er echt inzitten.
ValueError: too many values to unpack (expected 2) Het omgekeerde — meer waarden dan namen.
Ik maakte een tuple van één waarde en het is geen tuple De komma ontbreekt. (5) is een getal; (5,) is een tuple.
Een lijst in mijn tuple veranderde Een tuple beschermt zijn eigen structuur — welke dingen erin zitten kan niet veranderen. Maar als één van die dingen zelf veranderd kan worden, zoals een lijst, kan de binnenkant van die lijst alsnog veranderen. In ([1, 2], 3) kun je appenden op de eerste lijst.
Stap 4 van 6 — Voorspellen
Test je begrip
Wat wordt er afgedrukt na het unpacken?
point = (3, 7)
x, y = point
print(y, x)- A3 7
- B(3, 7)
- CEen `ValueError`
- D7 3
Er wordt geprobeerd op een tuple te appenden. Welke fout komt, en waarom juist die?
point = (3, 7)
point.append(9)- AEen `ValueError`
- BEr gebeurt niets; de tuple blijft ongewijzigd
- CEen `AttributeError` — een tuple kan niet veranderd worden, dus de veranderende methoden bestaan er simpelweg niet
- DEen `TypeError` — `append` mag niet op een tuple
De twee regels verschillen door één komma. Wat meldt type()?
one = (5)
really = (5,)
print(type(one))
print(type(really))- A<class 'int'> <class 'int'>
- B<class 'tuple'> <class 'tuple'>
- C<class 'int'> <class 'tuple'>
- D<class 'tuple'> <class 'int'>
Voor antwoorden heb je een account nodig
Log in om je antwoorden te controleren
De vragen staan hierboven, en ze in je hoofd uitwerken is waar het om draait. Log in om de antwoorden, de uitleg en de hints in drie niveaus te zien.
Jouw beurt
Schrijf een bestand genaamd contacts.py met een lijst van minstens vijf mensen, waarvan elke persoon een tuple is van een naam, een leeftijd en een favoriete vak.
Daarna:
- Print iedereen in uitgelijnde kolommen, met
for name, age, subject in contacts: - Vind de oudste persoon, unpack die, en print één zin over hem of haar
- Maak een lijst met alleen de namen en print die op één regel met
join - Print de gemiddelde leeftijd
- Verwissel twee variabelen in één regel en laat zien dat het werkte
Breek het daarna drie keer met opzet en lees elke melding:
- Probeer de leeftijd in een van de tuples te veranderen
- Probeer
appendaan te roepen op een tuple - Probeer een tuple van drie waarden te unpacken in twee namen
Drie verschillende fouten komen terug — TypeError, AttributeError, ValueError. Kun je aan jezelf uitleggen welke het is en waarom, dan zijn tuples van jou.
Stap 6 van 6
Uitdaging — de hoofdstukquiz
Tien vragen van makkelijk naar moeilijk. De laatste zijn met opzet lastig.
Log in om de quiz te maken