Memo

メモ > 技術 > プログラミング言語: Python > 数学の復習

■数学の復習
以下の書籍の勉強メモ やさしく学ぶ 機械学習を理解するための数学のきほん アヤノ&ミオと一緒に学ぶ 機械学習の理論と数学、実装まで https://www.amazon.co.jp/gp/product/B075GSMZDS 以下も参考になりそうなのでメモ 150 分で学ぶ高校数学の基礎 - Speaker Deck https://speakerdeck.com/e869120/150-fen-dexue-bugao-xiao-shu-xue-noji-chu 予備校のノリで学ぶ「大学の数学・物理」 - YouTube https://www.youtube.com/@yobinori ■総和 以下のような、1から100までの足し算があるとする \[1 + 2 + 3 + 4 + … + 99 + 100 \] 総和の記号を使うと、以下のように表現できる \[\sum_{i=1}^{100} i \] 何個足せばいいのかわからない場合、「n」を使って以下のように表現できる \[\sum_{i=1}^{n} i \] 同様に、以下のような式があるとする (式中の「(1)」や「(2)」は「1乗」「2乗」ではなく、「1番目」「2番目」の意味) \[E(\theta) = \frac{1}{2}((y^{(1)} - f_{\theta}(x^{(1)}))^{2} + (y^{(2)} - f_{\theta}(x^{(2)}))^{2} + … + (y^{(n)} - f_{\theta}(x^{(n)}))^{2}) \] これは以下のように表現できる \[E(\theta) = \frac{1}{2} \sum_{i=1}^{n} (y^{(i)} - f_{\theta}(x^{(i)}))^{2} \] ■関数 関数とは、数と数の間の関係を表すもの。値の変換装置 例えば「ある数を入力すると、2倍して1足した数が出力される」という変換装置があるとする \[出力 = 2(入力)+1 \] この場合、関数として記述すると以下のようになる \[f(x) = 2x + 1 \] 実際に値を当てはめて計算すると、以下のようになる \[f(1) = 2 \cdot 1 + 1 = 3 \] \[f(2) = 2 \cdot 2 + 1 = 5 \] \[f(-2) = 2 \cdot -2 + 1 = -3 \] \[f(0) = 2 \cdot 0 + 1 = 1 \] また関数の入力値と出力値をグラフ化することで「入力と出力の関係」を表すことができ、結果として直線や曲線が現れる ■微分 微分とは、小さな変化を見ること 関数のある点における傾きを調べたり、瞬間の変化を捉えることができるものとされる xが少し変化したとき、その変化量をΔxで表す Δは「デルタ」と読み、「微小な変化」の意味で使われる記号 ※ギリシャ語で差分は「διαφορa(diafora)」といい、この頭文字の大文字に由来している(実際は最後の「a」の上にコンマがある)  英語で言う「difference」のこと xの微細な変化を「x が x+Δx に変化した」と表し、横軸をx、縦軸をf(x)とすると、微細な変化量は以下のようになる \[\frac{ f(x + \Delta x) - f(x) }{\Delta x} \] これを平均変化度と言って Δf/Δx と表し、「f(x)をxで微分する」という意味になる 曲線の微細な変化を考える場合、平均変化度は曲線の接線となる。この接戦の傾きが微細な変化と言える Δ の代わりに d を使って df/fx と書くこともある(Δ は今のアルファベットで言えば D にあたるため) また df(x)/dx と書くこともあり、 さらに省略してf'(x)と書くこともある つまり、以下はどれも意味は同じ \[\frac{\Delta f}{\Delta x} \] \[\frac{df}{dx} \] \[\frac{df(x)}{dx} \] \[f'(x) \] x^2(xの2乗)を微分すると2xとなる(具体的な計算は、後述の「微分の計算」を参照) これは特定の点の傾きが分かる状態のもの(「xが1のときの傾きは2、xが2のときの傾きは4」という意味であり、「y = 2x」のような方程式を表しているわけでは無い) 具体的には ・「x = 0」のときの傾きは「2 * 0」なので「0」となる。これは「xが1増えてもyは増減しない」ので平面の状態 ・「x = -1」のときの傾きは「2 * -1」なので「-2」となる。これは「xが1増えたときyが2減る」ので右上がりの状態 ・「x = 1」のときの傾きは「2 * 1」なので「2」となる。これは「xが1増えたときyが2増える」ので右下がりの状態 この内容を前提として、もう少し具体的な内容で記載する 例えば「40秒で120m走行した車の速度」を求める場合、通常以下のように求める \[\frac{120m}{40s} = 3m/s \] ただしこれは平均速度であって、常に秒速3mの速度が出ていたわけではない ある時点における瞬間の速度は、それぞれで異なる値を取る 瞬間の変化量を求めるために、関数を「f(x)」、微小な数を「h」と置くとする ※一般的に、微分の数式では微細な数を「h」で表される 「h」が使われるようになった理由は「無難な文字が選ばれた」など色々な説があるが、よく分かっていないらしい https://bonyari-dtp.hatenablog.com/entry/2021/03/08/200000 このとき、関数「f(x)」の点「x」での傾きは以下のような式で表すことができる(左辺は「f(x)の微分」の意味を表す) \[\frac{d}{dx}f(x) = \lim_{h \to 0} \frac{ f(x + h) - f(x) }{h} \] 文字になると難しく感じるが、具体的な数字を代入してみるとイメージが付きやすい 例えば「10.0秒と10.1秒という0.1秒の間に、40.0mから40.6mに移動した」の場合、「x = 10」「h = 0.1」なので、 \[\frac{ f(10 + 0.1) - f(10) }{0.1} = \frac{ 40.6 - 40}{ 0.1 } = 6 \] となり、「傾き6」が速度となる なお「h = 0.1」はあくまでも例なので、実際は「限りなく0に近い数」となる ■微分の計算 計算の練習として、以下を微分してみる \[f(x) = x^{2} \] 微細な変化量を表す式において、変化量を「限りなく0に近い数」にすると、以下のように表すことができる \[\frac{df}{dx} = \lim_{x \to 0} \frac{ f(x + \Delta x) - f(x) }{\Delta x} \] f(x) は x^2 なので、置き換えると以下のようになる \[\frac{df}{dx} = \lim_{x \to 0} \frac{ (x + \Delta x)^{2} - x^{2} }{\Delta x} \] 式を展開する \[\frac{df}{dx} = \lim_{x \to 0} \frac{ x^{2} + 2x\Delta x + (\Delta x)^{2} - x^{2} }{\Delta x} \] 式を整理する \[\frac{df}{dx} = \lim_{x \to 0} \frac{ 2x\Delta x + (\Delta x)^{2} }{\Delta x} \] \[\frac{df}{dx} = \lim_{x \to 0} (2x + \Delta x) \] Δxを限りなく0に近づけると、Δxが消えて以下のようになる \[\frac{df}{dx} = 2x \] これで計算は完了 つまりxの2乗を微分すると2xになる 上の計算を踏まえて、以下に微分の性質を3つ示す。覚えておくと式の整理を効率よく行える 1つめ \[f(x) = x^{n} \] という式があるとき、これを微分すると以下のようになる \[\frac{d}{dx}f(x) = nx^{n-1} \] 2つめ 複数の関数や定数は以下のように扱える \[\frac{d}{dx}(f(x) + g(x)) = \frac{d}{dx}f(x) + \frac{d}{dx}g(x) \] \[\frac{d}{dx}(af(x)) = a\frac{d}{dx}f(x) \] 3つめ 「x」に関係のない定数aの微分は0になる \[\frac{d}{dx}a = 0 \] 以下計算例 \[\frac{d}{dx}5 = 0 \] \[\frac{d}{dx}x = \frac{d}{dx}x^{1} = 1\cdot x^{0} = 1 \] \[\frac{d}{dx}x^{3} = 3x^{2} \] \[\frac{d}{dx}x^{-2} = -2x^{-3} \] \[\frac{d}{dx}10x^{4} = 10\frac{d}{dx}x^{4} = 10\cdot 4x^{3} = 40x^{3} \] \[\frac{d}{dx}(x^{5} + x^{6}) = \frac{d}{dx}x^{5} + \frac{d}{dx}x^{6} = 5x^{4} + 6x^{5} \] ■偏微分 上で紹介した関数「f(x)」は変数が「x」しかない1変数関数だが、変数が2つ以上ある多変数関数も存在する 機械学習の最適化問題はパラメータの数だけ変数があるので、目的関数が多変数関数となる \[g(x_{1}, x_{2}, … , x_{n}) = x_{1} + x_{2}^{2} … + x_{n}^{n} \] 多変数関数を微分する場合、微分する変数だけに注目し、他の変数はすべて定数として扱うことにして微分する このような微分方法を偏微分という 例えば \[h(x_{1}, x_{2}) = x_{1}^{2} + x_{2}^{3} \] このように変数が2つある場合、3次元空間へのプロットとなる これを例えば「x2 = 1」に固定してみると、以下のように「h」は「x1」だけの関数になる \[h(x_{1}, x_{2}) = x_{1}^{2} + 1^{3} \] これで単純な二次関数となる 定数を微分するとすべて0になるので、「h」を「x1」で偏微分すると以下の結果になる(左辺は「h(x1, x2)の偏微分」の意味を表す) \[\frac{\partial}{\partial x_{1}}h(x_{1}, x_{2}) = 2x_{1} \] 同じ要領で「x1 = 1」に固定してみると、以下のように「h」は「x2」だけの関数になる \[h(x_{1}, x_{2}) = 1^{2} + x_{2}^{3} \] 「h」を「x2」で偏微分すると以下のようになる \[\frac{\partial}{\partial x_{2}}h(x_{1}, x_{2}) = 3x_{2}^{2} \] このように、微分したい変数のみに注目して、他の変数をすべて定数として扱うことで、その変数での関数の傾きを知ることができる 今回は2つの変数を持つ関数での例を挙げたが、変数がどれだけ増えたとしても同じ考え方が適用できる ■合成関数 例えば、以下のような2つの関数「f(x)」と「g(x)」があるとする \[f(x) = 10 + x^{2} \] \[g(x) = 3 + x \] このとき、「x」に適当な値を代入すると、それに対応する値が出力される \[f(1) = 10 + 1^{2} = 11 \] \[f(2) = 10 + 2^{2} = 14 \] \[g(1) = 3 + 1 = 4 \] \[g(2) = 3 + 2 = 5 \] 「x」には関数を代入することもできる \[f(g(x)) = 10 + g(x)^{2} = 10 + (3 + x)^{2} \] \[g(f(x)) = 3 + f(x) = 3 + (10 + x^{2}) \] 「f(x)」の中に「g(x)」が、もしくは「g(x)」の中に「f(x)」が使われているが、このように関数が複数組み合わさったものを合成関数と呼ぶ 例えば合成関数「f(g(x))」を「x」で微分することを考えてみる 解りやすくするために、いったん以下のように変数に置き換えてみる \[u = g(x) \] \[y = f(u) \] こうすると、以下のように段階的に微分できる \[\frac{dy}{dx} = \frac{dy}{du} \cdot \frac{du}{dx} \] つまり「y」を「u」で微分し、「u」を「x」で微分したものを掛けることで計算できる 実際に微分をすると以下のようになる \[\frac{dy}{du} = \frac{d}{du} f(u) \] \[\frac{dy}{du} = \frac{d}{du} (10 + u^{2}) = 2u \] \[\frac{du}{dx} = \frac{d}{dx} g(x) \] \[\frac{du}{dx} = \frac{d}{dx} (3 + x) = 1 \] それぞれの結果を掛けると、微分結果を得ることができる \[\frac{dy}{dx} = \frac{dy}{du} \cdot \frac{du}{dx} \] \[\frac{dy}{dx} = 2u \cdot 1 \] \[\frac{dy}{dx} = 2g(x) \] \[\frac{dy}{dx} = 2(3 + x) \] ■加法定理 以下の関係が成り立つ sin(A + B) = sinA cosB + cosA sinB sin(A - B) = sinA cosB - cosA sinB cos(A + B) = cosA cosB - sinA sinB cos(A - B) = cosA cosB + sinA sinB 加法定理の証明は、以下のページが解りやすい 加法定理 https://w3e.kanazawa-it.ac.jp/math/category/sankakukansuu/kahouteiri/henkan-tex.cgi?target=/math/cat... ■ベクトルと行列 ベクトルとは数を縦に並べたもの、行列とは数を縦と横に並べたもので、それぞれ以下のような形をしている \[a = \begin{bmatrix} 3 \\ 9 \end{bmatrix} , A = \begin{bmatrix} 6 & 3 \\ 8 & 10 \end{bmatrix} \] 慣習的にベクトルは小文字、行列は大文字のアルファベットを用いる(加えて、太文字で表すことが多い) ここでベクトルaは縦に2つの数が並んでおり、これは2次元ベクトルとなる 行列Aは縦横に2つの数が並んでおり、2×2(2行2列)のサイズの行列となる ベクトルを「列が1つしかない行列」と考えると、aは「2×1の行列」とみなすことができる \[A = \begin{bmatrix} 6 & 3 \\ 8 & 10 \end{bmatrix} , B = \begin{bmatrix} 2 & 1 \\ 5 & -3 \end{bmatrix} \] 行列は、それぞれ和差積の演算を定義することができる 和と差は単純に各要素ごとに足し算と引き算をすればいい \[A + B = \begin{bmatrix} 6 + 2 & 3 + 1 \\ 8 + 5 & 10 - 3 \end{bmatrix} = \begin{bmatrix} 8 & 4 \\ 13 & 7 \end{bmatrix} \] \[A - B = \begin{bmatrix} 6 - 2 & 3 - 1 \\ 8 - 5 & 10 + 3 \end{bmatrix} = \begin{bmatrix} 4 & 2 \\ 3 & 13 \end{bmatrix} \] 積は少し特殊で、左側の行列の「行」と右側の行列の「列」の要素を順番に掛けてから、それらを足し合わせる 行列同士の掛け算をする場合、左側にある行列の列数と、右側にある行列の行数が一致している必要がある \[AB = \begin{bmatrix} 6 * 2 + 3 * 5 & 6 * 1 + 3 * -3 \\ 8 * 2 + 10 * 5 & 8 * 1 + 10 * -3 \end{bmatrix} = \begin{bmatrix} 27 & -3 \\ 66 & -22 \end{bmatrix} \] また、以下のように行と列を入れ替える操作を転置と呼ぶ \[a = \begin{bmatrix} 2 \\ 5 \\ 2 \end{bmatrix} , a^{T} = \begin{bmatrix} 2 & 5 & 2 \end{bmatrix} \] ベクトル同士を掛ける場合、以下のように片方を転地してから積を計算することがある これはベクトル同士の内積を求めることと同じ \[a = \begin{bmatrix} 2 \\ 5 \\ 2 \end{bmatrix} , a^{T} = \begin{bmatrix} 1 \\ 2 \\ 3 \end{bmatrix} \] \[a^{T}b = \begin{bmatrix} 2 & 5 & 2 \end{bmatrix} \begin{bmatrix} 1 \\ 2 \\ 3 \end{bmatrix} \] \[a^{T}b = [ 2 * 1 + 5 * 2 + 2 * 3 ] \] \[a^{T}b = [ 18 ] \] ■ベクトルと内積 ※整理中。考え方や計算などに間違いがある可能性があるので注意 以下で具体例をもとに、ベクトルの性質を確かめる 2つの2次元ベクトルがあるとする \[a = (3, 1), b = (2, 3) \] aにおいて、斜辺の長さは \[\sqrt{3^{2} + 1^{2}} = \sqrt{10} (近似値は3.16227程度) \] となる またbにおいて、斜辺の長さは \[\sqrt{2^{2} + 3^{2}} = \sqrt{13} (近似値は3.60555程度) \] となる cosをもとに、ベクトルaとx軸の成す角度を求めると、 \[3 / 3.16227 = 0.94868... \] となり、このときの角度は18.43554...度となる(アークコサインでラジアンを求められるので、それを角度に変換する) またcosをもとに、ベクトルbとx軸の成す角度を求めると、 \[2 / 3.60555 = 0.55470... \] となり、このときの角度は56.30994...度となる(アークコサインでラジアンを求められるので、それを角度に変換する) よってベクトルaとbの成す角度は、 \[56.30994 - 18.43554 = 37.8744 \] となり、約38度となる これをもとに、公式を使ってベクトルaとbの内積を求めると \[a・b = |a|・|b|・cos\theta = 3.16227・3.60555・cos(37.8744) = 3.16227・3.60555・cos(38) = 3.16227 * 3.60555 * 0.78935 = 8.99994 \] となり、ベクトルaとbの内積は9となる 続いて、座標からも内積を求めてみる \[a = \begin{bmatrix} 3 & 1 \end{bmatrix}, b = \begin{bmatrix} 2 & 3 \end{bmatrix} \] 一方を転置して計算する \[a b^{T} = \begin{bmatrix} 3 & 1 \end{bmatrix} \begin{bmatrix} 2 \\ 3 \end{bmatrix} = \begin{bmatrix} 3 * 2 + 1 * 3 \end{bmatrix} = \begin{bmatrix} 9 \end{bmatrix} \] この場合も、値が9になることを確認できる つまりベクトル同士の掛け算において、片方を転置してから積を計算することで、ベクトル同士の内積を取ることができる 続いて、内積が何を求めているかを改めて考える まずはbの地点からベクトルaに対して垂直に線を引いた時の、その交点と原点の距離を求める 距離をxと置くと、以下のように求めることができる \[cos(37.8744) = x / 3.60555 \] \[0.78935 = x / 3.60555 \] \[x = 0.78935 * 3.60555 = 2.84604 \] 求められたxに、aの長さをかけたものが内積となる \[2.84604 * 3.16227 = 8.99994 \] この場合も、値が9になることを確認できる つまり内積とは「ベクトルbの終点からベクトルaに対して垂直に線を引いた時の、その交点と原点の距離」にベクトルaの長さをかけたもの ベクトルの内積というのは何を求めているのでしょうか。 - 内積を使って何が求ま... - Yahoo!知恵袋 https://detail.chiebukuro.yahoo.co.jp/qa/question_detail/q14183393379 【数学】「内積」の意味をグラフィカルに理解すると色々見えてくる その1 #Python - Qiita https://qiita.com/kenmatsu4/items/a144047c1b49aa8c7eb0 以下はベクトルを図示するプログラム ベクトルaの長さは約3.16、ベクトルbの長さは約2.85 3.16×2.85=9.006 で、おおよそ9になる
import numpy as np import matplotlib matplotlib.use('Agg') # 描画バックエンドを 'Agg' に設定(画像ファイルとして保存するため) import matplotlib.pyplot as plt # ベクトルを Numpy 配列として定義 a = np.array([3, 1]) b = np.array([2, 3]) # ベクトル a と b の内積を計算 dot_product = np.dot(a, b) print(dot_product) # 9 # グラフのサイズを設定 plt.figure(figsize=(8, 6)) # ベクトル a と b をプロット plt.quiver(0, 0, a[0], a[1], angles='xy', scale_units='xy', scale=1, color='r', label=f'a = {a}') plt.quiver(0, 0, b[0], b[1], angles='xy', scale_units='xy', scale=1, color='b', label=f'b = {b}') # 内積のハイライト表示 # 簡単のために、ベクトル b をベクトル a に射影する # 射影 (dot_product_b_on_a) は a の縮小版 projection_length = dot_product / np.linalg.norm(a) ** 2 # a に対する b の射影の長さを計算 print(projection_length) # 0.8999999999999998 dot_product_b_on_a = projection_length * a # 射影ベクトルを計算 print(dot_product_b_on_a) # [2.7 0.9] plt.quiver(0, 0, dot_product_b_on_a[0], dot_product_b_on_a[1], angles='xy', scale_units='xy', scale=1, color='g', label='Projection of b on a') # ベクトル a に垂直な線を引く plt.plot([b[0], dot_product_b_on_a[0]], [b[1], dot_product_b_on_a[1]], color='purple', linestyle='--', label='Line perpendicular to vector a') normalized_a = a / np.linalg.norm(a) scaled_a = normalized_a * 9 plt.quiver(0, 0, scaled_a[0], scaled_a[1], angles='xy', scale_units='xy', scale=1, color='pink', label='Scaled a (Length 9)') # グラフの軸設定 plt.xlim(0, 10) plt.ylim(0, 10) plt.xlabel('X axis') # X軸ラベル plt.ylabel('Y axis') # Y軸ラベル plt.axhline(0, color='black', linewidth=0.5) # X軸 plt.axvline(0, color='black', linewidth=0.5) # Y軸 plt.grid(which='major', color='gray', linestyle='-', linewidth=0.5) # 主目盛線 plt.minorticks_on() plt.grid(which='minor', color='gray', linestyle=':', linewidth=0.5) # 補助目盛線 plt.legend() # 凡例表示 # グラフを画像として保存 plt.savefig('graph.png')
さらに別の側面から考察 行列との関係を考えてみる 以下のベクトルaとbがあるとする a = (3, 1), b = (2, 3) ベクトルaとbの内積は以下のように求められる 3*2 + 1*3 = 9 ベクトルaとbを2行2列の行列とみなし、そのまま行列の積を求めると以下のようになる
a * b = a |3 1| * |2 3| = |(3*2 + 1*0) (3*3 + 1*0)| = |6 9| |0 0| |0 0| |(0*2 + 0*0) (0*3 + 0*0)| |0 0|
bを転置して計算すると以下のようになる
a * b = a |3 1| * |2 0| = |(3*2 + 1*3) (3*0 + 1*0)| = |9 0| |0 0| |3 0| |(0*2 + 0*3) (0*0 + 0*0)| |0 0|
転置して計算することで9(内積の値)になることが確認できる (スカラーと行列は別ではあるが、1つの要素以外は0なので、9と言えなくはない…と思う) さらに別の側面から考察 少し極端な値のベクトルで考えてみる 以下ベクトルaとbの場合、 a = (5, 1), b = (0.1, 50) 内積は以下のようになる 5*0.1 + 1*50 = 0.5 + 50 = 50.5 コサインを使って求める場合、内積は以下のようになる ・ベクトルaの長さは、三平方の定理より5.1(5.09901951359)となる ・ベクトルbの長さは、三平方の定理より50(50.0000999999)となる ・コサインの値は 50.5 / (5.10 * 50.00) なので0.198(0.19803921568)となる ・よってコサインを使用した内積は 5.1 * 50 * 0.198 で、約50.5となる つまり、転置して計算した場合と同じ値を求められていることが判る 続いて「a・b = ab cos(θ)」を数学的に証明する 2つの2次元実ベクトルA, Bの長さをそれぞれa, bとし、それらの交点をθとする また、ベクトルAの角度をΦとする このとき、ベクトルA, Bは以下のように表すことができる A = (a1, a2) = (a cosΦ, a sinΦ) B = (b1, b2) = (b cos(θ+Φ), b sin(θ+Φ)) 一方を転置して積を求める。つまり内積を求めると以下のようになる a cosΦ・b cos(θ+Φ) + a sinΦ・b sin(θ+Φ) 共通要素のabをまとめると以下のようになる ab { cosΦ・cos(θ+Φ) + sinΦ・sin(θ+Φ) } 三角関数の加法定理によると、以下の関係が成り立つ 1. sin(A + B) = sinA cosB + cosA sinB 2. sin(A - B) = sinA cosB - cosA sinB 3. cos(A + B) = cosA cosB - sinA sinB 4. cos(A - B) = cosA cosB + sinA sinB この定理のうち、4を用いて式を変形する ab { cos(Φ - (θ+Φ)) } = ab { cos(Φ - θ - Φ) } = ab { cos(-θ) } コサインカーブをもとにすると、「cos(-θ) = cos(θ)」となる よって、最終的に以下のように変形できる = ab cos(θ) これにより、「一方を転置して積を求める。つまり内積を求める」という計算は、以下と等価となる ab cos(θ) これで以下の関係が求められた a・b = ab cos(θ) 内積(ベクトルの内積)とは?定義・公式・計算例・意味・英語訳【線形代数】 | k-san.link https://k-san.link/inner-product/ 以下メモ 行列の積(掛け算)を分かりやすく解説! - 「なんとなくわかる」大学の数学・物理・情報 https://www.krrk0.com/matrix-multiplication/ 行列の演算(和・定数倍・積)の定義と性質をわかりやすく丁寧に | 数学の景色 https://mathlandscape.com/matrix-cal/ 行列の掛け算について、その「意味」を教えてください。 - まず、(1行2... - Yahoo!知恵袋 https://detail.chiebukuro.yahoo.co.jp/qa/question_detail/q11256265466 転置行列の意味が少しわかりました | 進化するガラクタ https://evolvingbook.com/2019/01/28/transposed-matrix/ 転置行列の意味・重要な7つの性質と証明 | 高校数学の美しい物語 https://manabitimes.jp/math/1046 「ルート2」を求める場合のJavaScript Math.sqrt(2) = 1.41421... 「cos(60)は0.5」を求める場合のJavaScript Math.cos(60 * Math.PI / 180) = 0.5 「0.5はcos(60)」を求める場合のJavaScript 180 / Math.PI * Math.acos(0.5) = 60 ■法線ベクトル 法線ベクトルとは、ある直接に垂直なベクトルのこと 例えば \[ax + by + c = 0 \] という直線があるとき、その法線ベクトルpは \[p = (a, b) \] となる ■指数・対数 指数とは、数の右上に記載して「その数を何乗するか」を表すもの 例えば以下のようなもの \[x^{3} = x \cdot x \cdot x \] \[x^{-4} = \frac{1}{x^{4}} = \frac{1}{x \cdot x \cdot x \cdot x} \] 指数は以下のような性質を持っており、これらは指数法則と呼ばれている \[a^{b} \cdot a^{c} = a^{b + c} \] \[\frac{a^{b}}{a^{c}} = a^{b - c} \] \[(a^{b})^{c} = a^{b + c} \] 上のように、指数は通常普通の数が使われるが、指数部が変数になっているものがある こようなものは指数関数と呼ばれ、以下のような関数の形をしている(「a > 1」の場合) \[y = a^{x} \] このような指数関数の逆関数として対数関数というものがあり、それを log を使って以下のように表す \[y = {log_{a}}x \] 逆関数とは、ある関数の「x」と「y」を入れ替えた関数のこと 逆関数のグラフの形は、もとの関数のグラフを時計回りに90度回転させて、左右方向に反転させた形になっている これは「a を y 乗すると x になる」と考えることができる また「a」の部分を「底」と呼ぶが、特にネイピア数(「e」という記号で表される 2.7182… という定数)を底としたものを自然対数と言い、 自然対数の場合は底を省略して単純に log または ln を使って以下のように表すことが多くある \[y = {log_{e}}x = log \ x = ln \ x \] この対数関数は以下のような性質を持っている \[log \ e = 1 \] \[log \ ab = log a + log b \] \[log \frac{a}{b} = log \ a - log \ b \] \[log \ a^{b} = b \ log \ a \] また、対数関数の微分もよく使われる 底を「a」とする対数関数の微分は以下のようになる \[\frac{d}{dx}log_{a}x = \frac{1}{x \ log \ a} \] 特に底が「e」の自然対数については、「log e = 1」という性質から、微分結果も以下のように簡潔なものになる \[\frac{d}{dx}log_{e}x = \frac{1}{x} \] ■代表値 平均値 … 変量の総和を個数で割ったもの。外れ値の影響を受けやすい 中央値 … 母集団の分布の中央にくる値。平均値に比べて外れ値の影響を受けにくい 最頻値 … 最も多い度数(頻度)を示す値。外れ値の影響はまず受けない ■標準偏差 標準偏差の意味と求め方 | AVILEN AI Trend https://ai-trend.jp/basic-study/basic/standard-deviation/ 統計学における分散とは?不偏分散との違いも! 例題でわかりやすく解説 | AVILEN AI Trend https://ai-trend.jp/basic-study/basic/variance/ 以下のデータがあるとする 名前: 得点 Aさん: 90点 Bさん: 80点 Cさん: 40点 Dさん: 60点 Eさん: 90点 平均は以下のように求められる \[(90 + 80 + 40 + 60 + 90) / 5 \\ = 72 \] 偏差(平均からの隔たりの大きさ)は以下のように求められる Aさん: 90 - 72 = 18 Bさん: 80 - 72 = 8 Cさん: 40 - 72 = -32 Dさん: 60 - 72 = -12 Eさん: 90 - 72 = 18 分散(データのばらつき具合)は以下のように求められる。偏差を2乗(マイナスの値を無くすため)し、すべてを足し合わせた値の平均を出している 偏差は個々の値を見るが、偏差ではデータ全体のばらつき具体を見ることができる 分散の値が大きければ、ばらつき具合が大きいということになる \[((90 - 72)^2 + (80 - 72)^2 + (40 - 72)^2 + (60 - 72)^2 + (90 - 72)^2) / 5 \\ = ((18)^2 + (8)^2 + (-32)^2 + (-12)^2 + (18)^2) / 5 \\ = (324 + 64 + 1024 + 144 + 324) / 5 \\ = 376 \] 分散は偏差を2乗した値の平均を取っているため、その数値はもとのデータとは単位が異なる そこで、平方根で本来のデータと単位を揃える この値を標準偏差と呼ぶ \[√376 \\ =19.3907194297 \] これで「平均点±19.39点の中に大体の人がいる」ということを求めらえる 正規分布(平均値と最頻値・中央値が一致し、それを軸として左右対称となっている確率分布)の場合、平均値±標準偏差中に観測データが含まれる確率は68.3%になる これが±標準偏差の2倍、3倍になるとさらに確率は上がる - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 範囲 範囲内に指定の数値が現れる確率 - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 平均値±標準偏差 68.3% 平均値±(標準偏差×2) 95.4% 平均値±(標準偏差×3) 99.7% - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 各値について、平均値との差を標準偏差で割ると「平均が0、標準偏差が1」のデータになる(つまり「0±1の中に大体(7割ほど)のデータが存在する」となる) これを標準化と呼ぶ(X軸のスケールのみが小さくなる。機械学習の際、データを標準化して扱うことで処理が早くなる) Aさん: (90 - 72) / 19.39 = 0.93 Bさん: (80 - 72) / 19.39 = 0.41 Cさん: (40 - 72) / 19.39 = -1.65 Dさん: (60 - 72) / 19.39 = -0.62 Eさん: (90 - 72) / 19.39 = 0.93 ※平均は「0.93 + 0.41 - 1.65 - 0.62 + 0.93 = 0」となる 分散は「((0.93 - 0)^2 + (0.41 - 0)^2 + (-1.65 - 0)^2 + (-0.62 - 0)^2 + (0.93 - 0)^2) / 5 = 1.00096 = おおよそ1」となる 標準偏差は「1」となる(1の平方根は1) 標準化については以下も参照 機械学習でなぜ正規化が必要なのか - Qiita https://qiita.com/yShig/items/dbeb98598abcc98e1a57 【統計・機械学習】標準化(Standardization)と正規化(Normalization)とは?初心者向けにわかりやすく解説 | AI Academy Media https://aiacademy.jp/media/?p=1147 正規化・標準化を徹底解説 (Python 前処理 サンプルコード付き) https://www.codexa.net/normalization-python/ 【機械学習入門】正規化と標準化の特徴量のスケーリングの使い分け方法 https://www.hobby-happymylife.com/%E3%83%97%E3%83%AD%E3%82%B0%E3%83%A9%E3%83%9F%E3%83%B3%E3%82%B0/no... 標準化した値を10倍して50を加えると、「平均が50、標準偏差が10」のデータになる。この値を偏差値と呼ぶ つまり、偏差値は以下のように求める ((得点 - 平均点) / 標準偏差) * 10 + 50 偏差値が50ということは、集団での平均値と一致するということになる 偏差値が60ということは、平均値±標準偏差なので、集団の中で上から約19.85%((100 - 68.3) / 2)のところに位置しているということになる 偏差値が70ということは、平均値±(標準偏差×2)なので、集団の中で上から約2.3%((100 - 95.4) / 2)のところに位置しているということになる 今回の場合、80点の偏差値は以下のようになる \[((80 - 72) / 19.39) * 10 + 50 \\ = 54.1258380609 \] 今回の場合、90点の偏差値は以下のようになる \[((90 - 72) / 19.39) * 10 + 50 \\ = 59.2831356369 \] ■標準偏差(実際の得点に近いデータで確認) 疑似偏差値計算 https://shade-search.com/sts/fsw/hensachi/test.cgi 作成された、以下の得点データで試す
0 0 6 8 10 10 11 13 15 17 18 18 18 20 21 21 21 22 22 22 23 23 23 24 24 24 25 25 25 25 26 26 26 26 26 27 27 27 27 27 28 28 28 29 30 31 31 31 31 32 32 32 32 32 32 33 33 33 34 34 34 34 34 34 35 35 35 35 36 36 36 36 36 36 37 37 37 38 38 38 38 38 39 39 39 39 40 40 40 41 41 41 41 41 41 41 41 41 42 42 42 42 42 42 43 43 43 43 43 43 43 43 44 44 44 44 44 44 45 45 46 46 46 46 46 46 46 46 46 46 47 47 47 47 47 47 47 47 47 47 47 47 48 48 48 49 49 49 49 49 50 50 50 50 50 50 50 50 51 51 51 51 51 51 51 52 52 52 52 52 52 53 53 53 53 53 54 54 54 54 54 54 54 55 55 55 55 55 55 55 55 56 56 56 56 56 56 57 57 58 58 58 58 59 59 59 59 59 59 59 60 60 60 61 61 62 62 62 62 62 63 63 63 63 63 63 63 64 64 64 64 64 65 66 66 66 66 66 67 67 67 67 67 67 67 68 68 68 69 69 69 69 69 69 70 70 70 70 70 71 71 71 72 72 73 73 74 74 74 75 75 77 77 77 77 77 78 79 79 79 79 79 79 79 80 80 81 82 82 82 83 83 84 85 87 87 90 91 96 96
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 得点エリア 人数 得点エリアの平均点 得点エリアの合計点 - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 0〜9 4 4.5 18.0 10〜19 9 14.5 130.5 20〜29 31 24.5 759.5 30〜39 42 34.5 1449.0 40〜49 64 44.5 2848.0 50〜59 60 54.5 3270.0 60〜69 44 64.5 2838.0 70〜79 30 74.5 2235.0 80〜89 12 84.5 1014.0 90〜100 4 95.0 380.0 - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 参考までに、得点エリアごとの人数をグラフにプロットするには以下のようになる
import numpy as np import matplotlib matplotlib.use('Agg') import matplotlib.pyplot as plt x = [ 0, 10, 20, 30, 40, 50, 60, 70, 80, 90] y = [ 4, 9, 31, 42, 64, 60, 44, 30, 12, 4] plt.figure(figsize=(4, 4), dpi=72) plt.plot(x, y) plt.savefig('output/graph.png')
偏差値は以下のようになる 得点合計 ... 14938 得点の平均 ... 49.7933333333333 標準偏差 ... 18.5568663542337 0点の偏差値 = (( 0 - 49.79) / 18.56) * 10 + 50 = 23.1734913793 24点の偏差値 = (( 24 - 49.79) / 18.56) * 10 + 50 = 36.1045258621 70点の偏差値 = (( 70 - 49.79) / 18.56) * 10 + 50 = 60.8890086207 96点の偏差値 = (( 96 - 49.79) / 18.56) * 10 + 50 = 74.8976293103 100点の偏差値 = ((100 - 49.79) / 18.56) * 10 + 50 = 77.0528017241 以下はサンプリングしたデータから標準偏差と偏差値を計算した場合 得点合計 = 14942 得点の平均=49.8066666666667 標準偏差 = 18.4979986905491 (疑似平均使用) 24点の偏差値 = 36.0489412404101 (疑似平均使用) 以下は全体の平均値のみ、オリジナルデータから得た場合 標準偏差 = 18.4980034958731 (オリジナルの平均使用) 24点の偏差値 = 36.0561528496371 (オリジナルの平均使用) 標準偏差の誤差 abs(18.4979986905491 - 18.5568663542337) = 0.0588676636845697 偏差値の誤差 abs(36.0489412404101 - 36.1003830921869) = 0.0514418517768078 ■最急降下法 最急降下法(さいきゅうこうかほう)もしくは勾配降下法(こうばいこうかほう)と呼ばれる ※整理中。以下を参考にメモを残しておきたい やる夫で学ぶ機械学習 - 単回帰問題 - - けんごのお屋敷 http://tkengo.github.io/blog/2016/01/04/yaruo-machine-learning2/ 最急降下法の概要 - Qiita https://qiita.com/Takayoshi_Makabe/items/ee467313c38b1879c097 \[g(x) = (x - 1)^{2} \] という二次関数のグラフがあるとき、最小値は x = 1 のときの g(1) = 0 である この式は単純なので簡単に求められるが、複雑な式の場合には以下のように求める方法がある まず、二次関数の増減表を求める 増減表を求めるためには関数を微分する \[\frac{d}{dx}g(x) = 2x - 2 \] 増減表は以下のようになる
x の範囲 … x<1 x=1 x>1 g(x) を微分したときの符号 … - 0 + g(x) の増減 … 減少 増加
例えば x = 3 からスタートして g(x) の値を小さくするためには、x を少しずつ左にずらしていけばいい(増減表から x > 1 の時は、グラフが左下がりになっているのがわかるため) x = -3 からだと、逆に右にずらしていけばいい つまり導関数の符号によって x をずらす方向が変わる(マイナスなら減少だから右にずらし、プラスなら増加だから左にずらす) このように微分して導関数を求めて、その符号によって x の位置をずらす、別の言い方をすると x を更新していくことで、最小値を求める x の更新を式にすると以下のようになる \[x := x - \eta \frac{d}{dx} g(x) \] これは「x を新しい x で定義していく」ということになり、つまりは計算で求めた x を次の計算に使うことになる この手法を最急降下法や勾配降下法という 微分式の前に付いている記号は「イータ」と読み、学習率と呼ばれる正の定数 学習率が小さければ、g(x) の最小値にたどり着くまでに何度も x を更新する必要があって時間がかかってしまう 逆に学習率を大きくすれば、速く g(x) の最小値にたどり着ける可能性があるが、x が定まらず発散してしまう可能性もある 具体的には g(x) の微分は 2x - 2 だから、x を更新する式は \[x := x - \eta (2x - 2) \] となる イータを1として x = 3 から始めて計算すると x := 3 - 1(2 * 3 - 2) = 3 - 4 = -1 x := -1 - 1(2 * -1 - 2) = -1 + 4 = 3 x := 3 - 1(2 * 3 - 2) = 3 - 4 = -1 となり、ループして求めることができない (1つ目の式で求められた「-1」を2つ目の式で使う。以降も同じように計算している) これが発散している状態 イータを0.1として計算すると x: = 3 - 0.1(2 * 3 - 2) = 3 - 0.4 = 2.6 x: = 2.6 - 0.1(2 * 2.6 - 2) = 2.6 - 0.3 = 2.3 x: = 2.3 - 0.1(2 * 2.3 - 2) = 2.3 - 0.2 = 2.1 x: = 2.1 - 0.1(2 * 2.1 - 2) = 2.1 - 0.2 = 1.9 となり、時間はかかるが正解には近づくことができている (1つ目の式で求められた「2.6」を2つ目の式で使う。以降も同じように計算している)

Advertisement