How to check if a dictionary is empty in Python

Discover multiple ways to check for an empty dictionary in Python. Get tips, see real-world applications, and learn to debug common errors.

How to check if a dictionary is empty in Python
Published on: 
Thu
Feb 12, 2026
Updated on: 
Mon
Apr 13, 2026
The Replit Team

You often need to check if a Python dictionary is empty for data validation or control flow. Python provides several straightforward methods to perform this check with minimal code.

In this article, you'll explore different techniques to check for an empty dictionary. You'll find practical tips, real-world applications, and debugging advice to help you write more robust code.

Using the not operator with dictionaries

my_dict = {}
if not my_dict:
print("The dictionary is empty")
else:
print("The dictionary is not empty")--OUTPUT--The dictionary is empty

In Python, all objects have an inherent boolean value, often called their "truthiness." Empty collections—including dictionaries, lists, and sets—are considered "falsy," meaning they evaluate to False in a boolean context. This behavior is a core part of the language's design.

The not operator simply inverts this value. When you write if not my_dict, you're directly testing if the dictionary is falsy. If my_dict is empty, the expression becomes not False, which evaluates to True, executing your conditional code. It's a concise and idiomatic approach favored for its readability.

Basic approaches to check for empty dictionaries

While leveraging a dictionary's truthiness is common, you can also use the len() function or a direct comparison to check if it's empty.

Using the len() function

empty_dict = {}
non_empty_dict = {"key": "value"}
print(f"Is empty_dict empty? {len(empty_dict) == 0}")
print(f"Is non_empty_dict empty? {len(non_empty_dict) == 0}")--OUTPUT--Is empty_dict empty? True
Is non_empty_dict empty? False

The built-in len() function gives you the number of key-value pairs in a dictionary. By comparing its output to 0, you create a very explicit check for emptiness. This method is often praised for its clarity.

  • It leaves no room for ambiguity; your code directly asks if the item count is zero.
  • This pattern is consistent for checking any collection in Python, like lists or sets, making your code easy to understand.

Using boolean evaluation

empty_dict = {}
non_empty_dict = {"a": 1, "b": 2}
print(f"bool(empty_dict) = {bool(empty_dict)}")
print(f"bool(non_empty_dict) = {bool(non_empty_dict)}")--OUTPUT--bool(empty_dict) = False
bool(non_empty_dict) = True

The bool() function explicitly converts an object to its boolean value. This is a direct way to see the "truthiness" of your dictionary. Since empty collections are considered "falsy" in Python, calling bool() on an empty dictionary returns False.

  • Any dictionary containing at least one key-value pair is "truthy" and evaluates to True.

While this method is very explicit, it's less common in practice. Most developers rely on Python's implicit boolean evaluation in conditional statements, like if my_dict:, for a more concise check when working with existing dictionaries, regardless of how you initially approach creating a dictionary in Python.

Comparing with an empty dictionary

my_dict = {}
is_empty = my_dict == {}
print(f"Is the dictionary empty? {is_empty}")

full_dict = {"a": 1}
print(f"Is full_dict empty? {full_dict == {}}")--OUTPUT--Is the dictionary empty? True
Is full_dict empty? False

You can directly compare your dictionary to an empty dictionary literal, {}, using the equality operator ==. This expression returns True if your dictionary contains no key-value pairs and False otherwise. It's an explicit and visually clear way to perform the check.

  • While this approach works, it's slightly less efficient because Python has to create a new empty dictionary object for the comparison.
  • Most developers prefer checking a dictionary's truthiness, like if not my_dict:, or its length, as those methods are generally more performant.

Advanced techniques for dictionary emptiness checks

Moving beyond the basic checks, you can also use specific dictionary methods, compare performance, and ensure type safety for more specialized situations.

Using dictionary methods

my_dict = {}
# Check if empty using keys()
if not my_dict.keys():
print("No keys found")
# Alternative using items()
if not my_dict.items():
print("No items found")--OUTPUT--No keys found
No items found

You can also use dictionary methods like keys() and items() to check for emptiness. These methods return "view objects," which are dynamic representations of the dictionary's contents. Just like the dictionary itself, an empty view object is falsy.

  • This allows you to write a check like if not my_dict.keys():, which leverages the same truthiness principle you've already seen.
  • The same logic also works with the values() method.

While this approach is valid, it's less common because checking the dictionary directly with if not my_dict: is more straightforward and idiomatic.

Performance comparison

import timeit

