Dictionaries store key–value pairs: you look up a key and get back a value. They are the natural structure for JSON-like data, configuration, and anything that maps names or IDs to something else. This guide covers creating and using dicts, safe access, iteration, and common patterns. For the type itself see Data types; for reading and writing JSON see How to read and write JSON.

1. What a dictionary is and when to use it

A dictionary is a mutable mapping: each key maps to exactly one value, keys must be unique and hashable (immutable types like str, int, tuple), and from Python 3.7 onward dicts preserve insertion order. Use a dict when you need to look up by name or id—user profiles, API responses, settings. Use a list when order matters and you index by position; use a set when you only care about unique keys and do not need values.

2. Creating dictionaries

Use curly braces with key: value pairs, or the dict() constructor. Keys can be strings (most common), numbers, or tuples of immutables.

# Empty dict
my_dict = {}

# Literal with string keys
person = {
    "name": "Alice",
    "age": 25,
    "city": "New York",
}

# dict() with keyword args (keys become strings)
person2 = dict(name="Bob", age=30, city="London")

# From list of (key, value) pairs
person3 = dict([("name", "Charlie"), ("age", 35)])

3. Accessing values and avoiding KeyError

d[key] returns the value for key but raises KeyError if the key is missing. Use d.get(key) to return None when the key is absent, or d.get(key, default) to return a default. Check membership with key in d before using d[key] if you prefer.

person = {"name": "Alice", "age": 25}

name = person["name"]              # "Alice"
age = person.get("age")            # 25
email = person.get("email")        # None
email = person.get("email", "N/A") # "N/A"

if "name" in person:
    print(person["name"])

For nested structures a missing key also causes KeyError—see KeyError with nested dicts and use .get() or check each level.

4. Adding, updating, and removing items

Assign to a key to add or update: d[key] = value. d.update(other) merges in another dict (or iterable of pairs). To remove: del d[key] (raises KeyError if missing), d.pop(key) (returns the value), d.popitem() (returns and removes an arbitrary pair in Python <3.7, last pair in 3.7+), d.clear() (removes all).

person = {"name": "Alice"}
person["age"] = 25
person["name"] = "Bob"
person.update({"city": "NYC", "country": "USA"})

del person["age"]
city = person.pop("city")
person.clear()   # {}

5. Keys, values, and items

d.keys(), d.values(), and d.items() return view objects that reflect the current dict. Iterating over d is the same as iterating over d.keys(). Use d.items() when you need both key and value in a loop. len(d) is the number of key–value pairs.

person = {"name": "Alice", "age": 25, "city": "NYC"}

for key in person:
    print(key, person[key])

for key, value in person.items():
    print(f"{key}: {value}")

6. Dictionary comprehensions

Build a dict from an iterable with {key_expr: value_expr for ... in ...}. Optional if at the end filters which pairs are included.

squares = {x: x ** 2 for x in range(5)}
# {0: 0, 1: 1, 2: 4, 3: 9, 4: 16}

even_squares = {x: x ** 2 for x in range(10) if x % 2 == 0}

7. Nested dictionaries

Values can be other dicts or lists. Access with chained brackets: d["a"]["b"]. If an intermediate key might be missing, use .get() or a loop to avoid KeyError.

students = {
    "Alice": {"age": 20, "grade": "A", "courses": ["Math", "Science"]},
    "Bob": {"age": 21, "grade": "B", "courses": ["History", "English"]},
}
alice_age = students["Alice"]["age"]
alice_courses = students["Alice"]["courses"]

8. Common patterns: counting and grouping

To count occurrences, use d.get(key, 0) + 1 in a loop, or collections.Counter. To group items by a key, use a dict of lists and append:

fruits = ["apple", "banana", "apple", "orange", "banana", "apple"]
count = {}
for fruit in fruits:
    count[fruit] = count.get(fruit, 0) + 1
# {"apple": 3, "banana": 2, "orange": 1}

# Group by grade
students = [{"name": "Alice", "grade": "A"}, {"name": "Bob", "grade": "B"}, {"name": "Charlie", "grade": "A"}]
by_grade = {}
for s in students:
    g = s["grade"]
    if g not in by_grade:
        by_grade[g] = []
    by_grade[g].append(s["name"])
# {"A": ["Alice", "Charlie"], "B": ["Bob"]}

9. Dictionary vs list

Use a dict when you look up by a key (name, id, symbol). Use a list when you care about order and position. Dict keys must be immutable; list indices are always integers. Both are mutable. For more on when to choose which, see Data types and Lists vs tuples (lists vs tuples; dict is the mapping type).

10. Best practices and next steps

Prefer get() when the key might be missing to avoid KeyError. Use descriptive key names. For defaults per key, consider collections.defaultdict. Copy with d.copy() (shallow) or copy.deepcopy(d) if values are mutable—see copy vs deepcopy. Next: sets for unique collections, tuples for immutable sequences, and read and write JSON for real‑world dict data.