numpyを含む、数学や計算

1. Google Colabでグラフ

numpyなどで数学の処理をする前に、Google Colabでグラフを書いてみる。

(1)グラフを書く仕組み →matplotlib

Jupyter Notebook(IPython)やGoogle Colabでは、マジックコマンドと呼ばれる拡張機能がある。
%をつけて関数を実行する。
・マジックコマンド

記号 解説
% 1行
%% 複数行にまたがる。(※具体例があった方がわかりやすいとは思っている)

以下のマジックコマンドにより、matplotlibの結果をGoogle Colab上に表示することができる。グラフ表示ができたり、円が描けたりするので、とても便利である。

%matplotlib inline

同時に、matplotlibライブラリ(グラフを表示するためのライブラリ)をimportする

import matplotlib.pyplot as plt
(2)グラフを描いてみよう

・グラフはいろいろな書き方があるので、少し複雑である。
・折れ線グラフはplt.plot()、棒グラフはplt.bar() 、散布図はplt.scatter()

設定内容 方法
タイトル plt.title plt.title("Sales data")
縦軸の項目 plt.xlabel plt.xlabel("Year")
横軸の項目 plt.ylabel plt.ylabel("Sales")
範囲指定 xlim plt.xlim(-500,500)
plt.ylim(-500,500)
罫線 plt.grid()

・色や太さは、以下で指定できる。
, color='red', linewidth=5
❶折れ線グラフ1
必要最小限なものでグラフを描く(Google colab)と、以下。

import matplotlib.pyplot as plt
sales = [100, 110, 120, 112]
year = ['H29', 'H30', 'H31', 'R1']
plt.plot(year,sales)    

❷折れ線グラフ2
別の書き方で書く。結果は同じ

import matplotlib.pyplot as plt
sales = [100, 110, 120, 112]
year = ['H29', 'H30', 'H31', 'R1']
fig, ax = plt.subplots() 
ax.plot(year,sales)

❸折れ線グラフ3
別の書き方で書く。結果は同じ

import matplotlib.pyplot as plt
sales = [100, 110, 120, 112]
year = ['H29', 'H30', 'H31', 'R1']
fig = plt.figure()
ax = fig.add_subplot(111) #もしくは(1,1,1)
ax.plot(year,sales)

❹もう少しグラフらしく
plt.title()、plt.xlabel()、plt.ylabel()は、無くてもグラフは表示される。

% matplotlib inline  
#↑これで、このcolab上にグラフを表示できる。
import matplotlib.pyplot as plt   #matplotlibはグラフを表示するためのライブラリ

#データをセット
sales = [100, 110, 120, 112]
year = ['H29', 'H30', 'H31', 'R1']

plt.plot(year,sales)     #グラフの作成 (横軸の項目,縦軸の項目)
plt.title("Sales data")    # グラフのタイトル
plt.xlabel("Year")          # 縦軸の項目
plt.ylabel("Sales")         # 横軸のラベル
plt.show()                    # グラフの表示

表示結果はこんな感じ
f:id:seeeko:20201101175536p:plain

(2)グラフについて、もう少し

先の1つめの書き方で、味を付けていこう。
❶複数の折れ線グラフ
データを足すだけなので、簡単。上のコードに以下を足してみよう。2つの折れ線グラフが色を変えて表示される。

sales2 = [110, 90, 180, 152]
plt.plot(year,sales2)  

f:id:seeeko:20210102154637p:plain

❷複数の折れ線グラフを2つのグラフに描く

import matplotlib.pyplot as plt   #matplotlibはグラフを表示するためのライブラリ

year = ['H29', 'H30', 'H31', 'R1']
sales = [100, 110, 120, 112]
sales2 = [110, 90, 180, 152]

fig = plt.figure()
ax1 = fig.add_subplot(121, title='Title',xlabel='Year', ylabel='Sales') #1×2の大きさの枠の1つ目に配置 書き方は、(1, 2, 1)でもできるはずだが、Titleを指定する場合などは工夫がいると思う。
ax1.plot(year,sales,label="uriage") 
ax2 = fig.add_subplot(122, title='Title',xlabel='Year', ylabel='Sales') #1×2の大きさの枠の2つ目に配置
ax2.plot(year,sales2,label="uriage") 

