pandas corr()の使い方|相関係数・相関行列を初心者向けに解説

describe()で平均値や標準偏差を確認したあとに、「売上と広告費には関係があるの?」「どの列とどの列が一緒に動いているの?」と気になることはありませんか?

そんなときに使えるのが、Pandasのcorr()です。corr()を使うと、複数の数値列の関係を相関係数としてまとめた「相関行列」を作れます。

ただし、df.corr()を実行して表を出すだけでは十分ではありません。大切なのは、相関係数の符号と大きさを読み、気になる組み合わせを散布図でも確認することです。

この記事では、Google Colabでそのまま試せる小さなDataFrameを使って、corr()の基本から相関行列の読み方、散布図との使い分けまで順番に解説します。

  1. この記事でわかること
  2. まず結論:corr()は「列と列の関係」をまとめて確認するときに使う
  3. 相関係数とは?-1〜1の値をどう読むか
  4. 相関を確認するサンプルDataFrameを作る
  5. pandas corr()の基本的な使い方
    1. 相関行列は「対角線以外」を見る
    2. 特定の列との相関だけを確認する
    3. ヒートマップで相関行列を視覚的に捉える
  6. 正の相関・負の相関・弱い相関を同じデータで読む
  7. Pearson・Spearman・Kendallはどう使い分ける?
  8. corr()でつまずきやすい3つのポイント
    1. 1. 数字に見えても文字列型になっていることがある
    2. 2. 欠損値があっても「0」として計算されるわけではない
    3. 3. NaNが出たら「計算できる変化があるか」を確認する
  9. corr()だけで判断せず、散布図で形を確認する
  10. データ分析では「確認→相関→可視化」の流れで使う
  11. 注意:相関が高くても因果関係があるとは限らない
  12. まとめ:corr()で関係を見つけ、散布図で確かめよう
  13. 関連記事
    1. カテゴリから探す
    2. pandas corr()とは何ですか?
    3. 相関係数が1、-1、0に近い場合はどういう意味ですか?
    4. corr()で文字列列がある場合はどうすればよいですか?
    5. corr()でNaNが出るのはなぜですか?
    6. PearsonとSpearmanはどう使い分けますか?
    7. DataFrame.corr()とSeries.corr()の違いは何ですか?
    8. corr()と散布図はどちらを使えばよいですか?
    9. 相関係数が高ければ因果関係があると言えますか?
    10. pandasの相関行列はヒートマップにしたほうがよいですか?

この記事でわかること

  • corr()を何のために使うのか
  • 相関係数の「1・0・-1」の意味
  • DataFrameから相関行列を作り、どこを見ればよいか
  • Pearson・Spearman・Kendallの基本的な違い
  • corr()describe()・散布図の使い分け
  • 文字列型や欠損値があるときの注意点
  • 相関係数だけで判断せず、散布図へ進む分析の流れ

この記事のゴールは、corr()で相関行列を作って正しく読み、気になる関係を散布図で確かめられるようになることです。

まず結論:corr()は「列と列の関係」をまとめて確認するときに使う

データを確認するときは、知りたいことによって使う方法を変えると迷いにくくなります。

