本文目录导读:

我来介绍如何使用Scikit-learn进行SVM分类的完整案例。
基本SVM分类案例
使用鸢尾花数据集
# 导入所需库
import numpy as np
import matplotlib.pyplot as plt
from sklearn import datasets
from sklearn.model_selection import train_test_split
from sklearn.preprocessing import StandardScaler
from sklearn.svm import SVC
from sklearn.metrics import classification_report, confusion_matrix, accuracy_score
import seaborn as sns
# 1. 加载数据
iris = datasets.load_iris()
X = iris.data[:, :2] # 只使用前两个特征便于可视化
y = iris.target
# 2. 划分训练集和测试集
X_train, X_test, y_train, y_test = train_test_split(
X, y, test_size=0.3, random_state=42
)
# 3. 数据标准化(SVM对特征尺度敏感)
scaler = StandardScaler()
X_train_scaled = scaler.fit_transform(X_train)
X_test_scaled = scaler.transform(X_test)
# 4. 创建并训练SVM模型
svm_classifier = SVC(kernel='rbf', C=1.0, gamma='scale', random_state=42)
svm_classifier.fit(X_train_scaled, y_train)
# 5. 预测
y_pred = svm_classifier.predict(X_test_scaled)
# 6. 评估模型
print("准确率:", accuracy_score(y_test, y_pred))
print("\n分类报告:")
print(classification_report(y_test, y_pred))
# 7. 混淆矩阵
cm = confusion_matrix(y_test, y_pred)
plt.figure(figsize=(8, 6))
sns.heatmap(cm, annot=True, fmt='d', cmap='Blues')'混淆矩阵')
plt.ylabel('真实值')
plt.xlabel('预测值')
plt.show()
完整的SVM分类案例(包含可视化)
import numpy as np
import matplotlib.pyplot as plt
from sklearn import datasets
from sklearn.svm import SVC
from sklearn.model_selection import train_test_split
from sklearn.preprocessing import StandardScaler
from matplotlib.colors import ListedColormap
def plot_decision_boundary(X, y, classifier, title):
"""绘制决策边界"""
# 创建网格点
x_min, x_max = X[:, 0].min() - 1, X[:, 0].max() + 1
y_min, y_max = X[:, 1].min() - 1, X[:, 1].max() + 1
xx, yy = np.meshgrid(np.arange(x_min, x_max, 0.02),
np.arange(y_min, y_max, 0.02))
# 预测网格点的类别
Z = classifier.predict(np.c_[xx.ravel(), yy.ravel()])
Z = Z.reshape(xx.shape)
# 绘制
plt.figure(figsize=(10, 8))
plt.contourf(xx, yy, Z, alpha=0.3, cmap=ListedColormap(['#FFAAAA', '#AAFFAA', '#AAAAFF']))
plt.scatter(X[:, 0], X[:, 1], c=y, cmap=ListedColormap(['#FF0000', '#00FF00', '#0000FF']),
edgecolors='black', s=50)
plt.xlabel('特征1')
plt.ylabel('特征2')
plt.title(title)
plt.colorbar()
plt.show()
# 加载数据
iris = datasets.load_iris()
X = iris.data[:, :2] # 只取前两个特征
y = iris.target
# 数据标准化
scaler = StandardScaler()
X_scaled = scaler.fit_transform(X)
# 划分数据
X_train, X_test, y_train, y_test = train_test_split(
X_scaled, y, test_size=0.3, random_state=42
)
# 比较不同核函数
kernels = ['linear', 'rbf', 'poly']
for kernel in kernels:
# 创建模型
svm = SVC(kernel=kernel, C=1.0, gamma='scale', random_state=42)
svm.fit(X_train, y_train)
# 预测和评估
y_pred = svm.predict(X_test)
accuracy = accuracy_score(y_test, y_pred)
print(f"核函数: {kernel}, 准确率: {accuracy:.4f}")
# 绘制决策边界
plot_decision_boundary(X_scaled, y, svm, f'SVM {kernel} 核 - 准确率: {accuracy:.4f}')
参数调优案例
from sklearn.model_selection import GridSearchCV
from sklearn.svm import SVC
from sklearn.datasets import make_classification
import numpy as np
# 生成示例数据
X, y = make_classification(n_samples=200, n_features=20, n_classes=2,
n_informative=2, random_state=42)
# 数据划分
X_train, X_test, y_train, y_test = train_test_split(
X, y, test_size=0.3, random_state=42
)
# 标准化
scaler = StandardScaler()
X_train_scaled = scaler.fit_transform(X_train)
X_test_scaled = scaler.transform(X_test)
# 定义参数网格
param_grid = {
'C': [0.1, 1, 10, 100], # 惩罚参数
'gamma': [0.001, 0.01, 0.1, 1], # RBF核参数
'kernel': ['rbf', 'poly', 'sigmoid'] # 核函数
}
# 网格搜索
grid_search = GridSearchCV(
SVC(random_state=42),
param_grid,
cv=5, # 5折交叉验证
scoring='accuracy',
n_jobs=-1 # 使用所有CPU核
)
# 训练
grid_search.fit(X_train_scaled, y_train)
# 最佳参数
print("最佳参数:", grid_search.best_params_)
print("最佳交叉验证得分:", grid_search.best_score_)
# 使用最佳模型
best_svm = grid_search.best_estimator_
y_pred = best_svm.predict(X_test_scaled)
print("\n测试集准确率:", accuracy_score(y_test, y_pred))
print("\n分类报告:")
print(classification_report(y_test, y_pred))
支持向量机回归 (SVR)
from sklearn.svm import SVR
from sklearn.datasets import make_regression
import numpy as np
# 生成回归数据
X, y = make_regression(n_samples=100, n_features=1, noise=20, random_state=42)
# 划分数据
X_train, X_test, y_train, y_test = train_test_split(
X, y, test_size=0.2, random_state=42
)
# 标准化
scaler_X = StandardScaler()
scaler_y = StandardScaler()
X_train_scaled = scaler_X.fit_transform(X_train)
X_test_scaled = scaler_X.transform(X_test)
y_train_scaled = scaler_y.fit_transform(y_train.reshape(-1, 1)).ravel()
# 创建SVR模型
svr = SVR(kernel='rbf', C=100, gamma=0.1, epsilon=0.1)
svr.fit(X_train_scaled, y_train_scaled)
# 预测
y_pred_scaled = svr.predict(X_test_scaled)
y_pred = scaler_y.inverse_transform(y_pred_scaled.reshape(-1, 1)).ravel()
# 可视化
plt.figure(figsize=(10, 6))
plt.scatter(X_test, y_test, color='blue', label='真实值')
plt.scatter(X_test, y_pred, color='red', label='预测值')
plt.plot(X_test, y_pred, color='green', label='SVR拟合线', alpha=0.5)
plt.xlabel('X')
plt.ylabel('y')'SVR回归结果')
plt.legend()
plt.show()
# 评估
from sklearn.metrics import mean_squared_error, r2_score
mse = mean_squared_error(y_test, y_pred)
r2 = r2_score(y_test, y_pred)
print(f"MSE: {mse:.4f}")
print(f"R2 Score: {r2:.4f}")
实际应用案例:文本分类
from sklearn.feature_extraction.text import TfidfVectorizer
from sklearn.svm import SVC
from sklearn.pipeline import Pipeline
import numpy as np
# 示例文本数据
texts = [
"这部电影太精彩了", "很棒的观影体验", "演员表演非常出色",
"这个故事很无聊", "剧情太差劲了", "不值得看",
"这个产品很好用", "质量非常好", "强烈推荐购买",
"质量太差", "使用体验很糟糕", "不建议购买"
]
labels = [1, 1, 1, 0, 0, 0, 1, 1, 1, 0, 0, 0] # 1:正面, 0:负面
# 创建pipeline
text_clf = Pipeline([
('tfidf', TfidfVectorizer(analyzer='char', ngram_range=(1, 3))),
('clf', SVC(kernel='linear', C=1.0)),
])
# 训练模型
text_clf.fit(texts[:10], labels[:10])
# 预测新文本
new_texts = [
"非常好看的作品",
"这是我看过最差的电影",
"性价比很高"
]
predictions = text_clf.predict(new_texts)
print("预测结果:")
for text, pred in zip(new_texts, predictions):
sentiment = "正面" if pred == 1 else "负面"
print(f"'{text}' -> {sentiment}")
关键参数说明
-
C (惩罚参数): 控制误分类的惩罚力度
- 小C:允许更多误分类,决策边界更平滑
- 大C:严格惩罚误分类,决策边界更复杂
-
kernel (核函数):
- 'linear': 线性核
- 'rbf': 径向基核(最常用)
- 'poly': 多项式核
- 'sigmoid': Sigmoid核
-
gamma (核系数): 影响RBF核的宽度
- 小gamma:决策边界更平滑
- 大gamma:决策边界更复杂
调优建议
- 标准化数据: SVM对特征尺度非常敏感
- 选择合适的核函数: 根据数据特点选择
- 参数调优: 使用GridSearchCV或RandomizedSearchCV
- 特征工程: 良好的特征可以显著提升性能
- 处理不平衡数据: 使用class_weight参数
这些案例涵盖了SVM分类的主要应用场景,你可以根据实际需求进行调整和扩展。