ax1.legend() #凡例
ax2.legend()

f:id:seeeko:20210102161647p:plain

❸棒グラフ
plt.plot() の部分を、plt.bar() に変更するだけ。

❹散布図
plt.scatter()関数を使う。plt.scatter(x,y)として、x軸とy軸の値を配列でセットする。

%matplotlib inline
import matplotlib.pyplot as plt
x = [5, 10, 15, 20]
y = [4, 11, 12, 15]
plt.scatter(x,y)

❺ヒストグラム
乱数を使ってデータを作成し、ヒストグラムを作る。
binは階級数であり、今回は10なので、10個の階級を作る。

import matplotlib.pyplot as plt
data = np.random.normal(0, 1, 100) 
fig, ax = plt.subplots() 
ax.hist(data, bins=10) 
(3)irisデータ

2項目だけを絞って、プロットしてみよう。

import sys
if 'google.colab' in sys.modules:
    !wget -P . https://raw.githubusercontent.com/UTokyo-IPP/utpython/master/7/iris.csv   #基となるCSVファイルを取り込み

import pandas as pd
iris = pd.read_csv('iris.csv')                                         #pandasのデータセットに入れる
zu=iris.loc[:, ['petal_length','petal_width','species']]   #項目が多いので、2つとラベルに限定する。

import seaborn as sns
%matplotlib inline                       #図をColabの中に描く
sns.pairplot(zu, hue="species")    #図を書く。hueとして、species(つまり花の種類、ラベル)によって色分け?をしてくれる。

こんな感じ。なぜ4次元のグラフになるかは別途調査。
f:id:seeeko:20201104102211p:plain

(4)1次関数、2次関数などののグラフ

先ほどまでは、データの値があって、それをプロットした。今度は、y=2x+1 のような関数をどうやってグラフにするかを説明する。
3つの方法を紹介するが、2つ目がいいと思う。3つ目は、たとえばy=0.143x + 0.055のような、小数点の関数の場合にエラーが出た気がする。
❶数字をプロットする

import matplotlib.pyplot as plt
x=[0,1,2,3,4,5]
y=[1,3,5,7,9,11]
plt.plot(x,y)     #グラフの作成 (横軸の項目,縦軸の項目)
plt.show()        # グラフの表示 間の数字も直線としてつないでくれる。

シンプルに、以下のように書いてもOK

import matplotlib.pyplot as plt
plt.plot([0,1,2,3,4,5],[1,3,5,7,9,11])     #グラフの作成 (横軸の項目,縦軸の項目)

❷yをxの式で表す
Google Colabを使うと、matplotlibの1文やplt.show()が不要なので、スッキリ書ける。

import numpy as np
import matplotlib.pyplot as plt
x = np.arange(0,5) #x=[0 1 2 3 4]でも同じ
plt.plot(x,2*x+1)

普通に書くと、以下であろう。

%matplotlib inline
import numpy as np
import matplotlib.pyplot as plt
x = np.arange(0,5) #x=[0 1 2 3 4]でも同じ
plt.plot(x,2*x+1)
plt.grid() #座標軸なので、無くてもいい
plt.show() #Google Colabなら不要

❸linespaceを使う

import numpy as np
import matplotlib.pyplot as plt
line=np.linspace(0,5) #グラフの範囲を指定
plt.plot(line, x*2 + 1) #x に対するyの値を x*2 + 1 で指定
plt.show()  

❹2次関数以上
2次関数だろうが、上記の❷の方式で、式で表せば、書き方は同じ。
ただ、プロットの幅を調整しないと、カクカクのグラフになる可能性がある。
x = np.arange(0,5,0.1)
こうすることで、プロット間隔が0.1単位になり、なめらかなグラフになる。

(5)複数のグラフを配置してみよう

以下は、横3、縦2に配置する。だが、実際にはうまくいっていない。縦一列になってしまっている。

