ラビットチャレンジ　レポート（その5　機械学習-ロジスティック回帰）

## ロジスティック回帰
分類問題を解くための教師あり機械学習モデル。線形回帰の時にも用いたような、m次元パラメータと入力の線形結合をSigmoid関数に入力することで出力を得る。この時の出力は、「y=1になる確率」と解釈できる。

### 分類問題
入力（説明変数、特徴量）はm次元のベクトル、出力はカテゴリ変数（特に、0or1の2値を分類する場合は2値分類になる）。

### Sigmoid関数の性質
sigmoid関数は以下の形で表される。

```math
\sigma(x) = \frac{1}{1+\exp(-ax)}
```
ここで、$a$は定数。$a$を増減させることで、$x=0$付近での関数の傾きを調整できる。
sigmoid関数の微分は、sigmoid関数自身で表すことが可能であるため、後々尤度関数の微分をするとき、計算しやすい。

```math
\frac{\partial \sigma(x)}{\partial x} = \frac{\partial}{\partial x}\left(\frac{1}{1+\exp(-ax)} \right) \\
= a \sigma(x)(1- \sigma(x))
```

### モデルの式
具体的に、ロジスティック回帰の式は以下のように表される。

```math
P(Y=1|\boldsymbol{x}) = \sigma(w_0 + w_1 x_1 + \dots + w_m x_m)
```
この式を元に、右辺の計算結果が0.5以上ならば$Y=1$、未満ならば$Y=0$として分類する。

### 最尤推定
パラメータがある値を取るときに、そのパラメータの関数としてある事象が起こる確率のことを**尤度関数**と呼ぶ。
例えば、確率pで1,確率1-pで0が得られる事象の尤度関数は、

```math
P(y_1, y_2, \dots, y_n;p) = \Pi_{i=1}^{n} p^{y_i} (1-p)^{1-y_i}
```
と書ける。あるデータ系列$y_1, y_2, \dots, y_n$が得られたときに、この尤度関数を最大化するようにパラメータを推定する方法を**最尤推定**と呼ぶ。

ロジスティック回帰モデルの尤度関数は以下のようになる。

```math
P(y_1, y_2, \dots, y_n|w_0, w_1, \dots, w_m) = \Pi_{i=1}^{n} p_i^{y_i}(1-p_i)^{1-y_i} \\
= \Pi_{i=1}^{n} \sigma(\boldsymbol{w}^\top \boldsymbol{x}_i)^{y_i}(1-\sigma(\boldsymbol{w}^\top \boldsymbol{x}_i))^{1-y_i} \\
= L(\boldsymbol{w})
```
これをパラメータ$\boldsymbol{w}$について偏微分することで、尤度関数が最大値をとるときのパラメータを求めるが、対数関数が単調増加であることを利用して、以下の対数尤度関数を考える。

```math
E(\boldsymbol{w})=-\log L(\boldsymbol{w}) = - \Sigma_{i=1}^{n} \{y_i \log{p_i} + (1-y_i) \log(1-p_i) \}
```

### 勾配降下法
反復学習により、パラメータを逐次的に更新するアプローチの1つ。
ロジスティック回帰に置いて、実際には先ほどの対数尤度関数を微分して解析的に解を求めることは困難なので、パラメータを以下の式を用いて逐次更新していく。

```math
\boldsymbol{w}_{k+1} = \boldsymbol{w}_{k} - \eta \frac{\partial E(\boldsymbol{w})}{\partial \boldsymbol{w}} = \boldsymbol{w}_{k} + \eta \Sigma_{i=1}^{n}(y_i - p_i) \boldsymbol{x}_i
```

### 混同行列
2値分類のモデルを評価するときによく用いられる指標。

| |検証用データの結果：真|検証用データの結果：偽|
|:----:|:----:|:-----:|
|**モデルの予測結果：真**|真陽性（TP）|偽陰性（FP）|
|**モデルの予測結果：偽**|偽陽性（FN）|偽陰性（TN）|

これらを用いた指標がいくつかある。

##### 正解率
正解した数/予測対象となった全データ数
分類したい2クラスで偏りがあると、あまりあてにならない。

```math
\frac{TP+TN}{TP+FN+FP+TN}
```

##### 再現率（Recall）
実際に陽性のもののうち。モデルで陽性と判定で来た割合。
病気の検診など、「陽性であるものを陰性を判定することを避けたい」ときに用いられる指標。

```math
\frac{TP}{TP+FN}
```

##### 適合率（Precision）
モデルが陽性と予測したものの中で、実際に陽性である割合。
迷惑メールの分類など、「見逃しが多くても寄り正確な」分類をしたいときに有用。

```math
\frac{TP}{TP+FP}
```

##### F値
再現率と適合率はトレードオフの関係にあるので、これらの調和平均をとり、両方が高いモデルを作りたいときに使う指標。

```math
\frac{2 * Recall * Precision}{Recall + Precision}
```

### ハンズオン
タイタニック号の乗客データを用いて、事故後の生死を判定するためのロジスティック回帰モデルを作成。
まずはチケット価格のみで予測してみる。

```python
from sklearn.model_selection import train_test_split
import pandas as pd
import numpy as np
import seaborn as sns

#ファイルの読み込み
titanic_df = pd.read_csv('./titanic_train.csv')![ロジスティック回帰-1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/526744/d715856d-4e56-92ec-9858-46e91ebf1dd6.png)


#不要データの削除
titanic_df.drop(['PassengerId', 'Name', 'Ticket', 'Cabin'], axis=1, inplace=True)

data1 = titanic_df.loc[:, ["Fare"]].values
label1 =  titanic_df.loc[:, ["Survived"]].values

from sklearn.linear_model import LogisticRegression
model = LogisticRegression()
model.fit(data1, label1)

w_0 = model.intercept_[0]
w_1 = model.coef_[0,0]

def sigmoid(x, w_0, w_1):
    return 1 / (1+np.exp(-(w_1*x+w_0)))

x_range = np.linspace(-1, 500, 3000)

plt.figure(figsize=(9,5))
plt.plot(data1,np.zeros(len(data1)), 'o')
plt.plot(data1, model.predict_proba(data1), 'o')
plt.plot(x_range, sigmoid(x_range, w_0, w_1), '-')
```

![ロジスティック回帰-1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2437549/e34fcb9d-a63e-af75-2b4e-dc9e8e54d5d6.png)

この推定からは、80辺りが生死の分かれ目に見える。

続いて、年齢と性別による予測。

```python
titanic_df['Gender'] = titanic_df['Sex'].map({'female': 0, 'male': 1}).astype(int)

data2 = titanic_df.loc[:, ["Age","Gender"]].values
label2 = titanic_df.loc[:, ["Survived"]].values

from sklearn.linear_model import LogisticRegression
model=LogisticRegression()
model.fit(data2, label2)

model.predict([[30,1]])
```
このモデルでは、年齢が30歳で男の人は"死"（推定結果が0）と判定された。（課題）