DEV Community

Cover image for Python Mystery Quiz: Can You Crack This Code?
Aaron Rose
Aaron Rose

Posted on

Python Mystery Quiz: Can You Crack This Code?

A deceptively simple puzzle that reveals one of Python's most fundamental concepts


The Challenge

Before we dive into any explanations, let's start with a quiz. Take a look at this Python code and predict what it will output:

a = 500
b = a
a = a + 100

list1 = [1, 2]
list2 = list1
list1.append(3)

print(f"b is {b}")
print(f"list2 is {list2}")
Enter fullscreen mode Exit fullscreen mode

What do you think the output will be?

A) b is 600 and list2 is [1, 2]

B) b is 500 and list2 is [1, 2, 3]

C) b is 500 and list2 is [1, 2]

D) b is 600 and list2 is [1, 2, 3]

Take a moment to think through it. The code looks straightforward, but there's something subtle happening here that trips up even experienced developers.

Scroll down when you're ready for the answer...


The Answer

The correct answer is B: b is 500 and list2 is [1, 2, 3]

If you got it right, excellent! If not, don't worry—this behavior puzzles many Python developers. The key to understanding this lies in one crucial concept that many tutorials gloss over.

The Mystery Revealed

The different behaviors in our code aren't random or inconsistent. They're the logical result of how Python handles two different types of objects: mutable and immutable.

Let's break down exactly what's happening, step by step.

Part 1: The Integer Surprise

a = 500
b = a
a = a + 100
Enter fullscreen mode Exit fullscreen mode

Here's what Python is actually doing:

  1. a = 500: Creates an integer object containing 500 and assigns the name a to point to it
  2. b = a: Makes b point to the same 500 object that a is pointing to
  3. a = a + 100: This is the key line. It evaluates a + 100 (which is 600), creates a brand new integer object containing 600, and reassigns a to point to this new object

The crucial insight: integers are immutable in Python. You cannot change the value of an integer object once it's created. When you write a = a + 100, Python doesn't modify the existing 500 object—it creates a new 600 object.

Since b was never reassigned, it still points to the original 500 object. Hence: b is 500.

Part 2: The List Plot Twist

list1 = [1, 2]
list2 = list1
list1.append(3)
Enter fullscreen mode Exit fullscreen mode

Now let's trace through the list operations:

  1. list1 = [1, 2]: Creates a list object containing [1, 2] and assigns list1 to point to it
  2. list2 = list1: Makes list2 point to the same list object that list1 is pointing to
  3. list1.append(3): Here's the difference—this modifies the existing list object by adding 3 to it

The key insight: lists are mutable in Python. When you call append(), you're modifying the existing list object, not creating a new one.

Since both list1 and list2 point to the same list object, and that object has been modified, both names now refer to [1, 2, 3]. Hence: list2 is [1, 2, 3].

The Bigger Picture: Variables Are Names, Not Boxes

This puzzle illustrates a fundamental truth about Python that many developers misunderstand: variables are names that point to objects, not containers that hold values.

Think of it like this:

  • A variable name is like a sticky note with a name written on it
  • Objects are like boxes containing actual data
  • Assignment sticks the name-tag onto a box
  • Multiple names can point to the same box

When you understand this mental model, the mystery code makes perfect sense:

  • With immutable objects (integers), operations create new boxes and move name-tags to point to them
  • With mutable objects (lists), operations modify the contents of existing boxes while all name-tags pointing to that box stay put

Why This Matters

Understanding mutability isn't just academic—it prevents real bugs. Consider this common Python gotcha:

def add_item(item, target_list=[]):
    target_list.append(item)
    return target_list

# This doesn't work as expected!
list1 = add_item("first")
list2 = add_item("second")  # Oops! list2 is now ["first", "second"]
Enter fullscreen mode Exit fullscreen mode

The default list [] is mutable, so all function calls share the same list object. Once you understand object mutability, this behavior becomes predictable rather than mysterious.

Test Your Understanding

Now that you know the secret, try predicting the output of this code:

x = "hello"
y = x
x = x + " world"

dict1 = {"key": "value"}
dict2 = dict1
dict1["key"] = "modified"

print(f"y is '{y}'")
print(f"dict2 is {dict2}")
Enter fullscreen mode Exit fullscreen mode

The answer: y is 'hello' and dict2 is {'key': 'modified'} (strings are immutable, dictionaries are mutable).

Wrapping Up

Python's variable system is elegant once you understand the underlying model. Variables don't contain objects—they point to them. Whether that pointed-to object can be modified depends on its mutability.

This single concept explains countless Python behaviors that seem mysterious at first glance. Master it, and you'll find Python code much more predictable and debuggable.

Understanding mutability is just one of many elegant concepts that make Python powerful. Once you see the pattern, you'll start recognizing it everywhere in your code.


What other Python mysteries have puzzled you? Share your examples in the comments—there might be a simpler explanation than you think! And if you found this helpful, follow for more Python insights that demystify the magic behind the code.


Aaron Rose is a software engineer and technology writer at tech-reader.blog and the author of Think Like Genius.

Top comments (0)