%matplotlib inline
import numpy as np
import matplotlib.pyplot as plt
num=1
for i in range(5):
  plt.subplot(3, 2, num) #横3、縦2に配置する。numは番号で、どこに配置するか。ループで1ずつ足している。
  plt.xlim(0,5) #グラフによって、xとyの表示される範囲が変わらないように、指定しておく
  plt.ylim(0,10)
  x = np.arange(0,5) #x=[0 1 2 3 4]でも同じ
  plt.plot(x,i*x+1)
  plt.title('func:y=' + str(i) + 'x+1')  #何のグラフかが分かるようにタイトルをつける
  plt.grid() #座標軸なので、無くてもいい
  plt.show() #Google Colabなら不要
  num += 1

2. math、statistics、numpyでやってみる

(1)数学の基本

❶言葉の定義
数学的な話だが、以下の言葉がある。
・幾何平均(きかへいきん)とは、通常の平均(算術平均)とは異なり、その積のn乗根を計算する。
たとえば、10、12、15であれば、算術平均は、12.33で、幾何平均は、10×12×15の3乗根(立方根)=12.16
・モード(最頻値:さいひんち):言葉の通り、「最も頻繁に(登場した)値」
・メディアン(中央値):データを大きさの順に並べたときに、真ん中に位置する値。母数nが偶数の場合は、中央の2つの値の平均。第2四分位数でもある。
・標準偏差:分散の平方根。バラつきを表す。偏差=観測値ー平均値
・偏差値:50+10×(得点-平均点)/標準偏差
・分散:偏差(平均との差)の2乗を合計し、母数で割ったもの。1/n × Σ(xi-平均)^2 
・変動係数:標準偏差/平均値 なぜこれが必要かというと、平均値が高いものは標準偏差も高くなる。なぜかというと、そもそもの値が大きいからだ。たとえば、TOEIC1000点満点の標準偏差が100で、英検のテスト100点満点の標準偏差が20とすると、どちらがバラつきが大きいかを比べるのに、標準偏差だけで見るのは適切ではない。
分位数(分位点):データを小さいものから大きいものに並べ、4等分したときの値が四分位点。先頭から第一四分位点、第二四分位点(=中央値)、・・・である。
 また、四分位範囲(IQR:Inter Quartle Range)はQ3-Q1
・ネイピア数はeのことで、e = 2.71828・・・
❷補足情報
・分散=2乗の平均 ー 平均の2乗
f:id:seeeko:20201231112552p:plain
・ベイズの定理
 条件付き確率に関する定理。Bが起こったとわかったときにAが起こる確率をP(A|B)とする。このとき、P(A|B)=P(A⋀B)÷ P(B)
・シグモイド関数・・・S字のカーブを描く
・ユークリッド距離 (euclidean distance)は、直線距離なので、2次元の場合は、√(x1-x2)^2+(y1-y2)^2 。
一方、マンハッタン距離 (manhattan distance)は、格子状の道を進む場合と考えよう。
・積分において、範囲が定められているものを定積分、定められていないものが不定積分
・f(x,y,z)などの多変数関数において、xで微分などの特定の変数で微分することを偏微分という

❸相関関係
・散布図を書くと、相関関係がわかる。相関関係には正の相関関係と負の相関関係がある。
・相関係数は、値を定数倍しても、定数を加えても、xとyの座標を逆にしても、単位を変えても変わらない。
・相関関係が強いと、相関係数は1に近づき、弱いと0に近づく。
・相関係数の求め方であるが、まずは共分散を求める。共分散Sxyは、Sxy=1/n ×Σ(xi-xの平均値)×(yi-yの平均値)。これは、xとyの偏差(値-平均)の面積になる。ただし、相関関係がない場合はマイナスの値になるため、全体としては0に近づく。ただ、変数そのものの値によってSxyの大きさが変わるので、それぞれの標準偏差で割る。
相関係数r=Sxy/(Sx × Sy)

❹2項分布
結果が2種類の場合、たとえば、コインの裏表やサイコロのある数字が出るか、など。
1つが成功とし、その確率をpとすると、もう一つの失敗の確率は1-p
試行回数がn回のとき、成功回数Xを確率変数とする分布が二項分布である。
以下の例で考えると、n=10で、あたりの確率p=0.5とすると、
P(X=0)=0.001
P(X=1)=0.010
P(X=2)=0.044
・・・
となり、これを見ると、よく見る2項分布のグラフになる。
https://bellcurve.jp/statistics/course/6979.html

