From 359494afc3ef2412c2d5ef2568b968c680e8a899 Mon Sep 17 00:00:00 2001 From: root Date: Sun, 29 Jun 2025 14:00:00 +0800 Subject: [PATCH] Sun Jun 29 14:00:00 CST 2025 inscode --- main.py | 147 +++++++++++++++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 146 insertions(+), 1 deletion(-) diff --git a/main.py b/main.py index 4c0c135..b36985b 100644 --- a/main.py +++ b/main.py @@ -1 +1,146 @@ -print('欢迎来到 InsCode') \ No newline at end of file +print('欢迎来到 InsCode') +import torch +import torch.nn as nn +import torch.optim as optim +import numpy as np +import matplotlib.pyplot as plt +from sklearn.model_selection import train_test_split +from sklearn.metrics import accuracy_score, confusion_matrix +import seaborn as sns + +# 设置随机种子保证可重复性 +torch.manual_seed(42) +np.random.seed(42) + +# 1. 生成1000个随机二维向量作为特征 +n_samples = 100 +X = np.random.randn(n_samples, 2) # 1000个二维向量 + +# 2. 创建二分类标签(基于某种规则,这里使用简单的线性决策边界) +# 例如:如果x1 + x2 > 0则为1,否则为0 +y = (X[:, 0] + X[:, 1] > 0).astype(np.float32) + +# 3. 将数据转换为PyTorch张量 +# RNN需要序列数据,所以我们将每个向量视为长度为2的序列 +X_tensor = torch.FloatTensor(X).unsqueeze(1) # 形状变为 [1000, 1, 2] +y_tensor = torch.FloatTensor(y).view(-1, 1) # 形状变为 [1000, 1] + +# 4. 划分训练集和测试集 +X_train, X_test, y_train, y_test = train_test_split( + X_tensor, y_tensor, test_size=0.2, random_state=42 +) + +# 5. 定义RNN模型 +class SimpleRNN(nn.Module): + def __init__(self, input_size=2, hidden_size=16, output_size=1): + super(SimpleRNN, self).__init__() + self.hidden_size = hidden_size + self.rnn = nn.RNN(input_size, hidden_size, batch_first=True) + self.fc = nn.Linear(hidden_size, output_size) + self.sigmoid = nn.Sigmoid() + + def forward(self, x): + # 初始化隐藏状态 + h0 = torch.zeros(1, x.size(0), self.hidden_size) + + # 前向传播RNN + out, _ = self.rnn(x, h0) + + # 只取序列的最后一个时间步的输出 + out = out[:, -1, :] + #print(out) + + # 全连接层和sigmoid激活 + out = self.fc(out) + out = self.sigmoid(out) + return out + +# 6. 初始化模型、损失函数和优化器 +model = SimpleRNN() +criterion = nn.BCELoss() # 二分类交叉熵损失 +optimizer = optim.Adam(model.parameters(), lr=0.01) + +# 7. 训练模型 +epochs = 20 +losses = [] +accuracies = [] + +for epoch in range(epochs): + # 前向传播 + outputs = model(X_train) + loss = criterion(outputs, y_train) + + # 反向传播和优化 + optimizer.zero_grad() + loss.backward() + optimizer.step() + + # 记录损失和准确率 + losses.append(loss.item()) + + # 计算训练准确率 + with torch.no_grad(): + train_outputs = model(X_train) + train_pred = (train_outputs > 0.5).float() + acc = accuracy_score(y_train, train_pred) + accuracies.append(acc) + +# 8. 评估模型 +with torch.no_grad(): + # 测试集预测 + test_outputs = model(X_test) + test_pred = (test_outputs > 0.5).float() + test_acc = accuracy_score(y_test, test_pred) + print(f"Test Accuracy: {test_acc:.4f}") + + # 混淆矩阵 + cm = confusion_matrix(y_test, test_pred) + + # 训练集决策边界可视化 + # 创建一个网格点 + x_min, x_max = X[:, 0].min() - 1, X[:, 0].max() + 1 + y_min, y_max = X[:, 1].min() - 1, X[:, 1].max() + 1 + xx, yy = np.meshgrid(np.linspace(x_min, x_max, 100), + np.linspace(y_min, y_max, 100)) + + # 预测每个网格点的类别 + grid = np.c_[xx.ravel(), yy.ravel()] + grid_tensor = torch.FloatTensor(grid).unsqueeze(1) + Z = model(grid_tensor) + Z = (Z > 0.5).float().view(xx.shape) + +# 9. 绘制结果 +plt.figure(figsize=(15, 5)) + +# 绘制决策边界和数据点 +plt.subplot(1, 3, 1) +plt.contourf(xx, yy, Z, alpha=0.4) +plt.scatter(X[:, 0], X[:, 1], c=y, s=20, edgecolor='k') +plt.title("Decision Boundary and Data Points") +plt.xlabel("Feature 1") +plt.ylabel("Feature 2") + +# 绘制训练损失曲线 +plt.subplot(1, 3, 2) +plt.plot(losses) +plt.title("Training Loss") +plt.xlabel("Epoch") +plt.ylabel("Loss") + +# 绘制训练准确率曲线 +plt.subplot(1, 3, 3) +plt.plot(accuracies) +plt.title("Training Accuracy") +plt.xlabel("Epoch") +plt.ylabel("Accuracy") + +plt.tight_layout() +plt.show() + +# 绘制混淆矩阵 +plt.figure(figsize=(6, 6)) +sns.heatmap(cm, annot=True, fmt='d', cmap='Blues', + xticklabels=['Predicted 0', 'Predicted 1'], + yticklabels=['Actual 0', 'Actual 1']) +plt.title("Confusion Matrix") +plt.show() \ No newline at end of file -- GitLab