List Comprehensions — Concise and Powerful List Creation
List comprehensions are one of Python’s most elegant and expressive features.
Chapter 3: Data Structures
Sub-chapter: List Comprehensions — Concise and Powerful List Creation
List comprehensions are one of Python’s most elegant and expressive features.
They allow you to build new lists in a single, readable line of code, transforming or filtering data as you iterate over sequences.
Not only do they make code shorter, but they are also faster and often clearer than traditional loops.
🧠 Why Use List Comprehensions?
List comprehensions are ideal for:
- ✅ Creating new lists from existing iterables
- ⚡ Transforming data (e.g., squaring numbers, extracting substrings)
- 🧩 Filtering items based on conditions
- 🧱 Flattening or restructuring nested lists
⚙️ Basic Syntax
new_list = [expression for item in iterable if condition]
| Component | Description |
|---|---|
| expression | The operation or transformation performed on each item |
| item | Variable representing the current element |
| iterable | Source data (list, tuple, range, etc.) |
| condition | (Optional) Filter that decides which items to include |
🧮 Example 1 — Creating a List of Squares
numbers = [1, 2, 3, 4, 5]
squares = [x**2 for x in numbers]
print(squares) # [1, 4, 9, 16, 25]
Equivalent loop:
squares = []
for x in numbers:
squares.append(x**2)
💡 List comprehensions are more compact and faster than explicit loops.
🧩 Example 2 — Filtering Elements
numbers = [1, 2, 3, 4, 5, 6, 7, 8, 9]
even_squares = [x**2 for x in numbers if x % 2 == 0]
print(even_squares) # [4, 16, 36, 64]
The condition filters elements before applying the expression.
🧠 Example 3 — Conditional Expressions Inside Comprehensions
You can apply conditional logic within the expression:
labels = ["even" if x % 2 == 0 else "odd" for x in range(1, 6)]
print(labels) # ['odd', 'even', 'odd', 'even', 'odd']
🧩 The conditional comes before the
forkeyword in this form.
🧮 Example 4 — Transforming Strings
words = ["python", "rocks", "hard"]
uppercased = [word.upper() for word in words]
print(uppercased) # ['PYTHON', 'ROCKS', 'HARD']
🧱 Example 5 — Flattening a Nested List
List comprehensions can replace nested loops neatly.
matrix = [[1, 2, 3], [4, 5, 6], [7, 8, 9]]
flattened = [num for row in matrix for num in row]
print(flattened) # [1, 2, 3, 4, 5, 6, 7, 8, 9]
⚙️ Example 6 — Working with Dictionaries and Tuples
Extract keys or transform dictionary data:
person = {"name": "Alice", "age": 30, "city": "New York"}
keys = [key for key in person]
values = [v.upper() if isinstance(v, str) else v for v in person.values()]
print(keys) # ['name', 'age', 'city']
print(values) # ['ALICE', 30, 'NEW YORK']
🧩 Example 7 — List Comprehensions with Files (Real-World Example)
Let’s read a file and collect only lines that contain the word “error”.
# Read and filter log lines
with open("system.log") as f:
error_lines = [line.strip() for line in f if "error" in line.lower()]
print(error_lines)
This compactly replaces a full multi-line loop and works beautifully for quick data filtering.
⚡ Example 8 — Using enumerate() and zip()
names = ["Alice", "Bob", "Charlie"]
ages = [25, 30, 35]
combined = [f"{i}. {name} ({age})" for i, (name, age) in enumerate(zip(names, ages), start=1)]
print(combined)
# ['1. Alice (25)', '2. Bob (30)', '3. Charlie (35)']
🧮 Example 9 — Nested Conditions and Multiple Loops
pairs = [(x, y) for x in range(3) for y in range(3) if x != y]
print(pairs)
# [(0, 1), (0, 2), (1, 0), (1, 2), (2, 0), (2, 1)]
🧱 Example 10 — Real-World Data Transformation
Imagine a dataset of product names with mixed cases and extra spaces:
products = [" apple ", "BANANA", "Cherry ", "banana"]
cleaned = sorted({p.strip().capitalize() for p in products})
print(cleaned) # ['Apple', 'Banana', 'Cherry']
Here, we combined:
- Comprehension to clean and format text
- Set conversion to remove duplicates
- Sorting for presentation
⚙️ Performance Comparison
List comprehensions are generally faster than for loops and map() due to internal optimizations.
import timeit
print(timeit.timeit('[x**2 for x in range(1000)]', number=10000))
print(timeit.timeit('list(map(lambda x: x**2, range(1000)))', number=10000))
⚡ List comprehensions typically outperform equivalent
map()or loop-based code.
🧱 Comparison: for Loop vs Comprehension vs map()
| Approach | Syntax | Readability | Speed | Mutability |
|---|---|---|---|---|
| For Loop | Multi-line | ✅ Clear | 🐢 Slower | Mutable |
| Comprehension | One line | ✅✅ Compact | ⚡ Fast | New list |
| map() / filter() | Functional | ⚠️ Abstract | ⚡ Fast | Returns iterator |
⚠️ Common Pitfalls
- Over-nesting: Nested comprehensions can be hard to read — use loops instead when logic gets complex.
- Large datasets: Creating massive lists in memory can cause performance issues — consider generator expressions
( ). - Readability first: One-liners are elegant but can obscure intent if overused.
🧠 Best Practices
- Keep list comprehensions short and focused.
- Combine them with conditional filters for clarity.
- Use set or dict comprehensions when appropriate.
- For large data processing, prefer generator expressions to save memory.
- Always prioritize readability over cleverness.
🧾 Key Takeaways
- List comprehensions make Python code concise, efficient, and elegant.
- Support conditional filtering, nested loops, and data transformations.
- Faster than
forloops for most use cases. - Ideal for data cleanup, file filtering, transformations, and analysis tasks.
Mastering list comprehensions lets you write Python code that’s not only efficient — but beautifully expressive.