AI 実装検定への道(7)
AI 実装検定 A級合格へ向けて学習を進めています。
前回投稿が6回目で、引き続きGoogle Colaboratoryを利用してプログラミングの章を進めて書いています。
ここまでに公式テキストでは、217ページの中ほどまできました。
1次配列(行列)を準備して、合計、最大値(Max)、最小値(Min)を求めましたが、次は多次元の配列になるようなので、小休止しました。
前々回同様にconcatenateを利用して多次元の配列(行列)の連結を勉強しましたが、この際連結の方向を「axis」を利用して、行方向(縦)に連結する場合は「axis=0」、縦方向(横)に連結するためには「axis=1」、そして公式テキストの解説とは異なりますが配列(行列)内で『直接横に』連結させる場合には「axis=2」を利用すること。その度に、「shape」を利用して繰り返し配列(行列)の形状を確かめました。その後、NumPyでの計算として、パソコンでExcelを利用するのと同様に「+」「ー」「*」、ただし割り算をする場合は少数で商を求める「/」、商と余りをそれぞれ導く「//」と「%」を理解して、最後は配列(行列)の中から合計、最大値(Max)、最小値(Min)を求めました。
ここから、多次元の配列について合計、最大値(Max)、最小値(Min)を求めます。
あと残り100ページくらいなので、頑張ろう!
(あと10回くらいは続くかな・・・ぼちぼちと)
まず、前回同様にrandomを利用して、3×4の配列(行列)を生成します。
(コード記述)
import numpy as np
D=np.random.random((3,4))
D
(結果)
array([[0.74629681, 0.45679478, 0.36455411, 0.29958036],
[0.52781072, 0.46413488, 0.46041405, 0.91336505],
[0.82565726, 0.98301983, 0.46559749, 0.20492164]])
いつもの通り、shapeを使って形状を確認しておきます。
(コード記述)
D.shape
(結果)
(3, 4)
では、前回勉強した合計(sum)、最大値(Max)、最小値(Min)を求めていきます。
(コード記述)
D.sum()
(結果)
6.712146985465767
(コード記述)
D.max()
(結果)
0.9830198317010657
(コード記述)
D.min()
(結果)
0.20492163939666308
「axis」の再登場
前回同様に、ランダムで生成した配列(行列)の中には現れていなかった桁まで数値が示されました。さて、次に2次元配列では、全要素の比較だけでなく行や、列の中で比較もできるそうです。ここでも「axis」が登場します。
「axis」は前回には、配列(行列)どうしの計算の方向・・・について利用しましたが、どうなるでしょうか?
列ごと(縦方向)で計算する場合は、「axis=0」
行ごと(横方向)に計算するときは、「axis=1」を使うそうです。
元の配列(行列)を今一度記します。
array([[0.74629681, 0.45679478, 0.36455411, 0.29958036],
[0.52781072, 0.46413488, 0.46041405, 0.91336505],
[0.82565726, 0.98301983, 0.46559749, 0.20492164]])
(コード記述)
D.sum(axis=0)
(結果)
array([2.09976479, 1.9039495 , 1.29056565, 1.41786705])
(コード記述)
D.sum(axis=1)
(結果)
array([1.86722607, 2.3657247 , 2.47919622])
この通り、もとの3×4の配列(行列)から「axis=0」を使って列ごと(縦方向)で計算すると1×4の配列(行列)?が生成され、「axis=1」を使って行ごと(横方向)で計算すると1×3の配列(行列)?が示されました。
同様に、最大値(Max)、最小値(Min)についても「axis=0」を使って列ごと(縦方向)に、「axis=1」を使って行ごと(横方向)に抽出できるとのこと。
元の配列(行列)を今一度記します。
array([[0.74629681, 0.45679478, 0.36455411, 0.29958036],
[0.52781072, 0.46413488, 0.46041405, 0.91336505],
[0.82565726, 0.98301983, 0.46559749, 0.20492164]])
(コード記述)
D.max(axis=0)
(結果)
array([0.82565726, 0.98301983, 0.46559749, 0.91336505])
(コード記述)
D.max(axis=1)
(結果)
array([0.74629681, 0.91336505, 0.98301983])
(コード記述)
D.min(axis=0)
(結果)
array([0.52781072, 0.45679478, 0.36455411, 0.20492164])
(コード記述)
D.min(axis=1)
(結果)
array([0.29958036, 0.46041405, 0.20492164])
この通り、配列の中で合計(sum)、最大値(Max)、最小値(Min)を求める場合でも、「axis=0」を使って列ごと(縦方向)に、「axis=1」を使って行ごと(横方向)に計算出来るということでした。
「axis=0」を使って列ごと(縦方向)に計算、比較抽出。
↓ ↓ ↓
↓ ↓ ↓
↓ ↓ ↓
「axis=1」を使って行ごと(横方向)に計算、比較抽出。
→ → →
→ → →
→ → →
こんな感じで覚えておくことにします。
3×4の配列(行列)にある12の数値の平均値を求める場合は「mean」を使います。
(コード記述)
np.mean(D)
(結果)
0.5593455821221472
検算はしていません・・・
配列(行列)の要素の一部を取り出す「mask」
まず最初に、0〜10までの間で15個の数字を含む配列(行列)を準備。
(コード記述)
E=np.random.randint(10,size=(15))
E
(結果)
array([5, 1, 0, 1, 7, 6, 0, 4, 2, 3, 4, 5, 9, 7, 9])
最初、size(15)と記述し、「=」を忘れていました。
その時のエラーメッセージがこれ。
size・・・のあたりで、何か間違いがあるんだなと気づけました。
ーーーーーーーーーーーーーーーーーーーーーーーーーーーーーー
NameError Traceback (most recent call last)
<ipython-input-16-a3b25d78a413> in <module>
----> 1 E=np.random.randint(10,size(15))
2 E
NameError: name 'size' is not defined
次に、E>0 と記述してみます。
(コード記述)
E>0
(結果)
array([ True, True, False, True, True, True, False, True, True, True, True, True, True, True, True])
最初に生成した配列(行列)の中に「0」が2個あったので、その部分のみ「False」と示されました。このように、配列(行列)の中で条件に合致する?部分を「True」と「False」で返す機能が「mask」なんだそうです。
この中から、4より大きい数を抜き出します。
(コード記述)
E[E>4]
(結果)
array([5, 7, 6, 5, 9, 7, 9])
これが何の役に立つのか???と思いながらでしたが、公式テキストにはこのようなことが書いてあります。平均降水量を求める時、雨が降った日の限定して計算したい場合には晴れた日を除外する必要があります。
すぐ前で、「mean」を使って平均を求めましたが、「mask」と組み合わせることで、対象を絞って計算することができるというわけなんですね。
最初の配列(行列)全体で平均を求めると・・・
(コード記述)
np.mean(E)
(結果)
4.2
4より大きな数値に絞って平均を求めると・・・
(コード記述)
np.mean(E[E>4])
(結果)
6.857142857142857
「pandas」でのデータ作成
ここまで、配列(行列)を扱うのにも、数学の教科書に示されたような大きな括弧に囲まれていない数値を見るのに慣れてきたように思いますが、「pandas」という拡張ライブラリを利用すれば、表形式のデータが扱えるみたいです。
まず、「NumPy」を読み込んだのと同様に、「pandas」を読み込みます。
(コード記述)
import numpy as np
import pandas as pd
もう慣れてきましたが、「NumPy」は「np」と略し、「pandas」は「pd」とするようです。「pandas」で表現する表は、表全体を表す「DataFrame」と表の1列1列を表す「Series」で構成されるとのこと。
まずは、「Series」から開始
(コード記述)
F=pd.Series([5,1,3,1,4])
F
(結果)
0 5 1 1 2 3 3 1 4 4 dtype: int64
5つの数字を指定したので、このように1列5行に各数値が格納されています。左側の数値は0行目〜4行目までを示していそうです。こうして生成したSeriesをvalueプロパティで呼び出すとNumPyの配列(行列)で取り出すことができるそうです。
(コード記述)
F.values
(結果)
array([5, 1, 3, 1, 4])
次は、Seriesで生成した5つの数値から、部分的に要素を取り出す手法です。0番目(実質1番目)の数値は・・・
(コード記述)
F[0]
(結果)
5
ここで注意:F(0)としちゃうとエラーになります!
( )ではなく、[ ]なので注意です。
2番目(実質3番目)の数値
(コード記述)
F[2]
(結果)
3
範囲指定して抽出するには、F[2:5]と書く。
(5の手前の4までという理解をする)
(コード記述)
F[2:5]
(結果)
2 3 3 1 4 4 dtype: int64
「index」を使ってみる。記述は、F.index。
(コード記述)
F.index
(結果)
RangeIndex(start=0, stop=5, step=1)
「index」とは、左に表示された行番号的なもの。
(結果)
0 5
1 1
2 3
3 1
4 4
dtype: int64
RangeIndex(start=0, stop=5, step=1)には、start=0で0から始まっていること、stop=5で5の手前まで(4)で終わっていること。step=1で1つずつ増えていることが示されているようです。
pandasでデータの選択
前述の通り、「index」には数字が使われていましたが、アルファベットを利用することも可能なようです。Excelだと行は数字で、列にはアルファベットが使われていますね。
(コード記述)
G=pd.Series([6,2,4,2,5],index=["a","b","c","d","e"])
G
(結果)
a 6 b 2 c 4 d 2 e 5 dtype: int64
先程は、indexの番号で数字を取り出しましたが、今度はここで利用したアルファベットで指定します。では、3行目の4を取り出してみます。
(コード記述)
G["c"]
(結果)
4
意味があるのかどうか分かりませんが、「index」に好きな数字をしてしてみます。
(コード記述)
H=pd.Series([6,2,4,2,5],index=[8,3,6,1,9])
H
(結果)
8 6 3 2 6 4 1 2 9 5 dtype: int64
これで、上記と同じく4を呼び出そうとすると・・・
(コード記述)
H[6]
(結果)
4
なんだか頭がこんがらがりそうですね・・・次の例は、とても分かりやすいです。国算理社英の5教科の点数を表にしてみます。それぞれ、85点、95点、90点、75点、65点(高校時代のバランスはこんなもんだったかな)としてみます。
(コード記述)
I=pd.Series([85,95,90,75,65],index=["国語","算数","理科","社会","英語"])
I
(結果)
国語 85 算数 95 理科 90 社会 75 英語 65 dtype: int64
(コード記述)
I["理科"]
(結果)
90
おっと!これでもいいと思ったのだが、公式テキストでは「score」を使っています。
(コード記述)
score=pd.Series({"国語":85,"算数":95,"理科":90,"社会":75,"英語":65})
score
(結果)
国語 85 算数 95 理科 90 社会 75 英語 65 dtype: int64
なんだか結果は同じに見えるんだけど・・・
公式テキストに文句がある!
「score」を使うときには、([ ])ではなく、({ })なんですね!
これ、めっちゃ良くみないと判別つきませんでした!
これは酷いな〜。注意書きでもつけて欲しかったな〜
気を取り直して、社会の点数を抜き出してみます。
(コード記述)
score["社会"]
(結果)
75
次に、算数から社会までの3つにデータを抜き出します。
(コード記述)
score["算数":"社会"]
(結果)
算数 95 理科 90 社会 75 dtype: int64
今日はここまで。
公式テキストでは、227ページの途中まで進みました。
(10ページしか進んでいない・・・)
多次元の配列(行列)について合計(sum)、最大(max)、最小(min)を求めたり、それを「axis」を使って列ごと(縦方向)であったり、行ごと(横方向)に抜き出してみたり。「mask」を使って条件に合致した判別と「mean」による平均値算出。最後に「NumPy」のように拡張ライブラリのひとつである「pandas」を使って表形式に文字を並べ、そこからデータを選択するというところまで進めました。
次回は、もう少し、「Series」についてアレンジを勉強していきます。
以上
(なんだかんだ、コードは33個)
今日は、雪が降ってきたので非常に寒いです・・・明朝の名古屋は雪が積もってるのかな?