今まで線形モデルの Perceptron[link] と Linear Regression[link] に関して勉強してきました。今回は、新しい線形モデルである Logistic Regression に関して勉強したので、Python で実装しました。
導入
Logistic Regression は、 Logistic Regression は Perceptron と Linear Regression のちょうど間に位置すると言ってもいいです。Perceptron は、アウトプットとして、+ か - のようにバイナリの結果を返しました。[ h(x] = sign(w(t)x) ] Liner Regression は、実数の値を返しました。[ h(x) = w(t)x ] これらに対して、今回の新しいモデルである Linear Regression は 0 から 1 の範囲の確率を返します。[ h(x) = theta(w(t)x ] ここでの theta関数は、theta(s) = e^s / 1 + e^s と便宜的に、0 から 1 を返すように設定します。(ロジスティクス関数) x が大きくなればなるほど、アウトプットは 1 に近くなります。逆に小さくなればなるほど、0 に近くなります。
次にコスト関数と、その関数の Gradient を見ていきます。まず、コスト関数は、
その Gradient は、確率的勾配降下法というもので、
です。そもそも確率的勾配降下法とは、Linear Regressioの際に使用した、最急降下法をよりシンプルにしたものです。通常の勾配法では、データ分だけパラメータ(w)を更新するために微分する必要があります。しかし、確率的勾配降下法では、データ分の和を計算する過程を省きます。ここでの”確率的”とは、乱数を使い実行の度に結果が異なるということを表現しています。このアルゴリズムを使用し、パラメータの更新式は、
となります。
Convex function なので local minimum に収束するこの手法でも global minimum であることが保証されています。また、学習率である eta を少しずつ小さくしていきます。下記のグラフのように、eta が大きいと最適な値を飛ばしてしまい学習が安定せず、小さすぎると非効率です。そのため eta をはじめは 0.1 程度の設定し、学習が進むにつれて小さくするというのが一般的のようです。
実装
Pythonで実装した内容がこちらです。
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 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 | #-*- coding: utf-8 -*- import matplotlib.pyplot as plt import numpy as np # 特徴関数 # # def phi(x, y): return np.array([x, y, 1]) # シグモイド関数 # # def sigmoid(z): return 1.0 / (1 + np.exp(-z)) ############################################### # BY using other data set data = np.loadtxt('ex2data1.txt', delimiter=',') X = data[:, 0:2] Y = data[:, 2] N = Y.size; w = np.random.randn(3) # パラメータをランダムに初期化 eta = 0.1 # 学習率の初期値 for i in xrange(400): list = range(N) np.random.shuffle(list) for n in list: x_n, y_n = X[n, :] t_n = Y[n] # 予測確率 feature = phi(x_n, y_n) predict = sigmoid(np.inner(w, feature)) w -= eta * (predict - t_n) * feature # イテレーションごとに学習率を小さくする eta *= 0.9 # 図を描くための準備 seq = np.arange(0, 120, 0.1) xlist, ylist = np.meshgrid(seq, seq) zlist = [sigmoid(np.inner(w, phi(x, y))) for x, y in zip(xlist, ylist)] # 散布図と予測分布を描画 plt.imshow(zlist, extent=[0,120,0,120], origin='lower', cmap=plt.cm.PiYG_r) plt.plot(X[Y==0,0], X[Y==0,1], 'x', color='blue') plt.plot(X[Y==1,0], X[Y==1,1], 'o', color='red') plt.legend(['Not admitted', 'Admitted']) plt.show() |
参考
Gihyo.jp : 第16回 最適化のための勾配法
Gihyo.jp : 第18回 ロジスティック回帰
Gihyo.jp : 第19回 ロジスティック回帰の学習
Gihyo.jp : 第20回 ロジスティック回帰の実装
Machine Learning with Python - Logistic Regression
Caltech : Lecture 9 (The Linear Model II )