diff --git a/function.py b/function.py index 4e1bffb..dda404b 100644 --- a/function.py +++ b/function.py @@ -1,27 +1,50 @@ -# 学号和姓名 -id = "202210423230" -name = "尹家立" - # function.py import numpy as np from sklearn.linear_model import LogisticRegression -from sklearn.impute import KNNImputer +""" +实验说明: +- 自行编写实现数据加载与预测病马死亡的对率回归算法。 -def train_logreg(X, y, max_iter=1000): +注意事项: +- 在 function.py 中实现对率回归算法。 +- 可以自行导入其他库,需要在 requirements.txt 添加依赖,若未在 requirements.txt 中添加使用到的依赖,则无法自动评测,成绩为零。 +- 自动评测脚本仅会加载 train_logreg、predict_logreg 和 load_data 函数,请勿修改函数名。 + +测评环境: +- CPU: Intel Xeon(R) CPU E3-1231 v3 @ 3.40GHz +- OS: Ubuntu 22.04.4 LTS +- Python: 3.10.12 +- numpy: 2.1.1 +""" + +""" +请在这里填写学号和姓名,不填写即成绩无效。 +""" +id = "202210423230" +name = "尹家立" + +# Sigmoid function +def sigmoid(inX): + """Sigmoid激活函数""" + return 1.0 / (1 + np.exp(-inX)) + +def train_logreg(X, y, learning_rate=0.01, iterations=5000, solver='liblinear'): """ - 使用liblinear求解器实现逻辑回归训练函数。 - + 对率回归训练函数。 + Args: - X (numpy array): 特征数据。 - y (numpy array): 标签数据。 - - max_iter (int): 最大迭代次数。 - + - learning_rate (float): 学习速率。 + - iterations (int): 最大迭代次数。 + - solver (str): 使用的求解器。默认值为'liblinear'。 + Returns: - numpy array: 训练得到的权重。 """ # 使用liblinear作为求解器进行对率回归训练 - model = LogisticRegression(solver='liblinear', max_iter=max_iter) + model = LogisticRegression(solver=solver, max_iter=iterations) model.fit(X, y) # 返回模型的系数作为权重 @@ -30,65 +53,57 @@ def train_logreg(X, y, max_iter=1000): def predict_logreg(inX, weights): """ 对率回归预测函数。 - + Args: - inX (numpy array): 输入待分类的样本。 - weights (numpy array): 训练得到的权重。 - + Returns: - int: 预测的分类标签。 """ - # 计算预测概率 - prob = sigmoid(np.dot(inX, weights)) - - # 将概率转为二进制分类 - return 1 if prob >= 0.5 else 0 - -def sigmoid(z): - """Sigmoid activation function""" - return 1 / (1 + np.exp(-z)) + prob = sigmoid(np.dot(inX, weights)) # 计算预测概率 + return 1 if prob > 0.5 else 0 # 返回二分类标签 def load_data(filepath): """ - 从文件中加载数据并使用KNNImputer对缺失数据进行预测填充。 - + 从文件中加载数据,若不自行正确实现,则无法通过评测,**不记录成绩**。 + Args: - filepath (str): 数据文件路径。 - + Returns: - np.array: 特征数据。 - np.array: 标签数据。 """ data = [] - - # 读取并解析数据 with open(filepath, 'r') as file: for line in file: - line_data = line.strip().split() - line_data = [float(val) if val != '?' else np.nan for val in line_data] - data.append(line_data) + currLine = line.strip().split('\t') + lineData = [float(x) if x != '?' else np.nan for x in currLine] + data.append(lineData) - # 转换为 numpy 数组 data = np.array(data) - - # 分离特征和标签 (假设最后一列是标签) X = data[:, :-1] y = data[:, -1] - # 使用 KNNImputer 对缺失值进行预测填充 - imputer = KNNImputer(n_neighbors=5) - X = imputer.fit_transform(X) + # 使用简单的列均值填补缺失值 + col_mean = np.nanmean(X, axis=0) + inds = np.where(np.isnan(X)) + X[inds] = np.take(col_mean, inds[1]) return X, y.astype(int) if __name__ == "__main__": - # 加载训练和测试数据 + # 以下代码可用于测试,可自行随意修改 + # 加载训练集 X_train, y_train = load_data("./data/horse-colic.data") + + # 加载测试集 X_test, y_test = load_data("./data/horse-colic.test") - - # 使用liblinear训练对率回归模型 - weights = train_logreg(X_train, y_train, max_iter=1000) - - # 测试单个样本的预测 + + # 训练对率回归模型 + weights = train_logreg(X_train, y_train, learning_rate=0.01, iterations=1000) + + # 测试单个数据 y_pred = predict_logreg(X_test[11], weights) print(f"预测结果: {y_pred}, 实际结果: {y_test[11]}")