Skip to main content

机器学习 - 周志华

v6UAtN

本书作为机器学习领域的入门教材,在内容上尽可能涵盖机器学习基础知识的各方面,包括决策树、神经网络、支持向量机、贝叶斯分类器、集成学习、聚类等经典方法。

关于作者

周志华 是机器学习领域的权威专家:

  • 南京大学教授:长期从事机器学习和人工智能研究
  • ACM/AAAI/IEEE Fellow:国际人工智能学会会士
  • 教育部长江学者:国家级人才计划特聘教授
  • 《机器学习》作者:该书被誉为中国机器学习领域的"圣经"

周志华教授因其在机器学习领域的杰出贡献,被同行亲切地称为"西瓜教授"(因其教材中常用"挑西瓜"举例)。

核心内容

1. 模型评估与选择

# 留出法 (Hold-out)
from sklearn.model_selection import train_test_split

X_train, X_test, y_train, y_test = train_test_split(
X, y, test_size=0.3, random_state=42, stratify=y
)

# 交叉验证 (Cross-Validation)
from sklearn.model_selection import cross_val_score, KFold

kf = KFold(n_splits=10, shuffle=True, random_state=42)
scores = cross_val_score(model, X, y, cv=kf, scoring='accuracy')
print(f"平均准确率:{scores.mean():.3f}")

# 留一法 (Leave-One-Out)
from sklearn.model_selection import LeaveOneOut

loo = LeaveOneOut()
scores = cross_val_score(model, X, y, cv=loo)

# 性能度量指标
from sklearn.metrics import (
accuracy_score, precision_score, recall_score, f1_score,
roc_auc_score, confusion_matrix, classification_report
)

# 查准率 (Precision)、查全率 (Recall)、F1 分数
precision = precision_score(y_true, y_pred)
recall = recall_score(y_true, y_pred)
f1 = f1_score(y_true, y_pred)

# ROC 曲线与 AUC
from sklearn.metrics import roc_curve, auc
fpr, tpr, _ = roc_curve(y_true, y_score)
roc_auc = auc(fpr, tpr)

2. 线性模型

from sklearn.linear_model import LinearRegression, Ridge, Lasso, LogisticRegression

# 线性回归
# 最小二乘法:w* = (X^T X)^(-1) X^T y

lin_reg = LinearRegression()
lin_reg.fit(X_train, y_train)

# 正则化线性回归
# 岭回归 (Ridge): L2 正则化
ridge = Ridge(alpha=1.0)
ridge.fit(X_train, y_train)

# Lasso: L1 正则化 (可进行特征选择)
lasso = Lasso(alpha=0.1)
lasso.fit(X_train, y_train)

# 逻辑回归 (对数几率回归)
# P(y=1|x) = 1 / (1 + exp(-w^T x))

log_reg = LogisticRegression(
penalty='l2',
C=1.0,
solver='lbfgs',
multi_class='auto'
)
log_reg.fit(X_train, y_train)

# 广义线性模型
# 联系函数 g(·): 将线性模型扩展到指数族分布

3. 决策树

from sklearn.tree import DecisionTreeClassifier
from sklearn.tree import export_graphviz
import graphviz

# 决策树三要素
# 1. 特征选择:信息增益、信息增益比、基尼指数
# 2. 决策树生成:递归构建
# 3. 决策树剪枝:预剪枝、后剪枝

dt = DecisionTreeClassifier(
criterion='gini', # 或 'entropy' (信息增益)
max_depth=5, # 最大深度 (预剪枝)
min_samples_split=10, # 内部节点分裂所需最小样本数
min_samples_leaf=5, # 叶节点最小样本数
max_features='sqrt', # 最大特征数
random_state=42
)
dt.fit(X_train, y_train)

# 特征重要性
importances = dt.feature_importances_

