Реализация SVM с нуля с помощью pytorch
Добрый день всем машин лернерам! Нужна ваша помощь. Накидал план реализации SVM, но некоторые места не получается реализовать. Помогите, пожалуйста, кто чем может (желательно с комментариями).
def rbf(x1, x2, sig=1.):
d = exp(- (np.sum(np.power((x1-x2),2))) / (2*sig**2))
return torch.Tensor(d).type(torch.float32)
def hinge(scores, labels):
#Cредний лосс для батча
losses = max(0,1 - labels * scores)
return np.average(losses)
class MYSVM(BaseEstimator, ClassifierMixin):
def linear(x1, x2):
#Линейное ядро
return np.dot(x1,x2)
def fit(self, X, Y):
assert (np.abs(Y) == 1).all()
n_obj = len(X)
X, Y = torch.FloatTensor(X), torch.FloatTensor(Y)
Kernel = self.kernel_function(X, X).float()
self.bet = torch.full((n_obj, 1), fill_value=0.001, dtype=X.dtype, requires_grad=True)
self.bi = torch.zeros(1, requires_grad=True) # Смещение
opt = optim.SGD((self.bet, self.bi), lr=self.lr)
for epoch in range(self.epochs):
perm = torch.randperm(n_obj)
sum_loss = 0
for i in range(0, n_obj, self.batch_size):
inds = perm[i:i + self.batch_size]
x_batch = X[inds]
y_batch = Y[inds]
k_batch = Kernel[inds]
opt.zero_grad()
predictions = x_batch * self.bet[inds] - self.bi #не уверен
predictions = preds.flatten()
loss = self.lmbd * self.bet[inds].T @ k_batch @ self.bet + hinge(predictions, y_batch)
loss.backward()
optimizer.step()
sum_loss += loss.item()
self.X = X
self.fitted = True
return self
def predict_scores(self, batch):
with torch.no_grad():
batch = torch.from_numpy(batch).float()
Kernel = self.kernel_function(batch, self.X)
#Значения отступа для каждого объекта в батче
return ### ????????????
def predict(self, batch):
scor = self.predict_scores(batch)
an = np.full(len(batch), -1, dtype=np.int64)
an[scores > 0] = 1
return an
Ответы (1 шт):
Автор решения: Dmitry Korshunov
→ Ссылка
Думаю что правильный ответ будет такой:
def predict_scores(self, batch):
with torch.no_grad():
batch = torch.from_numpy(batch).float()
K = self.kernel_function(batch, self.X)
# compute the margin values for every object in the batch
return (K @ self.betas + self.bias).flatten()
Еще я бы поправил в функции fit:
predictions = x_batch @ self.bet - self.bi