Big picture
Collections hold related values under a common structure. Marks for a class belong naturally in a sequence, fixed coordinates can use a tuple, and an attendance lookup can associate each roll number with its status. Choosing a structure depends on operations, not just on bracket shape.
This lesson compares lists, tuples and dictionaries, then follows the effects of changes and copies. In output questions, record both the values and which names refer to the same object. Many surprising answers come from overlooking that second part.
Learning goals
Compare sequences with mappings.
Apply list and tuple operations with correct return values.
Explain aliasing and shallow-copy behaviour.
Use dictionary keys, defaults and updates.
Design collection algorithms with empty-input checks.
Core ideas
1. Comparing the three structures
A list is a mutable ordered sequence, a tuple is an immutable ordered sequence, and a dictionary is a mutable mapping from keys to values. Sequences use positional indices; dictionaries use keys. Lists and tuples permit repeated values. A dictionary cannot retain two separate entries with the same key: a later assignment replaces that key's value.
Structure | Access | Mutability | Typical use |
|---|---|---|---|
List | Integer index | Mutable | Editable marks |
Tuple | Integer index | Immutable structure | Fixed coordinates |
Dictionary | Key | Mutable | Roll-number lookup |
Modern Python dictionaries preserve insertion order, but this does not make them positional sequences. The expression d[0] requests the key zero rather than the first inserted entry. Describe purpose and permitted operations together when justifying a data structure.
2. List creation, indexing and slicing
Create lists with square brackets or list applied to an iterable. A list can contain mixed types and nested lists. Positive and negative indices work as for strings, and slices exclude their stop. Unlike a string, a list allows element assignment and slice assignment.
For marks = [63, 78, 85], changing marks[1] replaces the second value. A slice can produce a new outer list, but it does not recursively duplicate nested elements. An empty list is legal, yet accessing its first element raises IndexError. Membership tests values, while len counts top-level elements. A nested list counts as one element at the outer level, regardless of how many values it contains. Draw separate boxes for the outer list and inner lists when tracing a nested structure.
3. Adding, removing and arranging list elements
append(x) adds x as one element; extend(iterable) adds each item from the iterable. insert(i, x) inserts before the specified position. remove(x) deletes the first matching value and raises ValueError when absent. pop(i) removes and returns the indexed item, defaulting to the last. del removes by position or slice.
sort() sorts the existing list and returns None. sorted(...) returns a new sorted list. reverse() reverses in place rather than sorting in descending order. Use count and index for occurrence counts and first positions. Distinguish the list's changed state from a method's return value: assigning the result of append or sort back to the list variable usually loses the reference you intended to retain.
4. Aliasing, copying and a tested example
Aliasing means multiple names refer to the same object. Assignment does not automatically copy a list. A shallow copy creates a new outer collection but shares references to nested objects.
a = [8, 3]
b = a
c = a[:]
b.append(5)
c.sort()
print(a, b, c)
nested = [[1], [2]]
copy = nested[:]
copy[0].append(9)
print(nested)Output:
[8, 3, 5] [8, 3, 5] [3, 8]
[[1, 9], [2]]The append affects both aliases but not the separate outer list c. Sorting c returns no new list. In the nested example, the copied outer list still refers to the same inner list at position zero, so appending through the copy changes the inner object seen through nested. This is a reference relationship, not a failure of slicing.
5. Tuples and unpacking
A tuple groups values without allowing its own elements to be reassigned. Commas create tuples: a one-element tuple needs a trailing comma, such as (8,). Parentheses without that comma simply group the expression. Empty tuples use ().
Tuples support indexing, slicing, concatenation, repetition, membership, count and index, but not append or in-place sort. Unpacking binds corresponding elements to names, and the number of targets must match unless special unpacking syntax is used. A tuple can contain a mutable list: the tuple's references cannot be replaced, but that inner list can still change. Thus “immutable tuple” does not mean every object reachable from it is immutable. This distinction matters when predicting nested mutations and considering whether a tuple is suitable as a dictionary key.
6. Dictionary keys and updates
A key–value pair associates a unique key with a value. Keys must be hashable; common suitable keys include strings, integers and tuples whose elements are themselves hashable. Lists cannot be keys. Values may repeat and can be mutable objects.
Use d[key] to retrieve an existing entry, and d[key] = value to add or replace one. get(key, default) returns a fallback for a missing key without inserting it. update merges entries, replacing matching keys. pop removes a key and returns its value; del removes the entry without returning it. A missing lookup with brackets raises KeyError. Choose explicit defaults carefully: returning zero for missing marks may hide a data-quality issue if absence and an actual zero score mean different things.
7. Traversal, views and a mapping example
Iterating directly over a dictionary visits keys. keys, values and items provide views of keys, values and key–value pairs. Use items when both components are needed. Avoid changing dictionary size while iterating over it; collect intended changes first or traverse a separate snapshot.
stock = {"pen": 12, "book": 5}
stock["pen"] += 3
stock.update({"book": 7, "file": 4})
print(stock["pen"], stock.get("ruler", 0))
for item, count in stock.items():
print(item, count)Output:
15 0
pen 15
book 7
file 4The missing ruler lookup uses a default without adding a ruler entry. Updating an existing key changes its value, while the new file entry is appended to the insertion order. The dictionary contains three entries, not four.
8. Collection algorithms and safe testing
For totals and averages, sum the relevant sequence and divide only when its length is nonzero. For a linear search, examine values until a match appears or the traversal ends. To find the largest item manually, initialise from an actual first element after checking the sequence is nonempty; starting at zero fails when all values are negative.
A frequency dictionary counts occurrences by updating a key for each observed item. Decide whether differently cased words should share a key before counting. Test duplicates, an empty input, one item and a missing lookup. When deleting list elements during forward traversal, shifting indices can cause skipped entries; constructing a filtered result is often clearer. Explain the invariant: after each processed item, the stored summary should correctly describe the items examined so far.
A reliable approach to questions
Read the command word before choosing an answer. A definition needs the distinguishing feature; a comparison needs matching criteria on both sides; an application needs a reason linked to the situation.
Extract the supplied evidence and assumptions. Keep a small working table rather than relying on memory. If information is absent, state the limit instead of inventing a value or claiming certainty.
Work through the relevant rule one step at a time. For a program, record the changing state; for a scenario, connect the requirement to the feature that meets it. Explain why the closest alternative fails.
Check the result against the original question, including boundary cases, units and wording. Present a concise final answer followed by enough reasoning for another student to reproduce your conclusion.
Connections that matter
Strings share sequence indexing and slicing but are immutable.
Iteration supports searching, totals and frequency counts.
Functions can receive collections, so mutation rules affect callers.
Common mistakes
Calling assignment a copy: two names may alias one mutable object.
Expecting sort to return a list: it returns None.
Assuming tuple immutability freezes inner lists: nested mutable objects can change.
Using dictionary position as a key: dictionary access is key-based.
Revision checklist
I can compare sequences with mappings.
I can apply list and tuple operations with correct return values.
I can explain aliasing and shallow-copy behaviour.
I can use dictionary keys, defaults and updates.
I can design collection algorithms with empty-input checks.