確率変数Xは、二項分布B(n,p)で表される。

(2)statisticsの場合

import statistics でインポート

項目 関数 備考
平均(average) statistics.mean() numpyの場合はnp.average()
中央値(median) statistics.median() -
最頻値(mode) statistics.mode() -
分散(variance) statistics.variance() -
標準偏差(standard deviation) statistics.pstdev() statistics.stdevを使うと母数がN-1になるので、値が異なる。

以下、実行例

import statistics
x=[0,3,3,5,5,5,5,7,7,10,20,30,40,100,111]
print(statistics.mean(x))      #==>平均 23.4
print(statistics.median(x))    #==>中央値 7
print(statistics.mode(x))      #==>最頻値 5
print(statistics.variance(x))  #==>分散 1237.3999999999999
print(statistics.pstdev(x))     #==>標準偏差33.98391776512335
print(statistics.stdev(x))     #==>35.17669683185162 stdev(母数をN–1で計算した標準偏差)  

参考までに、標準偏差の公式をもとに、プログラムを組んだ場合は、以下

import math
import statistics
x=[0,3,3,5,5,5,5,7,7,10,20,30,40,100,111]
total=0
for i in x:
  total += (i-sum(x)/len(x))**2
s=total/len(x)
hensa=round(math.sqrt(s),3)  
print(hensa) #==>33.984 標準偏差
(3)関数が不要

❶絶対値

print(abs(-5)) #==>5 

❷虚数
複素数 高校でやった3+2iみたいなやつ。実数+虚数(i)
iではなく、jを使う。また、1iの場合、jはなく、1jと表記する。

a=3+2j
print(type(a)) #==><class 'complex'>  このように、jはcomplex型
print(a**2)  #==> (5+12j)
b=1+1j;c=1-1j
print(b*c) #==> (2+0j)

❸四捨五入
あとで説明するnumpyでも書くことができるが、round()を使えばいいだろう。注意点は、1.5などの値が、偶数に寄るところかな。

print(round(1.5))  # ==>2 OK
print(round(2.5))  # ==>2 人間が計算すると3だが、偶数に寄ってしまう。
print(round(1.4999))  # ==>1 OK
print(round(2.5001))  # ==>3 OK

桁数に関してであるが、注意点は、0やマイナスを指定しても、桁数は小数点以下の第1位まで「.0」で表示される。

a = 123.45678
print(round(a)) #==> 123
print(round(a, 2)) #==> 123.45 小数点2桁まで
print(round(a, 1)) #==> 123.5
print(round(a, 0)) #==> 123.0  ※123ではない
print(round(a, -1)) #==>120.0 10の桁で四捨五入
(4)numpy

numpyに関しては、いろいろと応用がきくので、後述する。
❶標準偏差、平均

import numpy as np
x=[0,3,3,5,5,5,5,7,7,10,20,30,40,100,111]
# 標準偏差
print(np.std(x))  #==> 33.98391776512335
# 平均
print(np.average(x))   #==> 23.4

❷相関係数
2つの配列が、どれくらい相関しているかを表す値。

import numpy as np
x = np.array([
[1,2,4,7,9,13,21,4,7],
[3,2,8,13,22,15,11,8,1]])
np.corrcoef(x) 

結果は、以下のように配列で返ってくる。右上と左下の値が相関係数。

array([[1.        , 0.48444926],
       [0.48444926, 1.        ]])
(4)mathを使う

❶logの計算

import math
print(math.log(25))   #==>  3.2188758248682006 底数e
print(math.log(25,2)) #==>  4.643856189774724 底数2
print(math.log(25,5)) #==>  2.0 底数5

❷平方根(ルート)

import math
print(math.sqrt(4)) #==> 2.0
print(math.sqrt(5)) #==> 2.23606797749979

