pandas の dropna で欠損値を含む行・列を削除する

欠損値を含む行や列をそのまま使うと、集計結果や機械学習モデルの精度に悪影響を及ぼすことがあります。pandas の dropna メソッドを使えば、欠損値を含むデータを簡単に削除できます。

基本的な使い方

dropna をそのまま呼び出すと、1 つでも NaN を含む行が削除されます。

import pandas as pd
import numpy as np

df = pd.DataFrame({
    "name": ["Alice", "Bob", "Charlie", "Diana"],
    "age": [25, np.nan, 35, 28],
    "score": [88.5, 92.0, np.nan, np.nan]
})
print(df.dropna())

この例では age か score のどちらかに NaN がある行がすべて除外され、Alice の行だけが残ります。データ量が多い場合、思った以上に行が減ってしまうことがあるので注意が必要です。

列方向に削除する

axis 引数を指定すれば、列方向の削除も可能です。

print(df.dropna(axis=1))

axis=1 とすると、NaN を 1 つでも含む列が丸ごと削除されます。欠損率の高い列を一括で落としたいときに便利ですが、重要な列まで消えてしまわないか確認しましょう。

how 引数で削除条件を変える

デフォルトでは how=“any”、つまり 1 つでも NaN があれば削除されます。how=“all” にすると、すべてのセルが NaN である行(または列)だけが削除対象になります。

df2 = pd.DataFrame({
    "a": [1, np.nan, np.nan],
    "b": [np.nan, np.nan, np.nan],
    "c": [3, 4, np.nan]
})
print(df2.dropna(how="all"))
how="any"

1 つでも NaN があれば削除する。厳密にクリーンなデータが欲しいときに使う

how="all"

すべてが NaN の行・列だけ削除する。部分的な欠損は許容したいときに使う

subset で特定の列だけを判定対象にする

すべての列を見るのではなく、特定の列に欠損があるかどうかで判定したい場合は subset を使います。

print(df.dropna(subset=["age"]))

この例では age 列に NaN がある行だけが削除され、score 列に NaN がある行は残ります。分析に不可欠な列だけを基準にすれば、必要以上にデータを失わずに済みます。

thresh で許容する非欠損数を指定する

thresh 引数を使うと、「非欠損値が n 個以上ある行だけを残す」という条件で削除できます。

print(df.dropna(thresh=2))

thresh=2 とすれば、NaN でない値が 2 個以上ある行が残ります。列数が多いデータで「ほとんど埋まっている行は残したい」という場面で重宝するオプションです。

dropna は手軽で強力ですが、安易に使うとデータ量が大幅に減ってしまうリスクがあります。削除前後で行数を比較し、欠損率が高い場合は fillna による補間も検討するのがよいでしょう。