No history yet

Advanced Data Structures

Beyond the List

You're already familiar with Python's lists for storing ordered sequences of items. But for many real-world problems, lists aren't the most efficient tool. We need structures that can handle unique items, map keys to values, or guarantee that data can't be changed. This is where dictionaries, sets, and tuples come in.

These advanced data structures are the workhorses of Python. They offer specialised ways to store and access data, often with significant performance benefits. Mastering them is key to writing cleaner, faster, and more professional code.

Dictionaries for Key-Value Mapping

Think of a dictionary as a real-world dictionary. You don't read it from start to finish; you look up a word (a key) to find its definition (a value). Python dictionaries work the same way. They store data as key-value pairs, providing an incredibly fast way to retrieve a value if you know its key.

Unlike lists, which are indexed by integers, dictionary keys can be almost any immutable type, such as strings, numbers, or even tuples. This makes them perfect for modelling objects or storing configuration settings.

# Creating a dictionary for a user profile
user_profile = {
    "username": "alex_w",
    "user_id": 101,
    "is_active": True,
    "permissions": ["read", "write"]
}

# Accessing a value by its key
print(user_profile["username"])  # Output: alex_w

# Adding a new key-value pair
user_profile["last_login"] = "2023-10-27T10:00:00Z"

# Modifying an existing value
user_profile["is_active"] = False

# Using the .get() method for safe access
# This returns None instead of raising an error if the key doesn't exist.
email = user_profile.get("email")
print(email) # Output: None

A common task is iterating through a dictionary's contents. You can loop through its keys, its values, or both at the same time.

user_profile = {
    "username": "alex_w",
    "user_id": 101,
    "is_active": True
}

# Looping through keys (the default behavior)
print("Keys:")
for key in user_profile:
    print(key)

# Looping through values
print("\nValues:")
for value in user_profile.values():
    print(value)

# Looping through key-value pairs
print("\nItems:")
for key, value in user_profile.items():
    print(f"{key}: {value}")

Sets for Uniqueness

A set is an unordered collection of unique items. Think of it as a bag of things where duplicates are automatically discarded and the order doesn't matter. Sets are highly optimised for membership testing (checking if an item is present) and for performing mathematical set operations like union, intersection, and difference.

They are ideal for tasks like removing duplicates from a list or comparing two collections of items.

# Creating a set from a list with duplicates
numbers = [1, 2, 2, 3, 4, 4, 4]
unique_numbers = set(numbers)
print(unique_numbers)  # Output: {1, 2, 3, 4}

# Checking for membership is very fast
print(3 in unique_numbers) # Output: True

# Set operations
set_a = {1, 2, 3, 4}
set_b = {3, 4, 5, 6}

# Union: all items from both sets
print(set_a | set_b)  # Output: {1, 2, 3, 4, 5, 6}

# Intersection: items present in both sets
print(set_a & set_b)  # Output: {3, 4}

# Difference: items in set_a but not in set_b
print(set_a - set_b)  # Output: {1, 2}

Tuples for Immutability

A tuple is an ordered collection of items, much like a list. The crucial difference is that tuples are immutable, meaning they cannot be changed after they are created. You can't add, remove, or modify elements in a tuple.

This immutability might seem like a limitation, but it's a powerful feature. It guarantees that the data remains constant, which can prevent accidental modifications in large programs. Because they are simpler than lists, Python can implement internal optimisations that make them slightly faster and more memory-efficient.

They are commonly used for data that shouldn't change, such as coordinates (x, y), RGB colour values, or returning multiple values from a function.

# A tuple of coordinates
point = (10, 20)

# Accessing elements is the same as with lists
print(f"x: {point[0]}, y: {point[1]}")

# A function returning multiple values as a tuple
def get_user_info():
    return ("alex_w", 101, True)

# Unpacking a tuple into variables
username, user_id, is_active = get_user_info()
print(f"User: {username}, ID: {user_id}")

# This would raise a TypeError because tuples are immutable
# point[0] = 15

A common saying among Python developers is: "Use a tuple when you can, and a list when you must."

Now that you've seen these three powerful data structures, let's test your understanding.

Quiz Questions 1/5

Which of the following data structures is immutable, meaning its contents cannot be changed after creation?

Quiz Questions 2/5

What is the primary advantage of using a set over a list for checking if an item exists within a collection?

Understanding when to use each data structure is a mark of an effective Python programmer. Choosing the right one can make your code not only faster but also more readable and robust.