前提・実現したいこと
SVMのアルゴリズムをsklearnを用いずに実装したい。
発生している問題・エラーメッセージ
RuntimeWarning: invalid value encountered in double_scalars self.w0_ = (y[ind] - np.dot(X[ind, :], self.w_)).sum() / ind.sum()
*追加
File "C:\Users\anaconda3\svm_hard.py", line 56, in fit self.w_ = ((a[ind] * y[ind]).reshape(-1, 1) * X[ind, :]).sum(axis = 0) IndexError: arrays used as indices must be of integer (or boolean) type
該当のソースコード
Python
1import numpy as np 2from operator import itemgetter 3 4class SVC: 5 6 def fit(self, X, y, selections = None): 7 a = np.zeros(X.shape[0]) 8 ay = 0 9 ayx = np.zeros(X.shape[1]) 10 yx = y.reshape(-1, 1) * X 11 indices = np.arange(X.shape[0]) 12 13 while True: 14 ydf = y * (1 - np.dot(yx, ayx.T)) 15 iydf = np.c_[indices, ydf] 16 i = int(min(iydf[(y < 0) | (a > 0)], 17 key = itemgetter(1))[0]) 18 j = int(max(iydf[(y < 0) | (a > 0)], 19 key = itemgetter(1))[0]) 20 21 if ydf[i] >= ydf[j]: 22 break 23 24 ay2 = ay - y[i] * a[i] - y[j] * a[j] 25 ayx2 = ayx - y[i] * a[i] * X[i, :] - y[j] * a[j] * X[j, :] 26 ai = ((1 - y[i] * y[j] + y[i] * np.dot(X[i, :] - X[j, :], X[j, :] * ay2 - ayx2)) 27 / ((X[i] - X[j])**2).sum()) 28 29 if ai < 0: 30 ai = 0 31 aj = (-ai * y[i] - ay2) * y[j] 32 33 if aj < 0: 34 aj = 0 35 ai = (-aj * y[j] - ay2) * y[i] 36 37 ay += y[i] * (ai - a[i]) + y[j] * (aj - a[j]) 38 ayx += y[i] * (ai - a[i]) * X[i, :] + y[j] * (aj - a[j]) * X[j, :] 39 40 if ai == a[i]: 41 break 42 43 a[i] = ai 44 a[j] = aj 45 46 self.a_ = a 47 ind = a != 0. 48 self.w_ = ((a[ind] * y[ind]).reshape(-1, 1) * X[ind, :]).sum(axis = 0) 49 self.w0_ = (y[ind] - np.dot(X[ind, :], self.w_)).sum() / ind.sum() 50 51 def predict(self, X): 52 return np.sign(self.w0_ + np.dot(X, self.w_))
Python
1import numpy as np 2import matplotlib.pyplot as plt 3import svm_hard 4 5plt.axes().set_aspect("equal") 6np.random.seed(0) 7X0 = np.random.randn(20, 2) 8X1 = np.random.randn(20, 2) + np.array([5, 5]) 9y = np.array([1] * 20 + [-1] * 20) 10 11X = np.r_[X0, X1] 12model = svm_hard.SVC() 13model.fit(X, y) 14 15plt.scatter(X0[:, 0], X0[:, 1], color = "k", marker = "+") 16plt.scatter(X1[:, 0], X1[:, 1], color = "k", marker = "*") 17 18def f(model, x): 19 return (-model.w0_ - model.w_[0] * x) / model.w_[1] 20 21x1 = -0.2 22x2 = 6 23 24plt.plot([x1, x2], [f(model, x1), f(model, x2)], color = "k") 25plt.scatter(X[model.a_ != 0, 0], X[model.a_ != 0, 1], 26 s = 200, color = (0, 0, 0, 0), edgecolor = "k", marker = "o") 27 28plt.show()
試したこと
1つ目のコード単体ではエラーは発生しなかったのですが、2つ目のコード上で呼び出して使おうとするとエラーが発生します。
SVMを用いた分類アルゴリズムを書こうとしていますが、境界線をうまく表示させることができません。
![
*追加
おそらくこの文がうまくできていないようです。
ind = a != 0. としているのですが、うまく動作しません。
*さらに追加
ind = a[a != 0] とすることにより、最初のエラーはなくなりましたが、今度は別のエラーが発生してしまいました。
補足情報(ツールのバージョンなど)
anaconda Spyder(Python 3.7)
回答1件
あなたの回答
tips
プレビュー