From e138b41a3ce2fe1e56b9c170aaab6647cee70485 Mon Sep 17 00:00:00 2001 From: dong <2938690875@qq.com> Date: Thu, 14 Nov 2024 17:14:19 +0800 Subject: [PATCH] =?UTF-8?q?=E6=9B=B4=E6=96=B0=20function.py?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- function.py | 38 +++++++++++++++++++++++--------------- 1 file changed, 23 insertions(+), 15 deletions(-) diff --git a/function.py b/function.py index 3afa3b0..d588228 100644 --- a/function.py +++ b/function.py @@ -34,33 +34,41 @@ def load_data(filepath): with open(filepath, 'r') as file: for line in file: fields = line.strip().split() - if '?' in fields: # 处理缺失值 - fields = [0 if f == '?' else float(f) for f in fields] + fields = [0 if f == '?' else float(f) for f in fields] # 缺失值填充 features = np.array(fields[:-1], dtype=float) - label = int(fields[-1]) # 确保标签未合并 + label = int(fields[-1]) data.append(features) labels.append(label) - return np.array(data), np.array(labels) + labels = np.array(labels) -def train_svm(X, y, learning_rate=0.01, iterations=1000): + # 检查标签是否为三类 + unique_labels = np.unique(labels) + if len(unique_labels) != 3: + raise ValueError("标签数量不为3,请确保标签未合并!") + + return np.array(data), labels + +def train_svm(X, y, learning_rate=0.01, iterations=1000, regularization_strength=0.01): n_samples, n_features = X.shape n_classes = len(np.unique(y)) weights = np.zeros((n_classes, n_features)) + # 将标签转化为多类别(one-vs-rest)形式 + y_one_vs_rest = np.array([[1 if y[i] == c else -1 for c in range(n_classes)] for i in range(n_samples)]) + for _ in range(iterations): - for idx, x_i in enumerate(X): - for c in range(n_classes): - y_i = 1 if y[idx] == c else -1 - if y_i * (np.dot(weights[c], x_i)) < 1: - weights[c] += learning_rate * (y_i * x_i - (2 * 1/iterations) * weights[c]) - else: - weights[c] -= learning_rate * (2 * 1/iterations) * weights[c] + # 计算预测值 + margins = y_one_vs_rest * (X @ weights.T) + mask = margins < 1 + grad = -np.einsum('ij,ik->kj', y_one_vs_rest * mask, X) / n_samples + weights -= learning_rate * (grad + regularization_strength * weights) return weights -def predict_svm(inX, weights): - scores = [np.dot(w, inX) for w in weights] - return np.argmax(scores) +def predict_svm(X, weights): + scores = X @ weights.T + return np.argmax(scores, axis=1) +