机器学习笔记 1 —— Perceptron

1. 感知机

模型
感知机是根据输入实例的特征向量 x x x对其进行二类分类的线性分类模型:

f ( x ) = sign ⁡ ( w ⋅ x + b ) f(x)=\operatorname{sign}(w \cdot x+b) f(x)=sign(wx+b)

感知机模型对应于输入空间(特征空间)中的分离超平面 w ⋅ x + b = 0 w \cdot x+b=0 wx+b=0


策略
感知机学习的策略是极小化损失函数:

min ⁡ w , b L ( w , b ) = − ∑ x i ∈ M y i ( w ⋅ x i + b ) \min _{w, b} L(w, b)=-\sum_{x_{i} \in M} y_{i}\left(w \cdot x_{i}+b\right) w,bminL(w,b)=xiMyi(wxi+b)

损失函数对应于误分类点到分离超平面的总距离。

方法
  感知机学习算法是基于 随机梯度下降法 的对损失函数的最优化算法,有原始形式和对偶形式。当训练数据集线性可分时,感知机学习算法是收敛的。当训练数据集线性可分时,感知机学习算法存在无穷多个解,其解由于不同的初值或不同的迭代顺序而可能有所不同。



2. 二分类模型

模型
f ( x ) = s i g n ( w ⋅ x + b ) f(x) = sign(w\cdot x + b) f(x)=sign(wx+b)

sign ⁡ ( x ) = { + 1 , x ⩾ 0 − 1 , x < 0 \operatorname{sign}(x)=\left\{\begin{array}{ll}{+1,} & {x \geqslant 0} \\ {-1,} & {x<0}\end{array}\right. sign(x)={+1,1,x0x<0


策略
给定训练集:

T = { ( x 1 , y 1 ) , ( x 2 , y 2 ) , ⋯   , ( x N , y N ) } T=\left\{\left(x_{1}, y_{1}\right),\left(x_{2}, y_{2}\right), \cdots,\left(x_{N}, y_{N}\right)\right\} T={(x1,y1),(x2,y2),,(xN,yN)}

定义感知机的损失函数 L ( w , b ) L(w, b) L(w,b)

L ( w , b ) = − ∑ x i ∈ M y i ( w ⋅ x i + b ) L(w, b)=-\sum_{x_{i} \in M} y_{i}\left(w \cdot x_{i}+b\right) L(w,b)=xiMyi(wxi+b)


算法

随即梯度下降法 Stochastic Gradient Descent

随机抽取一个误分类点使其梯度下降:

{ w = w + η y i x i b = b + η y i \left\{\begin{array}{ll}{w = w + \eta y_{i}x_{i}} \\ {b = b + \eta y_{i}}\end{array}\right. {w=w+ηyixib=b+ηyi

当实例点被误分类,即位于分离超平面的错误侧,则调整 w w w, b b b的值,使分离超平面向该无分类点的一侧移动,直至误分类点被正确分类



3. 感知机的实现

首先把我们需要的库导入;

import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
from sklearn.datasets import load_iris

3.1 数据集预处理

可以使用 sklearn 库中的 iris 鸢尾花数据集,使用方法如下:

iris = load_iris()
df = pd.DataFrame(iris.data, columns=iris.feature_names)
df['label'] = iris.target	# 添加一列
df.columns = [
	'sepal length',
	'sepal width',
	'petal length',
	'petal width',
	'label'
]
print(df)
print(df.shape)	# (150, 5)
# 统计 label 的每种值的数量
print(df.label.value_counts())

# 绘制散点图
plt.scatter(df[:50]['sepal length'], 
	df[:50]['sepal width'], label='0')
plt.scatter(df[50:100]['sepal length'], 
	df[50:100]['sepal width'], label='1')
plt.scatter(df[100:150]['sepal length'],
	df[100:150]['sepal width'], label='2')
plt.xlabel('sepal length')
plt.ylabel('sepal width')
plt.legend()
plt.show()

输出结果为:

     sepal length  sepal width  petal length  petal width  label
0             5.1          3.5           1.4          0.2      0
1             4.9          3.0           1.4          0.2      0
2             4.7          3.2           1.3          0.2      0
..            ...          ...           ...          ...    ...
147           6.5          3.0           5.2          2.0      2
148           6.2          3.4           5.4          2.3      2
149           5.9          3.0           5.1          1.8      2
[150 rows x 5 columns]

(150, 5)

0    50
1    50
2    50
Name: label, dtype: int64

得到的结果如图:

利用这些数据我们可以得到训练数据的 X 和 y:

data = np.array(df.iloc[:100, [0, 1, -1]])
X, y = data[:, :-1], data[:, [-1]]
y = np.array([1 if i == 1 else -1 for i in y])

此时,鸢尾花样本有 100 个,每个样本有花瓣长度和花瓣宽度两个特征,分类的类别有 2 中,用 +1 和 -1 表示。


3.2 构建模型

根据上面的理论知识,可以利用随机梯度下降算法构建二类分类模型,其中 fit() 为拟合函数:

class Model:
	def __init__(self):
		self.W = np.zeros(X.shape[1], dtype=np.float32)
		self.b = 0
		self.lr = 0.1

	def sign(self, X, W, b):
		y = np.dot(X, W) + b
		return 1 if y > 0 else -1

	def fit(self, X_train, y_train):
		success = False
		while not success:
			wrong_count = 0
			for i in range(len(X_train)):
				X = X_train[i]
				y = y_train[i]
				if y * self.sign(X, self.W, self.b) < 0:
					self.W += self.lr * np.dot(X, y)
					self.b += y * self.lr
					wrong_count += 1
			if wrong_count == 0:
				success = True
		return 'Perception Model'

	def score(self):
		pass

3.3 预测分类

使用先前的模型先对数据训练,将分类结果绘制出来:

perception = Model()
res = perception.fit(X, y)
print(res)	# Perception Model


x_ = np.linspace(4, 7, 10)
y_ = -(perception.W[0] * x_ + perception.b) / perception.W[1]
plt.plot(x_, y_)

plt.plot(data[:50, 0], data[:50, 1], 'bo', color='blue', label='0')
plt.plot(data[50:100, 0], data[50:100, 1], 'bo', color='orange', label='1')
plt.xlabel('sepal length')
plt.ylabel('sepal width')
plt.legend()
plt.show()

结果如下:



4. sklearn

sklearn 的 Perception 模型(点击蓝色的字查看参数)为基于随机梯度下降 SGD 的分类模型:

下面使用 sklearn 的 Perceptron 模型:

from sklearn.linear_model import Perceptron

clf = Perceptron(
	fit_intercept=True,
	max_iter=1000,
	shuffle=True,
	tol=None)
clf.fit(X, y)

W = clf.coef_[0]
b = clf.intercept_

x_ = np.linspace(4, 7, 10)
y_ = -(W[0] * x_ + b) / W[1]
plt.plot(x_, y_)

plt.plot(data[:50, 0], data[:50, 1], 'bo', color='blue', label='0')
plt.plot(data[50:100, 0], data[50:100, 1], 'bo', color='orange', label='1')
plt.xlabel('sepal length')
plt.ylabel('sepal width')
plt.legend()
plt.show()

其中构造函数的参数 fit_intercept 代表计算 b,max_iter 代表最大训练次数,shuffle 为 True 代表每次训练后清洗数据,表两次训练后误差下降的量小于 tol 时停止训练;

训练好的模型的参数存储在 coef_intercept_

结果如下:


参考内容:

  1. 李航机器学习
  2. lihang-code-master
  3. https://scikit-learn.org/
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值