❸角度
角度を弧度法のラジアンに変更するために、math.radians()関数を使う。
高校数学で習ったかと思うが、180度をラジアンにするとπになる。90度はπ/2である。

import math
print(math.radians(180)) #==>3.141592653589793

❹sin(サイン)、cos(コサイン)

import math
#sin30度(またはπ/6)
print(math.sin(math.radians(30)))  # ==> 0.49999999999999994
print(math.sin(math.pi/6))  # ==> 0.49999999999999994
#cos30度
print(math.cos(math.radians(30)))  # ==> 0.8660254037844387
#sin90度
print(math.sin(math.radians(90)))  # ==> 1.0
#cos90度
print(math.cos(math.radians(90)))  # ==>6.123233995736766e-17 実際には0なんだけど、こう表現される。
#丸めてみよう
import numpy as np
print(np.round(math.cos(math.radians(90)))) #==>0.0

3. numpyをもっと

NumPy(Numerical Python)は、Numerical(数値)の言葉の通り、Pythonで数値計算をするライブラリ

(1)numpyでいろいろ表示

❶基本的な数学の値
e(ネイピア数)とパイとlog2を表示してみる

import numpy as np
print(np.e)        # ==> 2.718281828459045
print(np.pi)       # ==> 3.141592653589793
print(np.log(2))   # ==> 0.6931471805599453

❷四捨五入
np.round()関数を使い、カンマのあとに小数点以下の桁数を指定することで、四捨五入ができる。ただし、結果が偶数になるように寄せる偶数丸めなので、注意が必要。

import numpy as np
print(np.round(1.555, 2)) #==>1.56 偶数丸めで四捨五入
print(np.round(1.546, 2)) #==>1.55
print(np.round(1.545, 2)) #==>1.54 本来の四捨五入なら1.55であるべきだが、結果が偶数になるようにしているので、1.54

❸n次元方程式
n次の方程式も簡単に解くことができる。
以下は x^2-3x-2=0 を解く。各項の定数値を入れる

np.roots([1, -3,2])   # ==> array([2., 1.]) 結果は1と2だが、その値が配列に入る

❹連立方程式
連立方程式は、数学の行列で考える。
AX=Yとし、X=Y*A-1とする。 A-1はAの逆行列
たとえば、3x + 2y =1 , 2x +4Y = -2 の連立方程式は、行列にして以下のように解く。

import numpy as np
A = np.matrix([[3,2],[2,4]])
Y = np.matrix([[1],[-2]])
print(np.linalg.inv(A)*Y)

結果は以下のように、1と-1である。

[[ 1.]
 [-1.]]

❺行列およびその計算
・行列は、ふつうにリストで記載する。
・逆行列はnp.linalg.inv()、行列式はnp.linalg.det()、行列の掛け算はnp.dot()で簡単に計算してくれる

import numpy as np
a = [[-2, 1], [3, -2]]  #2次の場合
print(np.linalg.inv(a)) #逆行列
print(np.linalg.det(a)) #行列式

b = [[2, -3,1], [-1, 1,3], [4, -3,2]] #3次の場合
print(np.linalg.inv(b))   #逆行列
print(np.linalg.inv(b)*np.linalg.det(b))   #逆行列に行列式をかけた。

c=[[6],[-2],[1]]
print(np.dot(np.linalg.inv(b),c)) #行列の掛け算
(2)numpy配列の作成

・ndarrayという多次元の配列というか、NumPyでのデータ構造がある。NumPyによって高速な演算処理ができる(?)。
・numpyは行列の演算にはとても便利であり、固有値や逆行列を簡単に求めることができる。
numpyには、多次元配列が使えるnumpy.ndarrayと、2次元配列のnumpy.matirxがあり、2次元に限ればnumpy.matirxの方が、高速性や簡単さの面で利点があるが、わざわざ使う必要はないと思う。
❶作ってみる。そして、リストとの違い

import numpy as np
x = np.arange(5)
print(x) #==> [0 1 2 3 4]
print(type(x)) #==><class 'numpy.ndarray'> 型はnumpy.ndarray
#参考までに、リストを作る
x=list(range(5))
print(x) #==>[0, 1, 2, 3, 4]

