文章目錄
第一部分:線性問題部分
import numpy as np
import matplotlib.pyplot as plt
%matplotlib inline
from sklearn.svm import SVC
import sklearn.datasets as datasets
1.1、生成隨機散點
# 生成一序列的點,默認n_samples=100,中心centers=2
X,y = datasets.make_blobs(n_samples=50,centers=2)
X.shape #結果爲(50, 2)
(1)查看X:
array([[10.19536929, -6.98207178],
[ 8.17673749, 1.04956597],
[ 7.11262117, 1.93567167],
[ 7.69201225, 2.6067144 ],
... ...
[ 9.7840538 , -5.97999583],
[ 8.22020804, 2.17484189],
[ 9.52555314, -7.75041062]])
(2)查看y:
array([0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 1, 1, 1, 0, 1, 1,
0, 0, 1, 0, 1, 0, 0, 1, 0, 0, 0, 1, 0, 0, 1, 0, 1, 1, 0, 0, 0, 1,
1, 0, 1, 1, 1, 1])
(3)畫散點圖:
#導入顏色
from matplotlib.colors import ListedColormap
color = ListedColormap([(1.0,0,0),(0,1.0,0)]) #紅色和綠色
X,y = datasets.make_blobs(n_samples=100,centers=2) #生成100個散點,2箇中心
plt.scatter(X[:,0],X[:,1],c = y,cmap = color) #散點圖可視化
1.2、建模
- 現在需要畫一條線把紅色和綠色的點分隔開,先進行數據的學習,再確定這條線的截距和係數
- 線性迴歸方程:
f(X)
=w1*x1 + w2*x2 + b
=x*w + b_
w = -w1/w2
b_ = -b/w2
svc = SVC(kernel='linear') #線性模型
svc.fit(X,y) #訓練模型
(1)使用 svc.coef_
獲取該線的係數:
w1,w2 = svc.coef_[0]
print (svc.coef_)
print (w1)
print (w2)
[[ 0.14604164 -0.69448342]]
0.146041643741726
-0.6944834196263103
(2)使用 svc.intercept_
獲取截距:
b = svc.intercept_
b
array([-3.18503123])
(3)迴歸線 f(X)
= w1*x1 + w2*x2 + b
= x*w + b_
推導:
(4)支持向量點直線:
- 支持向量點和分隔線平行,所以它們的斜率相等,當
f(x) = -1
和f(x) = 1
時,可以求出通過支持向量點的兩條直線; - 公式:
f(X)
=x*w + b1
和f(X)
=x*w + b2
- 推導過程:
1 = w1*x + w2*y + b
-1 = w1*x + w2*y + b
b1 = -(b + 1)/w2
b2 = -(b - 1)/w2
1.3、數據可視化
plt.scatter(X[:,0],X[:,1],c = y,cmap = plt.cm.PuOr) #原數據散點圖
x = np.linspace(5,12,50) #這裏的x值可以根據上面隨機散點設置
#繪製迴歸線
plt.plot(x,x*w + b_)
#繪製支持向量點
plt.scatter(support_vectors_[:,0],support_vectors_[:,1],color = 'purple',s = 300,alpha = 0.3)
# 繪製兩個支持向量點的直線
plt.plot(x,x*w + b1,ls = '--')
plt.plot(x,x*w + b2 ,ls = '--')
第二部分:非線性問題部分
import numpy as np
import matplotlib.pyplot as plt
%matplotlib inline
from sklearn.svm import SVC
2.1、隨機生成數據
X = np.random.randn(300,2) #生成300行2列的隨機矩陣
X.shape #結果爲(300,2)
plt.scatter(X[:,0],X[:,1]) #繪製散點圖
2.2、屬性組合分隔數據
- 可以通過數據的屬性組合產生新的特徵將數據區分出來,如通過它們的象限區分出來它們的屬性;
- 第Ⅰ、Ⅲ象限相乘爲正, 第Ⅱ、Ⅵ 相乘爲負。
# 屬性組合
# x3 = x1*x2
x3 = X[:,0] * X[:,1]
y = x3 >=0
#繪製散點圖
plt.scatter(X[:,0],X[:,1],c = y)
2.3、建模
# rbf 徑向基 高斯分佈數據處理
svc = SVC(kernel='rbf')
svc.fit(X,y) #訓練學習模型
2.3.1、測試範圍
x1 = np.linspace(-3,3,100)
y1 = np.linspace(-3,3,100)
X1,Y1 = np.meshgrid(x1,y1) #網格交叉,X1和Y1都是(100, 100)的矩陣了
#散點圖可視化
X_test = np.concatenate([X1.reshape(-1,1),Y1.reshape(-1,1)],axis=-1) #concatenate數據集聯
plt.scatter(X_test[:,0],X_test[:,1])
結果分析: 這是結果是正確的。因爲這上面有10000個點,分佈太多密集。
2.3.2、預測分隔
y_ = svc.predict(X_test) #預測測試
plt.figure(figsize=(5,5)) #設置圖像比例
plt.scatter(X_test[:,0],X_test[:,1],c = y_) #作散點圖
2.3.3、求它的距離
d_ = svc.decision_function(X_test)
d_
array([0.1093417 , 0.11477454, 0.12075184, ..., 0.16816356, 0.16268286,
0.15759471])
繪製輪廓面:
plt.figure(figsize=(5,5))
plt.contourf(X1,Y1,d_.reshape(100,100)) #輪廓面contourf
結果分析: 顏色越深,說明值越大,離分離超平面越遠。
第三部分:SVM迴歸實戰
3.1、準備數據
import numpy as np
import matplotlib.pyplot as plt
%matplotlib inline
from sklearn.svm import SVR
X = np.linspace(0,3*np.pi,50).reshape(-1,1) #轉化爲二維數據
y = np.sin(X)
plt.scatter(X,y) #畫散點圖
3.2、建立模型
svr_linear = SVR(kernel='linear') #線性
svr_rbf = SVR(kernel='rbf') #高斯
svr_poly = SVR(kernel='poly') #多項式
svr_linear.fit(X,y)
svr_rbf.fit(X,y)
svr_poly.fit(X,y)
3.3、預測數據及可視化
# 生成測試集
X_test = np.linspace(0, 3*np.pi, 128).reshape(-1,1)
#在模型中預測目標
y1 = svr_linear.predict(X_test) #線性
y2 = svr_rbf.predict(X_test) #高斯
y3 = svr_poly.predict(X_test) #多項式
#可視化
plt.scatter(X,y) #原散點圖
plt.plot(X_test,y1)
plt.plot(X_test,y2)
plt.plot(X_test,y3)
plt.legend(['Linear','Rbf','poly']) #顯示標籤