知りたいこと 主に使う方法 見えるもの
1列の値を要約したい describe() 平均・標準偏差・四分位数など
複数の数値列の関係を一覧で見たい corr() 相関係数・相関行列
2列の関係を目で確かめたい 散布図(scatter 点の散らばり・外れ値・曲線的な関係

つまり、corr()1列ずつを見るdescribe()と、2列を図で見る散布図の間をつなぐ役割があります。

基本統計量の確認方法を先に知りたい方は、pandas describe()の使い方も参考にしてください。DataFrameそのものがまだ不慣れな場合は、Pandas DataFrame入門から確認すると流れをつかみやすくなります。

相関係数とは?-1〜1の値をどう読むか

相関係数は、2つの数値がどの程度一緒に動くかを**-1から1の範囲**で表した値です。

相関係数の状態 読み方 イメージ
1に近い 正の相関が強い 一方が大きいほど、もう一方も大きい傾向
0付近 直線的な相関が弱い 一方が変わっても、もう一方の増減がはっきりしない
-1に近い 負の相関が強い 一方が大きいほど、もう一方は小さい傾向
1または-1 完全な正・負の相関 点が完全に一直線に並ぶ関係

ここで重要なのは、符号は関係の向き、絶対値は直線的な関係の強さを見る手がかりだということです。たとえば-0.9は「マイナスだから弱い」のではなく、強い負の相関を示します。

また、「0.7以上なら必ず強い」のように数値だけで機械的に判断するのはおすすめできません。何を強いとみなすかは、データの種類や分析目的によって変わります。まずは相関係数で候補を見つけ、元データや散布図も確認するのが基本です。

相関を確認するサンプルDataFrameを作る

ここからは、ある店舗の12期間分のデータを例にします。広告費売上気温返品件数という4つの数値列を用意します。

今回は相関の違いを確認しやすいように、関係がはっきり表れる練習用データを使用します。

この例で知りたいのは、どの列同士が一緒に増減しているのかです。まずは元データを確認しましょう。

import pandas as pd

df = pd.DataFrame({
    "広告費": [10, 15, 20, 25, 30, 35, 40, 45, 50, 55, 60, 65],
    "売上": [82, 95, 103, 119, 128, 142, 151, 165, 172, 188, 197, 211],
    "気温": [18, 25, 12, 28, 16, 22, 30, 14, 26, 19, 24, 20],
    "返品件数": [42, 39, 37, 35, 32, 31, 28, 26, 24, 21, 19, 17]
})

df
広告費 売上 気温 返品件数
0 10 82 18 42
1 15 95 25 39
2 20 103 12 37
3 25 119 28 35
4 30 128 16 32
5 35 142 22 31
6 40 151 30 28
7 45 165 14 26
8 50 172 26 24
9 55 188 19 21
10 60 197 24 19
11 65 211 20 17

元のDataFrameは、1行が1期間の観測データです。この12行から、列同士の関係をまとめた表へ変換するのが次のcorr()です。

pandas corr()の基本的な使い方

DataFrameの相関係数をまとめて求める基本形は、次の1行です。

corr_matrix = df.corr()
corr_matrix.round(3)
広告費 売上 気温 返品件数
広告費 1.000 0.999 0.121 -0.999
売上 0.999 1.000 0.122 -0.998
気温 0.121 0.122 1.000 -0.114
返品件数 -0.999 -0.998 -0.114 1.000

実行すると、元の12行×4列のデータから、次のような4列×4列の相関行列が得られます。小数第3位に丸めると、おおよそ次の値です。

広告費 売上 気温 返品件数
広告費 1.000 0.999 0.121 -0.999
売上 0.999 1.000 0.122 -0.998
気温 0.121 0.122 1.000 -0.114
返品件数 -0.999 -0.998 -0.114 1.000

これが「処理前→処理後」の大きな変化です。corr()は各行を個別に表示するのではなく、列と列の組み合わせごとに1つの相関係数を計算します。

相関行列は「対角線以外」を見る

相関行列を初めて見ると、1.000がたくさん並んでいて戸惑うかもしれません。見るポイントは2つです。

  1. 対角線はすべて1になる
    • 広告費広告費のように、同じ列を自分自身と比較しているためです。
  2. 上下には同じ組み合わせが重複する
    • 広告費×売上売上×広告費は同じ関係なので、同じ値になります。

そのため、初心者のうちは対角線ではなく、異なる列同士の値を見ると考えれば十分です。

特定の列との相関だけを確認する

相関行列全体ではなく、たとえば「売上とほかの列の関係だけを見たい」という場合は、列名を指定します。

# 「売上」とほかの列との相関だけを確認
corr_matrix["売上"].drop("売上")
売上
広告費 0.999175
気温 0.122452
返品件数 -0.998055

corr_matrix["売上"]で売上の列だけを取り出し、drop("売上")で売上自身との相関係数1.0を除いています。特定の指標と関係が強い列を探したいときに便利です。

ヒートマップで相関行列を視覚的に捉える

列数が多いDataFrameでは、相関行列をヒートマップにすると、相関の強さと向きを色で見分けやすくなります。ここでは、先ほど作ったcorr_matrixをそのまま可視化します。

seabornライブラリのheatmap関数を使うと、簡単にヒートマップを作成できます。

!pip install japanize_matplotlib
import seaborn as sns
import matplotlib.pyplot as plt
import japanize_matplotlib # 日本語フォントを有効にする

plt.figure(figsize=(8, 6))
sns.heatmap(corr_matrix, annot=True, cmap='coolwarm', fmt='.3f', linewidths=.5)
plt.title('相関行列のヒートマップ')
plt.show()
広告費・売上・気温・返品件数の相関行列を示すヒートマップ
相関行列のヒートマップ

このcoolwarm配色では、赤系が正の相関、青系が負の相関、白に近い色が0付近を示します。まず色で気になる組み合わせを見つけ、annot=Trueで表示した数値を確認しましょう。

正の相関・負の相関・弱い相関を同じデータで読む

先ほどの相関行列から、特徴の異なる3つの組み合わせを見てみましょう。

print("広告費と売上      :", round(corr_matrix.loc["広告費", "売上"], 3))
print("広告費と返品件数  :", round(corr_matrix.loc["広告費", "返品件数"], 3))
print("売上と気温        :", round(corr_matrix.loc["売上", "気温"], 3))
広告費と売上      : 0.999
広告費と返品件数  : -0.999
売上と気温        : 0.122

このサンプルでは、次のように読めます。

  • 広告費と売上:0.999 → 強い正の相関がある
  • 広告費と返品件数:-0.999 → 強い負の相関がある
  • 売上と気温:0.122 → 少なくとも強い直線的な相関は見られない

ここで、0.122だから「売上と気温には絶対に何の関係もない」とは断定できません。corr()が捉える関係、とくに標準のPearson相関は直線的な関係が中心です。曲線的な関係や外れ値の影響は、相関係数だけでは見落とすことがあります。

このため、corr()結論を自動的に出す道具ではなく、詳しく見る組み合わせを探す道具として使うと理解しやすいです。

Pearson・Spearman・Kendallはどう使い分ける?

DataFrame.corr()は、標準ではPearson(ピアソン)の相関係数を計算します。初心者が連続した数値データの直線的な関係を見るなら、まずPearsonから始めればよいでしょう。

method ざっくりした考え方 初心者が使う場面
pearson 数値の直線的な関係を見る まず基本として使う
spearman 値の順位にもとづいて単調な関係を見る 順位関係を重視したいとき
kendall 順位の一致・不一致にもとづいて見る 順位データなどで候補になる

指定するときはmethod引数を使います。違いが見えやすいよう、ここだけ小さな比較用データを使います。xが増えるにつれてyも必ず増えますが、最後の値だけ大きく離れています。

method_df = pd.DataFrame({
    "x": [1, 2, 3, 4, 5, 6, 7, 8],
    "y": [1, 2, 3, 4, 5, 6, 7, 100]
})

print("Pearson :", round(method_df.corr(method="pearson").loc["x", "y"], 3))
print("Spearman:", round(method_df.corr(method="spearman").loc["x", "y"], 3))
print("Kendall :", round(method_df.corr(method="kendall").loc["x", "y"], 3))
Pearson : 0.624
Spearman: 1.0
Kendall : 1.0

この例では順位そのものは完全に同じ方向へ動いているため、SpearmanやKendallでは強い関係として表れます。一方、Pearsonは数値の直線的な関係を見るため、最後の大きな値の影響を受けます。

ここでは**「methodによって見ている関係が違う」**と分かれば十分です。Spearman・Kendallの統計理論や数式には深入りしません。通常の数値データで迷ったら、まずPearsonで確認し、分析目的に応じて別の方法を検討しましょう。

corr()でつまずきやすい3つのポイント

corr()は短いコードで使えますが、実際のCSVやExcelから読み込んだデータでは、データ型や欠損値に注意が必要です。

1. 数字に見えても文字列型になっていることがある

たとえばCSVから読み込んだ広告費が文字列になっていると、そのまま数値列として分析できないことがあります。まずdtypesで型を確認する習慣をつけましょう。

df_text = df.copy()
df_text["広告費"] = df_text["広告費"].astype(str)

df_text.dtypes
0
広告費 object
売上 int64
気温 int64
返品件数 int64

型が混在するDataFrameでは、初心者には数値列を明示してからcorr()を使う方法が分かりやすく、安全です。

numeric_df = df_text.select_dtypes(include="number")
numeric_df.corr().round(3)
売上 気温 返品件数
売上 1.000 0.122 -0.998
気温 0.122 1.000 -0.114
返品件数 -0.998 -0.114 1.000

DataFrame.corr()にはnumeric_onlyという引数もあります。数値列だけを対象にする書き方としてdf.corr(numeric_only=True)もありますが、なぜ列が対象外になったのかを理解するためにも、先にdtypesで型を確認するのがおすすめです。

数値列だけを選ぶ方法はpandas select_dtypes()の使い方、文字列になった数字を数値型へ直す方法はpandas to_numeric()の使い方で詳しく解説しています。

2. 欠損値があっても「0」として計算されるわけではない

実データには欠損値が含まれることがあります。corr()では、対象となる2列について利用できる観測値を使って相関を計算します。欠損値を勝手に0へ置き換えて計算するわけではありません。

たとえば一部の売上を欠損値にして確認します。

df_missing = df.copy()
df_missing.loc[[2, 7], "売上"] = pd.NA

print(df_missing[["広告費", "売上"]].isna().sum())
df_missing[["広告費", "売上"]].corr().round(3)
広告費    0
売上     2
dtype: int64
広告費 売上
広告費 1.000 0.999
売上 0.999 1.000

相関係数の計算に必要な最小データ数を決めたい場合は、min_periodsを指定できます。次の例では、広告費と売上の有効な組み合わせが10件しかないのに11件以上を必要とするため、この2列間の相関係数はNaNになります。

# 計算に必要な有効データ数を11件以上に指定
df_missing[["広告費", "売上"]].corr(min_periods=11)
広告費 売上
広告費 1.0 NaN
売上 NaN NaN

min_periodsは、少ないデータだけで相関係数が計算されるのを避けたい場合に便利です。PandasではPearson相関とSpearman相関で利用できます。

欠損が多いほど、組み合わせによって計算に使えるデータ数が変わる可能性があります。相関係数を見る前に「何件のデータが残っているのか」を意識しましょう。欠損値の場所や件数の確認は、Pandas isnull()で欠損値を確認する記事につなげて学べます。

なお、isnull()記事で扱っているmissingnoの「欠損パターン同士の相関」と、ここで扱う売上・広告費など通常の数値変数同士の相関は目的が異なります。

3. NaNが出たら「計算できる変化があるか」を確認する

相関係数がNaNになる代表例の1つが、すべて同じ値の列です。値が変化しない列では、通常の相関係数を計算できません。

df_constant = df[["広告費", "売上"]].copy()
df_constant["固定値"] = 1

df_constant.corr().round(3)
広告費 売上 固定値
広告費 1.000 0.999 NaN
売上 0.999 1.000 NaN
固定値 NaN NaN NaN

corr()NaNを見つけたら、エラーだと決めつけず、列の値がすべて同じではないか、欠損値が多すぎないか、計算に使えるデータが十分あるかを確認してください。

corr()だけで判断せず、散布図で形を確認する

相関係数は複数列を一覧で比較するのに便利ですが、点がどのように散らばっているかまでは分かりません。

たとえば広告費売上は相関係数が約0.999でした。この関係を散布図でも確認してみましょう。

import matplotlib.pyplot as plt

plt.scatter(df["広告費"], df["売上"])
plt.xlabel("Ad cost")
plt.ylabel("Sales")
plt.title("Ad cost vs Sales")
plt.grid(alpha=0.3)
plt.show()
広告費と売上の関係を示す散布図
広告費と売上の散布図

点が右上がりに並んでいれば、「広告費が大きい期間ほど売上も大きい」という傾向を目でも確認できます。

散布図には、相関係数だけでは気づきにくい次の情報があります。

  • 外れた点がないか
  • 点が直線ではなく曲線のように並んでいないか
  • 一部の点だけが相関係数を大きく動かしていないか

したがって、corr()で候補を探す → 散布図で実際の形を見るという順番が実践的です。散布図の色・サイズ・凡例などは、Matplotlib scatter入門で詳しく解説しています。この記事ではcorr()の結果を確かめるための最小限の描画にとどめます。

データ分析では「確認→相関→可視化」の流れで使う

実際の分析では、いきなりcorr()だけを実行するより、次の順番で進めると迷いにくくなります。

  1. head()dtypesでDataFrameの中身と型を確認する
  2. describe()で各数値列の分布をざっくり確認する
  3. 必要なら文字列の数字や欠損値を整える
  4. corr()で列同士の相関を一覧する
  5. 気になる組み合わせを散布図で確認する

つまり、corr()は前処理そのものではなく、整えたDataFrameを探索し、次に詳しく見るべき関係を見つける段階に位置づきます。

この流れを意識すると、df.corr()で表を出して終わるのではなく、分析の次の一手を決められるようになります。

注意:相関が高くても因果関係があるとは限らない

相関係数を読むときに、最も大切な注意点の1つです。

たとえば、このサンプルでは広告費売上に強い正の相関があります。しかし、この結果だけから**「広告費を増やしたことが売上増加の原因である」**とは断定できません。季節、キャンペーン、来店客数など、別の要因が両方に影響している可能性もあります。

corr()が示すのは、あくまでデータ上の関係です。相関関係と因果関係は別物として扱いましょう。

まとめ:corr()で関係を見つけ、散布図で確かめよう

この記事では、Pandasのcorr()を使って相関係数・相関行列を確認する方法を解説しました。

  • corr()列と列の関係を数値でまとめて確認するメソッド
  • 相関係数は-1〜1で、符号は向き、絶対値は直線的な関係の強さを見る手がかり
  • 相関行列では、同じ列同士の対角線より異なる列同士を見る
  • 標準のPearsonを基本にし、必要に応じてSpearman・Kendallを検討する
  • 文字列型や欠損値がある場合は、計算前にデータを確認する
  • 相関係数だけでは点の散らばりや外れ値が見えないため、散布図も組み合わせる
  • 強い相関があっても、因果関係があるとは限らない

初心者のうちは、describe()で各列を確認 → corr()で列同士の関係を探す → scatterで形を確認という流れを覚えておくと、データ分析を一段進めやすくなります。

関連記事

▲ ページトップへ戻る

pandas corr()とは何ですか?

corr()は、DataFrameやSeriesの数値データについて相関係数を計算するためのメソッドです。DataFrameに使うと、複数の列同士の相関係数をまとめた相関行列を作れます。

相関係数が1、-1、0に近い場合はどういう意味ですか?

1に近いほど強い正の相関、-1に近いほど強い負の相関を示します。0付近なら、少なくとも強い直線的な相関は見られません。ただし、0に近いからといって「あらゆる関係がない」とは断定できません。

corr()で文字列列がある場合はどうすればよいですか?

まずdtypesで型を確認してください。数値に見える文字列は必要に応じてto_numeric()で数値型へ変換します。分析対象を数値列に限定したい場合は、select_dtypes(include="number")で選択してからcorr()を使う方法が分かりやすいです。numeric_only=Trueを指定する方法もあります。

corr()でNaNが出るのはなぜですか?

すべて同じ値の列など、相関係数を計算できない場合はNaNになることがあります。欠損値が多く、2列の組み合わせで利用できるデータが十分にないケースにも注意してください。

PearsonとSpearmanはどう使い分けますか?

通常の数値について直線的な関係を見るなら、まず標準のPearsonが基本です。値そのものより順位関係・単調な関係を重視したい場合にはSpearmanが候補になります。Kendallも順位にもとづく方法ですが、この記事では統計理論の詳細には深入りしません。

DataFrame.corr()とSeries.corr()の違いは何ですか?

DataFrame.corr()は複数列の組み合わせをまとめて相関行列にします。2つのSeriesだけの相関係数が欲しい場合は、たとえばdf["広告費"].corr(df["売上"])のようにSeries.corr()を使えます。複数列を探索するならDataFrame、特定の2列だけならSeriesと考えると分かりやすいです。

corr()と散布図はどちらを使えばよいですか?

どちらか一方ではなく、組み合わせるのがおすすめです。まずcorr()で複数列から気になる組み合わせを見つけ、次に散布図で点の散らばり・外れ値・曲線的な関係を確認します。

相関係数が高ければ因果関係があると言えますか?

言えません。強い相関があっても、別の要因が両方に影響している可能性があります。corr()の結果だけから原因と結果を決めないようにしましょう。

pandasの相関行列はヒートマップにしたほうがよいですか?

列数が少なければ、まずcorr()の表を読めれば十分です。列数が多い場合はヒートマップで色分けすると全体を見やすくできますが、高度な装飾はこの記事の範囲外です。なお、通常の数値列の相関ヒートマップと、missingnoで見る欠損パターンの相関ヒートマップは目的が異なります。

コメント

タイトルとURLをコピーしました