# 机器学习:机器是怎么从数据里学出规则的

一、传统编程:把规则写进去

学习之前,我们来看 传统编程 是怎么运行的

这也被称为:硬编码, 程序员把规则写进去,机器按规则执行

但是,如果规则太过复杂,复杂到程序员自己都说不清楚了,怎么办?

比如:你来形容 鸟

  • 鸟有两条腿,坤也两条腿
  • 鸟嘴巴是尖的,坤也是尖的
  • 鸟有两翅膀,坤也是两翅膀

试图一直用规则穷举下去,会发现永远写不完,我们为什么能一眼看出来?只是我们见得多了,靠直觉,而不是靠规则

所以机器学习的核心思路:让机器自己从数据里 总结规则

一张图看清区别

二、监督学习:从数据里总结规律

学习也分多种,其中 监督学习 是最常用的

可能不太理解,画个图辅助一下

然后算法反复去看 数据 和 答案,不断调整自己内部参数,直到对大多数样本都能猜对为止,这个过程叫 迭代

每次猜错就微调一次,这个叫做 最小化误差

到这里看一下基本流程

那么机器是如何知道自己猜错了,并且往哪个方向调整的?

首先

答案是一开始就已经放在数据里面,在训练的时候,机器自动拿自己预测的去对比答案

其次,出现误差的处理步骤:

  1. 算出当前误差
  2. 算出误差对每个参数的斜率
  3. 朝正确答案方向微调参数
  4. 重复,直到答案正确

这个过程,叫做 梯度下降

为什么每次都是 微调 ?因为调太多,可能直接跳过 答案

那如果这个 微调 调的特别小,模型最后能训练好吗?

理论来说,可以,但是会导致训练时间、算力、电力等等消耗量极大,并且可能永远训练不完

三、SVM:找分类边界

假设你要把两类东西分开

你需要画一条线,把两类东西给分开

问题是,分开的线可以有无数条,如何去选择最好的那一条?

简单来说:你需要找到一条距离两边差不多相同的线

  • margin:间距,也叫缓冲带
  • 支撑向量:在 缓冲带 边缘的点, 决策边界 的位置,完全由这几个点决定

那如果出现下面这种,混在一起,根本画不出一条直线的怎么办

markdown 复制代码
*  。 *  。 *
。 *  。 *  。
*  。 *  。 *

四、核函数:把不可分的问题搬到高维

核函数:把数据搬到高维空间的函数

一维困境:

用二维解决:

二维混乱时,就用三维解决

以上面的二维举例,把 * 的 z 轴提高,就好了

五、交互模式与 Anaconda

首先,现在用的是 Python 交互模式,为什么会是 Python ?

之前做 数据分析 主要用的是 Matlab 和 R,转折点在 2000 年

对比之前普通写程序的方式

普通写程序:

scss 复制代码
写完这个文件(可能100行代码)  ->  运行(一次性)  -> 看结果(是否正确)

如果出错,也不知道是哪行错了,重新跑

交互模式:

shell 复制代码
输入一行 -> 立马看到结果 -> 再输入下一行

>>> x = 5
>>> x * 3
15
>>>

三个实用特性:

  1. 输变量名能直接看值,不需要print()
  2. 逐行调试,随时检查中间结果
  3. 上下键调出历史命令

Anaconda:解决版本冲突

Anaconda:简单来说,解决版本冲突的,使环境各自独立,互不干扰

css 复制代码
Anaconda
	环境A(Python 3.8 + sklearn 0.24)  ← 项目A用这个
    环境B(Python 3.11 + sklearn 1.3)  ← 项目B用这个
    环境C(Python 3.9 + tensorflow)    ← 深度学习用这个

六、数据集从哪来

一直在说数据集,那数据集怎么来的?数据长什么样?

1990年,NIST 收集了大量手写数据用于邮政编码识别,邮局需要机器自动读取信封上的数字,我们用的 digits 数据集就是它的精简版,1797张图,每张 8 x 8 像素

一张 8 x 8 的手写 0,

0 = 白 16 = 黑

画出来之后

数据的结构

用 train_test_split() 自动完成切分 训练集 和 测试集

为什么要切分 训练集 和 测试集 ?

训练集就像练习题,而测试集则是考试,如果你那测试集训练,就像提前把考试卷子做了很多遍,再去考. 这不就学会了,这叫背答案,这个背答案也被叫做 过拟合

那么问题来了, train_test_split()切分的时候,是随机切还是顺序切?

这里有个知识点补充一下,无论是随机切还是顺序切,图都不会重复,不存在训练集里面出现测试集的题目

如果按顺序切,假设数据集是按顺序排列的,最终切出来的

csharp 复制代码
[1,2,3,4,5,6,7,8,9,10]

那么他只训练前面的 1 - 8 ,后面的 9,10 则不会抽到,测试时,完全没见过 9 ,10,所以测试分数会比较低

