Counting Missing Values in Pandas – Best Techniques 2026

Data Manipulation Mar 18, 2026

Counting Missing Values in Pandas – Best Techniques 2026

Accurately counting missing values is the foundation of any good data cleaning process. In 2026, Pandas provides several efficient and informative ways to count missing values, from simple totals to detailed per-column and per-row breakdowns.

TL;DR — Most Useful Commands

  • df.isna().sum() – Count missing values per column
  • df.isna().sum().sum() – Total missing values in the entire DataFrame
  • df.isna().mean() * 100 – Percentage of missing values per column
  • df.isna().sum(axis=1) – Missing values per row

1. Basic Counting of Missing Values

import pandas as pd

# Create a small demo file so this example runs as-is
# (in your project, sales_data.csv is your real export)
import numpy as np
rng = np.random.default_rng(42)
n = 60
pd.DataFrame({
    "order_date": pd.date_range("2026-01-01", periods=n, freq="3D"),
    "customer_id": rng.integers(101, 121, n),
    "customer_name": rng.choice([" ana", "ben ", "chen", "dana"], n),
    "product_id": rng.integers(1, 9, n),
    "region": rng.choice(["North", "South", "East", "West"], n),
    "category": rng.choice(["Electronics", "Computers", "Books", "Home"], n),
    "payment_method": rng.choice(["card", "cash", "wallet"], n),
    "segment": rng.choice(["consumer", "business"], n),
    "quantity": rng.integers(1, 6, n),
    "amount": rng.uniform(50, 2500, n).round(2),
    "discount": rng.choice([0.0, 0.05, 0.1, 0.2], n),
}).assign(
    price=lambda d: (d["amount"] / d["quantity"]).round(2),
    profit=lambda d: (d["amount"] * rng.uniform(0.05, 0.3, n)).round(2),
).assign(
    ship_date=lambda d: d["order_date"] + pd.Timedelta(days=2),
    status=lambda d: np.where(d["amount"] > 2000, "priority", "standard"),
).to_csv("sales_data.csv", index=False)

df = pd.read_csv("sales_data.csv", parse_dates=["order_date"])

# Count missing values in each column
missing_count = df.isna().sum()
print("Missing values per column:")
print(missing_count.sort_values(ascending=False))

# Total number of missing values in the whole dataset
total_missing = df.isna().sum().sum()
print(f"\nTotal missing values in dataset: {total_missing}")

2. Percentage of Missing Values

# Percentage missing per column (very useful for reporting)
missing_pct = df.isna().mean() * 100
print("Percentage of missing values per column:")
print(missing_pct.round(2).sort_values(ascending=False))

3. Row-wise Missing Value Count

# How many missing values are in each row?
row_missing = df.isna().sum(axis=1)

print(f"Rows with at least one missing value: {(row_missing > 0).sum()}")
print("\nDistribution of missing values per row:")
print(row_missing.value_counts().sort_index())

4. Best Practices in 2026

  • Always start with df.isna().sum() to see missing values per column
  • Use df.isna().mean() * 100 to understand the percentage of missing data
  • Sort the results with .sort_values(ascending=False) to focus on the worst columns first
  • Check row-wise missingness with df.isna().sum(axis=1) when rows are important
  • Combine counting with visualization (bar plot or heatmap) for better understanding

Counting Missing Values

Counting gaps tells you how serious a missing-data problem is. isna().sum() counts per column, isna().sum(axis=1) counts per row, and isna().sum().sum() gives a total for the table.

Counting by group often reveals where data collection failed. Grouping and summing isna() can show that one region or one week accounts for most of the gaps.

Worked Example: Gaps per Column, Row and Group

Sensor readings are counted in several directions.

import pandas as pd
import numpy as np

df = pd.DataFrame({
    "site": ["A", "A", "B", "B", "B"],
    "temp": [21.0, np.nan, np.nan, 19.5, np.nan],
    "humidity": [40, 42, np.nan, 38, 39],
})

print(df.isna().sum())
print(df.isna().sum(axis=1).tolist())
print(int(df.isna().sum().sum()))
print(df.drop(columns="site").isna().groupby(df["site"]).sum())

There are four gaps in total, and site B accounts for three of them. Row counts show that the third reading lacks both measurements.

Practical Tips

Counts become more meaningful when they are compared with the size of the data. Ten missing values in a table of ten thousand rows are a minor issue, while ten in a table of fifty rows may change every result. Pair counts with percentages, and check counts by group or by date to find out whether one source is responsible for most of the problem.

Common Mistakes

  • Using count(), which counts non-missing values.
  • Forgetting axis=1 for row counts.
  • Including the grouping column in the summed mask.
  • Reporting totals without the size of the dataset.

Quick Summary

  • isna().sum() counts per column.
  • isna().sum(axis=1) counts per row.
  • Group the mask to find where gaps occur.
  • count() is the opposite: non-missing values.

Conclusion

Counting missing values accurately is the first critical step in data cleaning. In 2026, the combination of df.isna().sum() for counts and df.isna().mean() * 100 for percentages gives you a clear picture of data quality. Always analyze both column-wise and row-wise missingness before deciding how to handle the missing data.

Next steps:

  • Run a complete missing value count analysis on one of your current datasets using the methods above and identify which columns need attention

Related Tutorials

Share:
Last updated: March 2026
Built-in Functions in Python 2026 str() in Python 2026: String Conversion + Modern Formatting & Best Practices memoryview with JAX in Python 2026: Zero-Copy NumPy → JAX Array Interop + Efficient ML Examples memoryview with TensorFlow in Python 2026: Zero-Copy NumPy → Tensor Interop + GPU Pinning & ML Examples memoryview with TensorFlow in Python 2026: Zero-Copy NumPy → Tensor Interop + ML Examples memoryview with NumPy & PyTorch in Python 2026: Zero-Copy Views, Efficient Slicing & ML Interop Examples memoryview with NumPy in Python 2026: Zero-Copy Views, Efficient Slicing & Real ML Examples memoryview() in Python 2026: Zero-Copy Magic for Large Binary Data + Real Examples import() in Python 2026: How It Works, Security Risks & Modern Alternatives (importlib) zip() in Python 2026: How to Use It, strict=True Behavior & Real-World Examples vars() in Python 2026: Accessing Object Namespace + Modern Introspection Patterns type() in Python 2026: Dynamic Type Inspection & Object Creation + Modern Patterns tuple() in Python 2026: Immutable Sequences + Modern Patterns & Best Practices super() in Python 2026: Method Resolution & Modern Inheritance Patterns sum() in Python 2026: Summing Iterables + Modern Numeric Patterns & Best Practices staticmethod() in Python 2026: Static Methods, Utility Functions & Modern Best Practices sorted() in Python 2026: Sorting Iterables + Modern Patterns & Best Practices slice() in Python 2026: Creating Slice Objects + Modern Patterns & Best Practices setattr() in Python 2026: Dynamic Attribute Setting + Modern Patterns & Safety set() in Python 2026: Mutable Sets Creation + Modern Patterns & Best Practices