setup = "my_dict = {}"
print(f"not dict: {timeit.timeit('not my_dict', setup=setup, number=1000000):.6f} s")
print(f"len==0: {timeit.timeit('len(my_dict) == 0', setup=setup, number=1000000):.6f} s")
print(f"dict=={}: {timeit.timeit('my_dict == {}', setup=setup, number=1000000):.6f} s")--OUTPUT--not dict: 0.104372 s
len==0: 0.143678 s
dict=={}: 0.172548 s

When performance matters, not all checks are equal. The timeit module measures code execution speed, and the results consistently favor checking a dictionary's truthiness. The not my_dict approach is the fastest because it's a direct, low-level operation.

  • Checking len(my_dict) == 0 is slightly slower due to the overhead of a function call.
  • Comparing with an empty literal, my_dict == {}, is the least performant as it creates a new dictionary object just for the comparison. While these differences are tiny, the truthiness check is both the fastest and most idiomatic choice.

Type-safe emptiness checking

def is_empty_dict(obj):
if not isinstance(obj, dict):
raise TypeError("Expected dictionary type")
return len(obj) == 0

print(is_empty_dict({})) # Empty dictionary
try:
print(is_empty_dict([])) # Not a dictionary
except TypeError as e:
print(f"Error: {e}")--OUTPUT--True
Error: Expected dictionary type

Sometimes, you need to be certain you're working with a dictionary and not another type of object. This is where a type-safe check comes in handy. The function first uses isinstance(obj, dict) to verify the input is a dictionary. If it's not, a TypeError is raised, preventing your code from failing in unexpected ways.

  • This approach makes your functions more robust and predictable.
  • It's especially useful in larger applications where data might come from various sources and its type isn't guaranteed.

Move faster with Replit

Knowing how to check for an empty dictionary is a great step, but building a full application requires connecting many such techniques. Replit is an AI-powered development platform that lets you skip the setup and start coding instantly, as all Python dependencies are pre-installed.

Instead of piecing together individual functions, you can use Agent 4 to build a complete application from an idea. It takes your description and handles writing the code, connecting to databases, integrating APIs, and deploying your project. You can go from a concept to a working product much faster.

  • A user settings manager that checks for an empty configuration dictionary and applies default values if none are found.
  • An API data validator that filters out empty JSON objects before they are processed and stored in a database.
  • A form submission handler that verifies a dictionary of user inputs isn't empty before creating a new user profile.

Simply describe your app, and Replit will write the code, test it, and fix issues automatically, all within your browser.

Common errors and challenges

Even with simple checks, you can run into subtle errors involving nested data, potential KeyErrors, and other falsy values.

Debugging nested dictionary emptiness checks with .get()

When working with nested dictionaries, a simple emptiness check can easily backfire. If you try to access a key that doesn't exist, your program will crash with a KeyError before it even checks if the nested dictionary is empty.

The code below shows this in action. You'll see how a direct key access like user_data['preferences'] fails when the key is missing, while a similar check on an existing key works as expected.

user_data = {"profile": {}}

# This will work
if not user_data["profile"]:
print("Profile is empty")

# This will cause KeyError if the key doesn't exist
if not user_data["preferences"]:
print("Preferences are empty")

The code crashes with a KeyError because the expression user_data["preferences"] assumes the key exists. This is a common pitfall with nested data. The following example shows how to safely perform this check without causing an error.

user_data = {"profile": {}}

# Safely check if a nested dictionary exists and is empty
if not user_data.get("preferences", {}):
print("Preferences are empty or don't exist")

# For deeper nesting, continue chaining .get()
if not user_data.get("settings", {}).get("theme", {}):
print("Theme settings are empty or don't exist")

To avoid a KeyError, use the get() method. It lets you provide a default value if a key doesn't exist. The expression user_data.get("preferences", {}) returns an empty dictionary if the "preferences" key is missing, which then correctly evaluates to True in an if not check. This is a fundamental pattern when accessing dictionary in Python.

  • This is essential when you're working with data from external sources, like APIs, where you can't guarantee the data's structure.

Avoiding KeyError when checking dictionary subsections

A common mistake is assuming a key exists before checking its value, which often leads to a KeyError that crashes your program. This is especially tricky when you're trying to check if a nested dictionary section is empty. The following function attempts to set default display settings but will fail if the display key is missing. See how this simple oversight can cause a runtime error.

def process_user_settings(settings):
# This will raise KeyError if 'display' key doesn't exist
if not settings['display']:
settings['display'] = {"theme": "default", "font_size": 12}
return settings

user_settings = {"notifications": True}
process_user_settings(user_settings)

The function fails because it directly accesses settings['display'] without first checking if the 'display' key is present. This assumption causes a KeyError. The corrected function below shows how to avoid this runtime error, which is part of the broader topic of solving KeyError in Python.