按照随机切,最终切出来

csharp 复制代码
[1,3,5,7,9,2,4,6,8,10]

它就能训练到所有的数据,测试分数才有意义

reshape:把一维数据还原成二维图像

训练之前,我们要先亲自确认,标签的答案和图像长得是否一样

机器存储数据的方式为:

css 复制代码
digits.data[0] = [0,0,5,13 ...]共64个数

但这是一维的,图片是二维的,一维我们无法去判断,这时就需要 reshape

reshape(8,8)

ini 复制代码
第一行: [0,0,5 ... ,0]共八个数
...
第八行: [0,0,6 ... ,0] 

8 x 8 = 64

imshow():把数字变成颜色

  • 0 -> 白
  • 8 -> 灰
  • 16 -> 黑

用代码展示:

text 复制代码
//选索引
index = 100
//取出数据
image = digits.data[100]
label = digits.target[100]
//折叠,展示
image_2d = image.reshape(8,8)
plt.imshow(image_2d)
plt.title(f"标签:{label}")
plt.show()

而且不能只看一看,要多看几张图,这也叫做 探索性数据分析(EDA),目的是 提前预判模型会在哪里出错

训练流程

总结一下上面的流程

第一步:导入工具

text 复制代码
from sklearn.datasets import load_digits
from sklearn.model_selection import train_test_split
from sklearn.svm import SVC
from sklearn.metrics import accuracy_score
  • load_digits 数据集
  • train_test_split 切分工具
  • SVC SVM分类工具
  • accuracy_score 评分工具

第二步:加载数据并切分

ini 复制代码
digits = load_digits()

X_train, X_test, y_train, y_test = train_test_split(
   digits.data, digits.target
)

切分后:

  • x_train 1300张图
  • y_train 1300 对应标签
  • x_test 450张图
  • y_test 450对应标签

第三步:创建模型并训练

scss 复制代码
model = SVC()
model.fit(X_train,y_train)

第四步:预测并评估

scss 复制代码
y_pred = model.predict(X_test)
print(accuracy_score(y_test, y_pred))

predict():经过 SVM 决策函数,输出的结果

makefile 复制代码
输入:[0,0,4,5,9...] 一张没见过的图
经过SVM决策函数
输出:"1"

accuracy_score:判断准确率

ini 复制代码
y_pred = [1,2,3,4,5,...] 模型猜的
y_test = [1,2,3,4,6,...] 正确答案

准确率 = 猜对的数量 / 总数 = 4 / 5 ≈ 0.8

上面的流程简单来说,就如图

这也是监督学习的通用骨架, 换掉 SVC(),填入其他算法,其余步骤也完全不用变

七、交叉验证:看模型稳不稳

核心思路:杜绝偶然事件,采取考多次,取平均

scss 复制代码
from sklearn.model_selection import cross_val_score

model = SVC()
scores = cross_val_score(model, digits.data, digits.target, cv=3)

print(scores) #[0.96, 0.98, 0.97]
print(scores.mean())  #0.97
  • cv 就是测试多少次
  • scores 代表多次测试出来各自的准确度
  • scores.mean() 代表各自准确度的平均值

如何去判断模型是否有问题,其中一个方法就是看测试数据

ini 复制代码
情况1:
scores = [0.97,0.98,0.99]
mean = 0.97 波动小,稳定

情况2:
scores = [0.60, 0.98, 0.95]
mean = 0.84 波动大,不稳定

总结

最后,如果只用一句话去理解机器学习,那就是:机器学习不是把规则一条条写死,而是让机器从数据里自己总结规律。

前面讲到的监督学习、梯度下降、SVM、核函数、交互模式、Anaconda、数据集、reshape 和交叉验证,其实都在回答同一个问题:怎么让模型更容易学、学得更稳,也更方便验证结果。

所以这章真正想传达的,不是某一个具体算法,而是机器学习的基本思路:先用数据喂给模型,再用误差去调整模型,最后用测试和交叉验证确认它到底学得怎么样。

相关推荐
饼干哥哥6 小时前
用AI全自动剪辑,日更 100条爆款视频——HyperFrames、Remotion、Git使用入门
人工智能·机器学习·ai编程
魏祖潇1 天前
我在飞书里养了个“分身”——私聊喊它办事,群里 @ 它干活,还能替我传话
人工智能·机器学习
哥布林学者7 天前
深度学习进阶(三十一)FlashAttention:IO 感知的精确注意力
机器学习·ai
通信小呆呆9 天前
当算法有了“五感”:多模态数据融合如何向人体感官协同学习?
人工智能·学习·算法·机器学习·机器人
xiao5kou4chang6kai49 天前
MATLAB机器学习、深度学习--从数据预处理到模型训练
深度学习·机器学习·matlab·数据预处理