こんにちは。産婦人科でAIエンジニアのとみー(@obgyntommy)です。
今回はmatplotlibの練習問題になります。matplotlibについては以下の記事で復習しましょう。
【Python】matplotlibの使い方【基本から応用まで】
続きを見る
また、matplotlibの公式ドキュメントはこちらを参照してください。
matplotlib練習問題|使用するデータ
UCIが提供している乳癌の診断データを使用します。
データの大元はUCIのBreast Cancer Data Set です。
今回は、導入のしやすから、「scikit-learn」にあるデータを使います。
ライブラリインストールされていない方は、インストールしてください。
In[]
1 2 3 4 5 | # ターミナル、端末、コマンドプロンプトからは pip install scikit-learn # Jupyter note bookからの場合 !pip install scikit-learn |
matplotlib練習問題|データの準備
まずはデータの準備をします。
下記の4つのデータを使ってグラフを描画してデータの特徴を捉える練習をしましょう。
diagnosis
: 乳房組織の診断 0=悪性、1=良性radius_mean
: 中心から境界までの平均距離perimeter_mean
: 腫瘍のコアの平均サイズmean area
:平均面積
ライブラリとデータ読み込み
下記を実行してください。
In[]
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | import matplotlib.pyplot as plt import numpy as np from sklearn.datasets import load_breast_cancer data = load_breast_cancer() # 使うデータ 型:numpy diagnosis = data.target radius_m = data.data[:,0] perimeter_m = data.data[:,2] area_m = data.data[:,3] # データ数確認 print('diagnosis', len(diagnosis)) print('radius_m', len(radius_m)) print('perimeter_m', len(perimeter_m)) print('area_m', len(area_m)) |
Out[]
1 2 3 4 | diagnosis 569 radius_m 569 perimeter_m 569 area_m 569 |
この結果が示しているのは、以下です。
データは 569
つずつあります。
更に、全データの数と種類も確認します。
In[]
1 2 | print(data.data.shape) print(data.feature_names) |
Out[]
1 2 3 4 5 6 7 8 9 10 | (569, 30) ['mean radius' 'mean texture' 'mean perimeter' 'mean area' 'mean smoothness' 'mean compactness' 'mean concavity' 'mean concave points' 'mean symmetry' 'mean fractal dimension' 'radius error' 'texture error' 'perimeter error' 'area error' 'smoothness error' 'compactness error' 'concavity error' 'concave points error' 'symmetry error' 'fractal dimension error' 'worst radius' 'worst texture' 'worst perimeter' 'worst area' 'worst smoothness' 'worst compactness' 'worst concavity' 'worst concave points' 'worst symmetry' 'worst fractal dimension'] |
この結果からは30項目のデータがある事が分かります。
この課題を完了した後も、データを自習で使ってみてください。
matplotlib練習問題|課題で作成するグラフの種類
diagnosisの棒グラフ
diagnosisの
0:悪性
1:良性の数の棒グラフ
を作成してみましょう。
散布図と近似直線
以下、二つの散布図と近似直線を書いてみましょう。
グラフを見る際のTips
radius_m vs perimeter_m
radius_m vs area_m
これを見ることでそれぞれの特徴量の関係性(相関の有無)がわかります。
ヒストグラム3つを並べて表示
対象データは下記3つです。
表示方法はいろいろあるので、見やすい方法試してみてください。
グラフを見る際のTips
- radius_m
- perimeter_m
- area_m
これを見ることでデータの分布(正規分布かどうか)がわかります
ボックスプロットを3つ並べて表示する
- $x$ 軸には診断結果であるdiagnosis(0:悪性、1:良性)
- $y$ 軸には下記それぞれの項目の数値
グラフを見る際のTips
radius_m
perimeter_m
area_m
を見ることで診断結果と特徴量の関係性がわかります。
例えば、悪性の癌細胞は大きい!とかです。
matplotlib練習問題|補足
この課題では numpy
の知識が必要になります。そこで、numpy
でつまづいた方は以下の記事を参考にして下さい。
NumPyの入門【基礎から解説】
続きを見る
また、この課題のボックスプロットで np.where
を頻用していますので、補足します。
np.where
は where
(どこ) を意味しています。要するに、np.where
を使用する事で条件に一致する要素Noを取得することができます。
データ多いと確認しにくいので、適当に用意した、悪性、良性の g_ng
と面積の area
データで確認していきましょう。
1 2 3 4 5 | # 少ないデータで考える # 0:悪性 1:良性 g_ng = np.array([0, 1, 0, 1, 0, 1, 0, 1]) # 面積データ area = np.array([10, 3, 9, 2, 8, 2, 9, 1]) |
まず、np.where
で0:悪性 1:良性の要素No
を取得します。
1 2 3 4 | # 0:悪性の場所を取得 print('0の要素No', np.where(g_ng==0)) # 1:良性の場所を取得 print('1の要素No', np.where(g_ng==1)) |
すると、以下の結果が得られました。
1 2 | 0の要素No (array([0, 2, 4, 6], dtype=int64),) 1の要素No (array([1, 3, 5, 7], dtype=int64),) |
この要素Noのデータを取得したい場合は、area[要素No]
でデータが取得できます。
そのまま渡してあげることで、0の場合の area データ
、1の場合の area データ
が取得できます。
In[]
1 2 3 4 | # g_ngが0の要素No array([0, 2, 4, 6])をareaデータを取得 print(area[np.where(g_ng==0)]) # g_ngが1の要素No array([1, 3, 5, 7])をareaデータを取得 print(area[np.where(g_ng==1)]) |
Out[]
1 2 | [10 9 8 9] [3 2 2 1] |
この結果をリストに入れて、boxplot
で表示してみましょう。
1 2 3 | g_ng_area = [area[np.where(g_ng==0)], area[np.where(g_ng==1)]] plt.boxplot(g_ng_area) |
すると以下の図表を得る事ができます。
np.where
を使用する事で条件に一致する要素Noを取得することができましたね。
matplotlib練習問題|演習
再度、下記記事を参照して、それぞれのグラフを描画してみましょう。
参照記事は個別にコメントしてあります。
【Python】matplotlibの使い方【基本から応用まで】
続きを見る
演習のJupyter notebookをご利用される方は演習(google driveリンク)を参照いただければと思います。
diagnosisの棒グラフ
In[]
1 2 3 4 5 6 7 8 9 10 11 | # 0=M:悪性 1=B:良性 x = ['M', 'B'] # 0:悪性の数と1:良性の数 # count_nonzeroは条件式に一致(nonzero)の数(count)を取得できます。 y = [np.count_nonzero(diagnosis == 0), np.count_nonzero(diagnosis == 1)] """ 「x」, 「y」を使って棒グラフを表示してください 参考(棒線グラフ):https://obgynai.com/matplotlib/#_pltbar_pltbarh """ |
散布図と近似直線
In[]
1 2 3 4 | """ 「radius_m」と「perimeter_m」を使って、散布図と近似直線を書いてください。 参考(近似直線の描いてみる):https://obgynai.com/matplotlib/#i-9 """ |
In[]
1 2 3 4 | """ 「radius_m」と「area_m」を使って、散布図と近似直線を書いてください。 参考(近似直線の描いてみる):https://obgynai.com/matplotlib/#i-9 """ |
ヒストグラム3つを並べて表示
In[]
1 2 3 4 5 6 7 | """ 「radius_m」、「perimeter_m」、「area_m」それぞれのヒストグラムを描画してください。 ヒストグラムは横に3つ並べて表示してください。 参考(ヒストグラム):https://obgynai.com/matplotlib/#i-4 参考(2つのグラフを横に並べて表示する):https://obgynai.com/matplotlib/#2 """ |
ボックスプロットを3つ並べて表示
In[]
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | # 0:悪性と1:良性のデータに分けます。 # np.whereで0/1の場所を取得して、その場所のデータをそれぞれ分けてリストに入れています。 radius_m_box = [radius_m[(np.where(diagnosis==0))], radius_m[(np.where(diagnosis==1))]] perimeter_m_box = [perimeter_m[(np.where(diagnosis==0))], perimeter_m[(np.where(diagnosis==1))]] area_m_box = [area_m[(np.where(diagnosis==0))], area_m[(np.where(diagnosis==1))]] """ 上記で0:悪性と1:良性のデータに分けた 「radius_m_box」、「perimeter_m_box」、「area_m_box」それぞれのボックスプロット(箱ひげ)を描画してください。 ボックスプロットは横に3つ並べて表示してください。 参考(ボックスプロット):https://obgynai.com/matplotlib/#i-5 参考(2つのグラフを横に並べて表示する):https://obgynai.com/matplotlib/#2 """ |
matplotlib練習問題|解答
解答例(google driveリンク)を参照いただければと思います。
diagnosisの棒グラフ
In[]
1 2 3 4 5 6 7 8 9 10 11 12 | # 0=M:悪性 1=B:良性 x = ['M', 'B'] # 0:悪性の数と1:良性の数 # count_nonzeroは条件式に一致(nonzero)の数(count)を取得できます。 y = [np.count_nonzero(diagnosis == 0), np.count_nonzero(diagnosis == 1)] """ 「x」, 「y」を使って棒グラフを表示してください 参考(棒線グラフ):https://obgynai.com/matplotlib/#_pltbar_pltbarh """ plt.bar(x, y) |
散布図と近似直線
In[]
1 2 3 4 5 6 7 8 9 10 11 12 13 14 | """ 「radius_m」と「perimeter_m」を使って、散布図と近似直線を書いてください。 参考(近似直線の描いてみる):https://obgynai.com/matplotlib/#i-9 """ # 近似直線の式の a と b が入ったタプルを得る p = np.polyfit(radius_m, perimeter_m, 1) # 一次関数の式のオブジェクトを生成する f = np.poly1d(p) # 散布図と近似直線を描く plt.scatter(radius_m, perimeter_m, color = "b", label="score") plt.plot(radius_m, f(radius_m), color = "r", label="Ism") plt.legend(loc='lower right') |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 | """ 「radius_m」と「area_m」を使って、散布図と近似直線を書いてください。 参考(近似直線の描いてみる):https://obgynai.com/matplotlib/#i-9 """ # 近似直線の式の a と b が入ったタプルを得る p = np.polyfit(radius_m, area_m, 1) # 一次関数の式のオブジェクトを生成する f = np.poly1d(p) # 散布図と近似直線を描く plt.scatter(radius_m, area_m, color = "b", label="score") plt.plot(radius_m, f(radius_m), color = "r", label="Ism") plt.legend(loc='lower right') |
ヒストグラム3つを並べて表示する。
In[]
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 | """ 「radius_m」、「perimeter_m」、「area_m」それぞれのヒストグラムを描画してください。 ヒストグラムは横に3つ並べて表示してください。 参考(ヒストグラム):https://obgynai.com/matplotlib/#i-4 参考(2つのグラフを横に並べて表示する):https://obgynai.com/matplotlib/#2 """ fig = plt.figure(figsize=(10,5)) sp1 = fig.add_subplot(1, 3, 1) sp1.hist(radius_m) sp1.set_title('radius_m') sp2 = fig.add_subplot(1, 3, 2) sp2.hist(perimeter_m) sp2.set_title('perimeter_m') sp3 = fig.add_subplot(1, 3, 3) sp3.hist(area_m) sp3.set_title('area_m') plt.show() |
ボックスプロットを3つ並べて表示させる。
In[]
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 | # 0:悪性と1:良性のデータに分けます。 # np.whereで0/1の場所を取得して、その場所のデータをそれぞれ分けてリストに入れています。 radius_m_box = [radius_m[(np.where(diagnosis==0))], radius_m[(np.where(diagnosis==1))]] perimeter_m_box = [perimeter_m[(np.where(diagnosis==0))], perimeter_m[(np.where(diagnosis==1))]] area_m_box = [area_m[(np.where(diagnosis==0))], area_m[(np.where(diagnosis==1))]] """ 上記で0:悪性と1:良性のデータに分けた 「radius_m_box」、「perimeter_m_box」、「area_m_box」それぞれのボックスプロット(箱ひげ)を描画してください。 ボックスプロットは横に3つ並べて表示してください。 参考(ボックスプロット):https://obgynai.com/matplotlib/#i-5 参考(2つのグラフを横に並べて表示する):https://obgynai.com/matplotlib/#2 """ fig = plt.figure(figsize=(10,5)) sp1 = fig.add_subplot(1, 3, 1) sp1.boxplot(radius_m_box) sp1.set_title('radius_m') sp2 = fig.add_subplot(1, 3, 2) sp2.boxplot(perimeter_m_box) sp2.set_title('perimeter_m') sp3 = fig.add_subplot(1, 3, 3) sp3.boxplot(area_m_box) sp3.set_title('area_m') plt.show() |
今回の課題は以上となります。お疲れ様でした。