
【機械学習】欠損値に対する正しい対処法
2021.12.20
目次
欠損値を正しく処理する方法
データには、「欠損値」が含まれている場合が多くあります。
機械学習を行う場合は、欠損値をどのように処理するのかによって精度は大きく変わってきます。
本記事では、欠損値を正しく処理する方法について説明していきます。
欠損値を見つける方法
まずは、欠損値を処理するために、欠損値がどこにいくつあるのかを確認していきましょう。
今回扱うデータフレームを以下に定義します。
1 2 3 4 5 6 7 8 9 10 11 12 13 | import pandas as pd import numpy as np df = pd.DataFrame([['A1', 20, 51], ['B1', 31, 67], ['C1', None, 48], ['D1', 42, 59]], columns=['ID', 'age', 'weight']) print(df) # ID age weight #0 A1 20.0 51 #1 B1 31.0 67 #2 C1 NaN 48 #3 D1 42.0 59 |
欠損値を調べるには、「isnull関数」を利用します。
欠損値であれば「True」、欠損値でなければ「False」が返ってきます。
1 2 3 4 5 6 | print(df.isnull()) # ID age weight #0 False False False #1 False False False #2 False True False #3 False False False |
このように、欠損値がどこにあるかが分かります。
しかし、このままだとデータの数が多い時に確認することが大変ですね。
欠損値がある場所をみやすくする
そこで、「sum関数」を利用して見やすくします。
1 2 3 4 5 6 7 8 9 10 11 | print(df.isnull().sum()) # ID 0 # age 1 # weight 0 # dtype: int64 print(df.isnull().sum(axis=1)) # 0 0 # 1 0 # 2 1 # 3 0 # dtype: int64 |
これで「どこに」「いくつ」欠損値があるのかが分かります。
また、引数に axis=1 をいれると、行に対しての結果を見ることができます。
データを扱う時は、まずこのようにして欠損値の有無を確かめます。
欠損値を削除する
欠損値の数が少ない場合には、欠損値ごとデータを消してしまうという方法があります。
削除するには、「dropna関数」を使用します。
axis=1 を指定することで、欠損値が含まれる列を削除します。
1 2 3 4 5 6 7 8 9 10 11 | print(df.dropna()) # ID age weight # 0 A1 20.0 51 # 1 B1 31.0 67 # 3 D1 42.0 59 print(df.dropna(axis=1)) # ID weight # 0 A1 51 # 1 B1 67 # 2 C1 48 # 3 D1 59 |
欠損値を削除するのは簡単ですが、削除するということは情報を減らしてしまうということになります。
欠損値の削除は、数が少ない時のみにしましょう。
欠損値を代表値で埋める
欠損値を埋める最もシンプルな方法として、代表値で埋めるという方法があります。
平均値で埋める
最も一般的な方法は、平均値で埋める方法です。
欠損値を埋めるには、「fillna関数」を使います。
1 2 3 4 5 6 | print(df.fillna(df.mean())) # ID age weight # A1 20.0 51 # B1 31.0 67 # C1 31.0 48 # D1 42.0 59 |
中央値や最頻値で埋める
平均値で埋める以外にも、中央値や最頻値で埋める方法もあります。
中央値を求める時は「median関数」、最頻値を求める場合は「mode関数」を使います。
この他に、引数に method=’ffill 、もしくは method=’bfill を指定することによって、欠損値を前後の値で埋めることができます。
時系列データの際に有効です。
1 2 3 4 5 6 7 8 9 10 11 12 | print(df.fillna(method='ffill')) # ID age weight # 0 A1 20.0 51 # 1 B1 31.0 67 # 2 C1 31.0 48 # 3 D1 42.0 59 print(df.fillna(method='bfill')) # ID age weight # 0 A1 20.0 51 # 1 B1 31.0 67 # 2 C1 42.0 48 # 3 D1 42.0 59 |
欠損値を利用して特徴量を作成する
欠損値を埋めるのではなく、新しく特徴量として利用する方法もあります。
簡単に特徴量に変える方法として、欠損しているかどうかの2値変数にする方法があります。
1 2 3 4 5 6 7 8 9 10 11 | age_list = [] for i in df["age"].isnull(): if i == True: age_list.append(0) else: age_list.append(1) print(age_list) # [1, 1, 0, 1] |
欠損値を利用して特徴量を作ることによって、情報量を減らすことなく利用できるというメリットがあります。
欠損値のまま利用する
これまでは、欠損値に対して何かしらの処理をしてきましたが、欠損値をそのままにして利用するという方法もあります。
例えば、GBDTライブラリでは欠損値があってもそのまま扱うことができるため、そのまま扱うことも多くあります。
しかし、ニューラルネットワークやランダムフォレストなど、GBDT以外の多くの機械学習手法では、欠損値をそのまま扱うことはできないので、何かしらの処理をする必要があります。
さいごに
本記事では欠損値を正しく処理する方法を紹介しました。
以下のポイントを忘れないようにしましょう。
- 欠損値の有無の確認
- 欠損値が少なければ削除
- データに合わせて欠損値を補完
- 欠損値を利用して新たに特徴量を作る
- GBDTを使うなら欠損値のままでもOK
欠損値を処理する方法はたくさんありますが、重要なのはデータに合わせて正しく処理することです。
こちらの記事もオススメ!
書いた人はこんな人

- 「好きなことを仕事にするエンジニア集団」の(株)ライトコードです!
ライトコードは、福岡、東京、大阪の3拠点で事業展開するIT企業です。
現在は、国内を代表する大手IT企業を取引先にもち、ITシステムの受託事業が中心。
いずれも直取引で、月間PV数1億を超えるWebサービスのシステム開発・運営、インフラの構築・運用に携わっています。
システム開発依頼・お見積もりは大歓迎!
また、WEBエンジニアとモバイルエンジニアも積極採用中です!
ご応募をお待ちしております!
ITエンタメ2022.06.22IntelliJ IDEAとkotlinを送り出したJetBrains創業物語
ITエンタメ2022.06.15【アタリ創業者】スティーブ・ジョブズを雇った男「ノーラン・ブッシュネル」
ITエンタメ2022.06.13プログラミングに飽きてPHPを開発したラスマス・ラードフ
ITエンタメ2022.06.03【Unity開発秘話】ゲーマーを開発者にしてしまうゲームエンジン