このように、リストはカンマがあるが、numpyは空白で区切れらている。
❷多次元の配列を作ろう

y = np.arange(6).reshape(2, 3)
print(y) #==> [[0 1 2]
         #==>  [3 4 5]]

せっかくなので、このyについて、情報を確認する

print(type(y)) #==><class 'numpy.ndarray'> データの型がndarray
print(y.dtype) #==>int64 データの要素の型がint64
print(y.shape) #==>(2, 3) データの配列の形状

ちなみに、ndarrayではない多次元リストの場合は、こんな感じ。カンマで区切られているのと、縦方向にはない。

y=[[1, 2, 3], [4, 5, 6]] 

❸リストからnumpy配列(ndarray)の作成
リストやタプルからndarrayの配列を作ることができる。型変換をするだけ。

import numpy as np
x=list(range(5))
print(x) #==>[0, 1, 2, 3, 4]
y=np.array(x)
print(y) #==>[0 1 2 3 4]

❹pandasのDataFrameからndarrayを作成
to_numpy()を使う。昔は.valuesを使ったようだが、今は非推奨。

import numpy as np
import pandas as pd
x=pd.DataFrame([[1,2,3],[4,5,6]])
print(x)
y=x.to_numpy()
print(y)

出力結果は、以下

   0  1  2
0  1  2  3
1  4  5  6
[[1 2 3]
 [4 5 6]]

❺行列を作る。np.onesなど
・特定の文字で埋めた行列を作る

メソッド 解説
numpy.zeros() 0で埋める
numpy.ones() 1で埋める
numpy.full() 指定した値で埋める

・各要素が1の配列を作成する。

import numpy as np
x = np.ones(3) 
print(x) #==>[1. 1. 1.]
y = np.ones((2,4)) 
print(y) #==>[[1. 1. 1. 1.] 
         #==> [1. 1. 1. 1.]]
print(type(x)) #==> <class 'numpy.ndarray'>

・以下は要素がすべて5の行列

print(np.full((2, 3), 5))

出力結果は、以下

[[5 5 5]
 [5 5 5]]

・単位行列
np.eye()で、0と1からなる単位行列を作ることができる。

np.eye(3) #==> 3×3の単位行列
(3)numpy配列の演算や処理

❶ndarrayの結合
NumPy配列の結合には、np.hstackやnp.vstackがある。

import numpy as np
x=np.array([[1,2,3],[4,5,6]])
y=np.array([7,8,9])
print(np.vstack([x,y]))

出力結果は以下

array([[1, 2, 3],
       [4, 5, 6],
       [7, 8, 9]])

❷数列の処理
・等差数列:np.linspace()
等差数列を作成する。引数は順に、初項、末項、項数
たとえば、np.linspace(1,9,3) だと、初項が1で末項が9、項数が3個なので、公差は4になり、以下の結果になる。

x=np.linspace(1,9,3)
print(x)#==>[1. 5. 9.]

・階差数列:np.diff()
階差数列を作成する。

x=[1,9,3,5]
y=np.diff(x)
print(y)#==>[ 8 -6  2]

❸統計処理
中央値や第1四分位などを簡単に求めることができる。

import numpy as np
x = np.array([10,10,12,15,23,27,28,30,50])
print(np.median(x)) #==>23 中央値
print(np.percentile(x, 50)) #==>第2四分位  
q1,q3=np.percentile(x,[25,75]) # リスト[]に入れて、複数の変数に同時に入れることも可能
print(q1,q3) #==>12.0 28.0 第1四分位と第3四分位 

❹numpy配列の平坦化
ravelやflattenを使って、多次元のnumpy配列を1次元にする。

import numpy as np
#多次元のNumPy配列を作る
x = np.arange(6).reshape(2, 3) 
print(np.ravel(x)) #==>[0 1 2 3 4 5]
print(x.flatten()) #==>[0 1 2 3 4 5]

❺内積(ドット積)
行列aと行列bの内積は、以下で計算する。
np.dot(a, b) またはa@b

import numpy as np
a=np.array([1,2])
b=np.array([2,4])
print(a@b)
print(np.dot(a,b))

4. 乱数