def process_user_settings(settings):
# Use dict.get() with default empty dict
if not settings.get('display'):
settings['display'] = {"theme": "default", "font_size": 12}
return settings

user_settings = {"notifications": True}
result = process_user_settings(user_settings)
print(result)

The corrected function avoids a KeyError by using settings.get('display'). This method safely retrieves the key's value. If the key doesn't exist, get() returns None—a falsy value—so the if not condition correctly triggers. This allows you to handle both missing keys and empty dictionary values in one go. It's a crucial pattern when processing optional configuration data or unpredictable API responses where keys may not always be present.

Distinguishing between empty dictionaries and falsy values

A simple truthiness check using get() can be misleading. It doesn't distinguish between a missing key and a valid but "falsy" value like 0 or False. This ambiguity can cause your validation logic to fail, as the code below demonstrates.

def validate_config(config):
if not config.get("timeout"):
print("Timeout setting is missing")
if not config.get("retries"):
print("Retries setting is missing")

config = {"timeout": 0, "retries": 0}
validate_config(config) # Will incorrectly report both as missing

The check fails because a valid setting like 0 is falsy, causing the code to incorrectly flag it as missing. This creates ambiguity. The code below shows how to check for a missing key with more precision.

def validate_config(config):
# Use 'in' operator to check for key existence
if "timeout" not in config:
print("Timeout setting is missing")
if "retries" not in config:
print("Retries setting is missing")

config = {"timeout": 0, "retries": 0}
validate_config(config) # No output, correctly identifies keys exist

The corrected function uses the in operator to check for a key's existence, ignoring its value. This is the most precise way to determine if a key is truly missing. It's essential when your dictionary might contain valid "falsy" values like 0, False, or an empty string, which a simple truthiness check would incorrectly flag as missing. This approach ensures your validation logic is robust and handles all data correctly.

Real-world applications

Beyond theory, these checks are fundamental to everyday tasks like validating user input and managing a simple data cache.

Validating form input with empty value checks

You can easily validate form submissions by iterating through the data as a dictionary and checking for any empty values.

user_data = {"name": "John", "email": "john@example.com", "password": ""}

# Find fields with empty values
empty_fields = [k for k, v in user_data.items() if not v]

if not empty_fields:
print("Form is valid!")
else:
print(f"Please fill in these fields: {empty_fields}")

You can quickly find incomplete form fields using a list comprehension. This snippet builds a list called empty_fields by checking each value in the user_data dictionary. The expression if not v is what makes it work—it’s a concise way to identify "falsy" values, like the empty string for the password field.

  • The list comprehension gathers the keys of any items with these falsy values.

Finally, an if statement checks if the empty_fields list has any items. If it does, the form is invalid, and the user is prompted to complete the missing fields.

Creating a simple data cache system

Checking if a dictionary is empty is a simple yet effective way to build a basic cache that avoids redundant data fetching.

The get_user_data() function uses the condition if not cache: to determine if it needs to perform an expensive operation. Because an empty dictionary is "falsy," this check only passes when the cache has no data, which is typically just the first time the function is called.

  • On the first call, the cache is empty, so the app fetches and stores the data.
  • For all subsequent calls, the cache contains data, so the check fails and the stored information is returned instantly, improving performance.

def fetch_data():
print("Fetching data from database...")
return {"name": "Alice", "role": "Admin"}

# Simple cache implementation
cache = {}

def get_user_data():
if not cache:
# Cache is empty, fetch and store data
cache.update(fetch_data())
return cache

# First call - cache is empty
print(get_user_data())
# Second call - cache has data
print(get_user_data())

The get_user_data() function uses a simple check to see if the cache dictionary has any data. This pattern is a straightforward way to implement caching and improve efficiency.

  • If the cache is empty, the function calls fetch_data() to get new information and stores it using cache.update(), which demonstrates key principles of updating dictionary in Python.
  • When called again, the cache already contains data, so the check fails and the stored information is returned instantly.

This approach ensures the slow fetch_data() operation only runs once, saving time and resources.

Get started with Replit

Turn your knowledge into a real tool. Give Replit Agent a prompt like "build a settings validator that applies defaults if the config is empty" or "create a tool that filters empty API responses."

Replit Agent writes the code, tests for errors, and deploys your application. Start building with Replit.

Build your first app today

Describe what you want to build, and Replit Agent writes the code, handles the infrastructure, and ships it live. Go from idea to real product, all in your browser.

Build your first app today

Describe what you want to build, and Replit Agent writes the code, handles the infrastructure, and ships it live. Go from idea to real product, all in your browser.