# 可视化
dot_data = export_graphviz(
dt,
out_file=None,
feature_names=feature_names,
class_names=class_names,
filled=True,
rounded=True
)
graph = graphviz.Source(dot_data)
graph.render('decision_tree')

# ID3, C4.5, CART 算法对比
# ID3: 信息增益,多值特征偏好
# C4.5: 信息增益比,克服多值偏好
# CART: 基尼指数,二叉树

4. 支持向量机

from sklearn.svm import SVC, SVR
from sklearn.preprocessing import StandardScaler
from sklearn.pipeline import make_pipeline

# 硬间隔 SVM:数据线性可分
# 软间隔 SVM:允许部分样本不满足约束

# 核技巧:将低维非线性映射到高维线性可分
# 常用核函数:
# - 线性核:K(x, z) = x^T z
# - 多项式核:K(x, z) = (γ x^T z + r)^d
# - RBF 核:K(x, z) = exp(-γ||x-z||²)
# - Sigmoid 核:K(x, z) = tanh(γ x^T z + r)

svm_clf = make_pipeline(
StandardScaler(),
SVC(kernel='rbf', C=1.0, gamma='scale')
)
svm_clf.fit(X_train, y_train)

# 支持向量回归 (SVR)
svm_reg = make_pipeline(
StandardScaler(),
SVR(kernel='rbf', C=1.0, epsilon=0.1)
)
svm_reg.fit(X_train, y_train)

# 支持向量:距离超平面最近的样本
# 只有支持向量影响决策边界

5. 贝叶斯分类器

from sklearn.naive_bayes import GaussianNB, MultinomialNB, BernoulliNB

# 贝叶斯定理
# P(A|B) = P(B|A) * P(A) / P(B)

# 朴素贝叶斯假设:特征条件独立
# P(y|x) ∝ P(y) * Π P(xi|y)

# 高斯朴素贝叶斯 (连续特征)
gnb = GaussianNB()
gnb.fit(X_train, y_train)

# 多项式朴素贝叶斯 (离散特征,如文本分类)
mnb = MultinomialNB(alpha=1.0) # 拉普拉斯平滑
mnb.fit(X_train, y_train)

# 伯努利朴素贝叶斯 (二元特征)
bnb = BernoulliNB(alpha=1.0)
bnb.fit(X_train, y_train)

# 半朴素贝叶斯
# 独依赖估计 (ODE): 每个特征依赖一个其他特征
# TAN: 树形增强朴素贝叶斯

6. 集成学习

from sklearn.ensemble import (
RandomForestClassifier,
GradientBoostingClassifier,
AdaBoostClassifier,
VotingClassifier,
StackingClassifier
)

# Bagging: Bootstrap Aggregating
# 并行训练多个基学习器,投票或平均
# 代表:随机森林

rf = RandomForestClassifier(
n_estimators=100,
max_depth=10,
min_samples_split=5,
n_jobs=-1,
random_state=42
)
rf.fit(X_train, y_train)

# Boosting: 串行训练,后续模型关注前序模型的错误
# 代表:AdaBoost, GBDT, XGBoost, LightGBM

ada = AdaBoostClassifier(
n_estimators=50,
learning_rate=1.0,
random_state=42
)
ada.fit(X_train, y_train)

gbdt = GradientBoostingClassifier(
n_estimators=100,
learning_rate=0.1,
max_depth=3,
random_state=42
)
gbdt.fit(X_train, y_train)

# Voting: 多个模型投票
voting = VotingClassifier(
estimators=[
('rf', rf),
('gbdt', gbdt),
('svm', svm_clf)
],
voting='soft' # 或 'hard'
)
voting.fit(X_train, y_train)

# Stacking: 用元学习器组合基学习器
stacking = StackingClassifier(
estimators=[
('rf', rf),
('gbdt', gbdt)
],
final_estimator=LogisticRegression()
)

7. 聚类

from sklearn.cluster import KMeans, DBSCAN, AgglomerativeClustering
from sklearn.metrics import silhouette_score, davies_bouldin_score