randomまたはnumpyのrandomで乱数を表示できる。

(1)randomで乱数
import random
x=random.choice(['a', 'b', 'c'])
print(x) #==>3つの中からどれか一つを表示
y=random.randrange(10)
print(y) #==>9までの整数のどれかを表示
z=random.sample(range(5),3)
print(z) #==>[2, 3, 1]など。4までの値の中の3つを表示
(2)numpyで乱数

・np.random.rand()は、0以上1未満の乱数を返す
・np.random.randn()は、平均0で標準偏差1の乱数。なのでマイナスもある。
・()で数字を指定することで、n x m の配列を作れる。
・np.random.nomal(平均,標準偏差,出力数)とすることで、平均や標準偏差を指定できる
❶整数

import numpy as np
x=np.random.randint(3)  #0-2までの整数の乱数
print(x) #==> 例えば1
y=np.random.randint(10, 100, (3, 2)) # 10から100未満(つまり99まで)の3行2列の乱数
print(y) #==> たとえば、[[40 44] [21 47] [38 89]]

❷小数

import numpy as np
print(np.random.rand(1))  # ==> [0.12237108]
print(np.random.rand(2))  # ==> [0.42252938 0.50361044]
print(np.random.rand(2,2))  # ==> [[0.64196433 0.86794685] [0.4518707  0.71426258]]
print(np.random.randn(1,3))  # ==> [[ 1.02537103  0.95876857 -1.5977159 ]]

❸小数点の桁数を指定
・precisionで、小数の桁数、suppress=Trueで、eを使わない

import numpy as np
np.set_printoptions(precision=2, suppress=True)
x = np.random.rand(1,3)
print(x)   #==> [[0.7  0.65 0.28]]

❹np.random.nomalで平均と標準偏差を指定する
・以下は、平均が10で標準偏差が1の乱数を10個出す。
・せっかくなので、ヒストグラムも出しておく

#乱数の発生
import numpy as np
a=np.random.normal(10,1,5) #==>[ 9.63223816 10.60368672 10.76586044  9.13246247  9.08411977 ]
print(a)
#ヒストグラムの出力
import matplotlib.pyplot as plt
plt.hist(a)
(3)numpyとrandomの違い

randomを使うと、配列に入るので、カンマがある。numpyはnumpyの配列に入るのでカンマがない。以下がその例
❶randomで乱数

import random
y=random.sample(range(100), 5)
print(y)  #==> たとえば、[68, 85, 23, 15, 60]

❷numpyで乱数

import numpy as np
x=np.random.randint(0, 100,5) # 10から100未満の乱数を5つ
print(x) #==> たとえば、[62 32 35 47  7]

5. 相関係数(詳細)

(1)ケンドール順位相関係数

❶kendalltauモジュールをインポートする場合

from scipy.stats import kendalltau
x = [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]
y = [1,5,2,3,6,7,15,8,4,11,10,14,18,13,22,24,16,19,30,9,25,17,26,23,12,20,28,21,27,29]
print(kendalltau(x,y))
correlation, pvalue = kendalltau(x,y)
print('ケンドール相関係数=', correlation)
print('p値=',pvalue)

出力結果は、以下

KendalltauResult(correlation=0.664367816091954, pvalue=1.8514110976085208e-08)
ケンドール相関係数= 0.664367816091954
p値= 1.8514110976085208e-08

❷計算式から自分で作ってみた。

x = [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]
y = [1,5,2,3,6,7,15,8,4,11,10,14,18,13,22,24,16,19,30,9,25,17,26,23,12,20,28,21,27,29]
g=0;h=0;n=30
for i in range(n):
  for j in range(n):
    if i>=j:
      continue
    if x[i]>x[j] and y[i]>y[j]:
      g += 1
    elif  x[i]<x[j] and y[i]<y[j]:
      g += 1
    else:
      h += 1
print(g,h)  # ==> 362 73
print((g-h)/((n-1)*n/2)) # ==> 0.664367816091954

6. その他

・0で割る
a=1/0としてみる。すると、0で割ることはできないので、以下のようなエラーが出る
ZeroDivisionError: division by zero