# KMeans: 基于原型的聚类
# 目标:最小化簇内平方误差

kmeans = KMeans(
n_clusters=5,
init='k-means++', # 优化初始中心选择
n_init=10,
max_iter=300,
random_state=42
)
labels = kmeans.fit_predict(X)

# 肘部法则选择 K 值
inertias = []
for k in range(1, 11):
kmeans = KMeans(n_clusters=k, random_state=42)
kmeans.fit(X)
inertias.append(kmeans.inertia_)

# DBSCAN: 基于密度的聚类
# 可发现任意形状簇,识别噪声点
dbscan = DBSCAN(
eps=0.5, # 邻域半径
min_samples=5 # 核心点最少样本数
)
labels = dbscan.fit_predict(X)

# 层次聚类
hc = AgglomerativeClustering(
n_clusters=5,
linkage='ward' # 或 'complete', 'average', 'single'
)
labels = hc.fit_predict(X)

# 聚类评估 (无监督)
silhouette = silhouette_score(X, labels)
db_score = davies_bouldin_score(X, labels)

8. 神经网络基础

import tensorflow as tf
from tensorflow import keras

# M-P 神经元模型
# y = f(Σ wi*xi + b)
# 激活函数:ReLU, Sigmoid, Tanh

# 反向传播 (BP) 算法
# 链式法则计算梯度
# 随机梯度下降 (SGD) 更新权重

model = keras.Sequential([
keras.layers.Dense(64, activation='relu', input_shape=(n_features,)),
keras.layers.Dropout(0.3),
keras.layers.Dense(32, activation='relu'),
keras.layers.Dropout(0.3),
keras.layers.Dense(n_classes, activation='softmax')
])

model.compile(
optimizer=keras.optimizers.SGD(learning_rate=0.01, momentum=0.9),
loss='sparse_categorical_crossentropy',
metrics=['accuracy']
)

# 过拟合缓解
# 1. 正则化 (L1, L2)
# 2. Dropout
# 3. 早停 (Early Stopping)
# 4. 数据增强

# 优化器
# - SGD: 随机梯度下降
# - Momentum: 动量法
# - Adam: 自适应学习率

经典摘录

机器学习是研究如何通过计算的手段,利用经验来改善系统自身的性能的学科。

数据决定上限,算法只是逼近这个上限。

没有免费的午餐定理 (NFL): 对所有可能的问题,所有算法的期望性能相同。

奥卡姆剃刀:若有多个假设与观察一致,则选择最简单的那个。

集成学习的核心思想:三个臭皮匠,顶个诸葛亮。

读书心得

周志华教授的《机器学习》(西瓜书)是中国机器学习领域的经典教材。这本书以其系统性和严谨性著称,涵盖了机器学习的各个主要分支。

书中对我影响最深的是理论深度与实践广度的平衡。每个章节都从问题定义出发,介绍算法原理,给出数学推导,最后讨论实现细节。这种讲解方式帮助读者建立对算法的深入理解。

集成学习部分的讲解非常精彩。从 Bagging 到 Boosting,从随机森林到 GBDT,书中清晰地展示了"集思广益"的思想。这部分的理论分析和实践经验都很有价值。

支持向量机部分展示了统计学习理论的优美。最大间隔、核技巧、对偶问题等概念,虽然数学上有一定难度,但理解后会对机器学习的理论基础有更深的认识。

这本书的挑战在于数学要求较高。线性代数、概率论、优化理论的基础知识是必要的。但对于想要深入理解机器学习的读者来说,这些投入是值得的。

建议的学习方式:

  1. 配合吴恩达的机器学习课程
  2. 动手实现书中的算法
  3. 使用 scikit-learn 验证理解
  4. 在真实数据集上实践

《机器学习》是一本值得反复阅读的经典。每一次重读,都会有新的收获。