日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

Lesson 12.4 逻辑回归建模实验

發布時間:2025/4/5 编程问答 46 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Lesson 12.4 逻辑回归建模实验 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

Lesson 12.4 邏輯回歸建模實驗

??接下來進行邏輯回歸的建模實驗,首先需要導入相關庫和自定義的模塊。

# 隨機模塊 import random# 繪圖模塊 import matplotlib as mpl import matplotlib.pyplot as plt# numpy import numpy as np# pytorch import torch from torch import nn,optim import torch.nn.functional as F from torch.utils.data import Dataset,TensorDataset,DataLoader from torch.utils.tensorboard import SummaryWriter# 自定義模塊 from torchLearning import *# 導入以下包從而使得可以在jupyter中的一個cell輸出多個結果 from IPython.core.interactiveshell import InteractiveShell InteractiveShell.ast_node_interactivity = "all"

當然,我們可以通過查看我們自定義的函數幫助文檔來驗證是否導入成功

tensorGenCla? #Signature: #tensorGenCla( # num_examples=500, # num_inputs=2, # num_class=3, # deg_dispersion=[4, 2], # bias=False, #) #Docstring: #分類數據集創建函數。 # #:param num_examples: 每個類別的數據數量 #:param num_inputs: 數據集特征數量 #:param num_class:數據集標簽類別總數 #:param deg_dispersion:數據分布離散程度參數,需要輸入一個列表,其中第一個參數表示每個類別數組均值的參考、第二個參數表示隨機數組標準差。 #:param bias:建立模型邏輯回歸模型時是否帶入截距 #:return: 生成的特征張量和標簽張量,其中特征張量是浮點型二維數組,標簽張量是長正型二維數組。 #File: f:\code file\pytorch實戰\torchlearning.py #Type: function

一、邏輯回歸手動實現

??接下來,嘗試手動實現二分類邏輯回歸,還是根據此前介紹的深度學習建模流程進行手動實現。

1.生成數據集

??利用此前創建的tensorGenCla進行二分類數據集的創建

# 設置隨機數種子 torch.manual_seed(420) # 創建數據集 features, labels = tensorGenCla(num_class=2, bias=True)# 可視化展示 plt.scatter(features[:, 0], features[:, 1], c = labels)

features #tensor([[-2.0141, -0.9911, 1.0000], # [-0.6593, -2.7657, 1.0000], # [-1.9395, -1.2347, 1.0000], # ..., # [ 2.9623, 2.0861, 1.0000], # [ 0.4535, -0.2140, 1.0000], # [-2.6681, 3.3935, 1.0000]])

2.建模過程

  • Stage 1.模型選擇

針對二分類問題(0-1問題),我們可以簡單的輸出一個結果,作為標簽取值為1的概率,因此模型結構如下

對應的可定義如下模型

1)激活函數

def sigmoid(z):return 1/(1+torch.exp(-z))

2)邏輯回歸模型

def logistic(X, w):return sigmoid(torch.mm(X, w))

3)輔助函數

??由于sigmoid輸出結果是連續值,而用于二分類判別時,我們需要將連續數值轉化為所判定的類別,可定義對應分類函數如下:

def cal(sigma, p=0.5):return((sigma >= p).float()) a = torch.randint(10, (5, )) a #tensor([8, 0, 4, 4, 2]) a >= 5 #tensor([ True, False, False, False, False]) (a >= 5).float() #tensor([1., 0., 0., 0., 0.])

另外,對分類模型,我們往往會通過準確率判別模型效果,因此還需要定義準確率函數

def accuracy(sigma, y):acc_bool = cal(sigma).flatten() == y.flatten()acc = torch.mean(acc_bool.float())return(acc) p = torch.tensor([1, 1, 2]) == torch.tensor([1, 2, 2]) p #tensor([ True, False, True]) p.float() torch.mean(p.float()) #tensor([1., 0., 1.]) #tensor(0.6667)
  • Stage 2.定義損失函數
def cross_entropy(sigma, y):return(-(1/y.numel())*torch.sum((1-y)*torch.log(1-sigma)+y*torch.log(sigma)))
  • Stage 3.定義優化方法
def sgd(params, lr):params.data -= lr * params.grad params.grad.zero_()
  • Stage 4.訓練模型
features #tensor([[-2.0141, -0.9911, 1.0000], # [-0.6593, -2.7657, 1.0000], # [-1.9395, -1.2347, 1.0000], # ..., # [ 2.9623, 2.0861, 1.0000], # [ 0.4535, -0.2140, 1.0000], # [-2.6681, 3.3935, 1.0000]]) # 設置隨機數種子 torch.manual_seed(420) # 初始化核心參數 batch_size = 10 # 每一個小批的數量 lr = 0.03 # 學習率 num_epochs = 3 # 訓練過程遍歷幾次數據 w = torch.ones(3, 1, requires_grad = True) # 隨機設置初始權重# 參與訓練的模型方程 net = logistic # 使用邏輯回歸方程 loss = cross_entropy # 交叉熵損失函數# 訓練過程 for epoch in range(num_epochs):for X, y in data_iter(batch_size, features, labels):l = loss(net(X, w), y)l.backward()sgd(w, lr)train_acc = accuracy(net(features, w), labels)print('epoch %d, accuracy %f' % (epoch + 1, train_acc)) #<torch._C.Generator at 0x1d92af10cd0> #epoch 1, accuracy 0.904000 #epoch 2, accuracy 0.907000 #epoch 3, accuracy 0.914000 w #tensor([[1.0069], # [0.9753], # [0.5765]], requires_grad=True)

3.模型調試

根據上述迭代三輪返回的準確率,能夠看出整體還在增加,讓我們再多迭代幾輪查看結果

# 設置隨機數種子 torch.manual_seed(420) # 迭代輪數 num_epochs = 20# 設置初始權重 w = torch.ones(3, 1, requires_grad = True) # 設置列表容器 train_acc = []# 執行迭代 for i in range(num_epochs):for epoch in range(i):for X, y in data_iter(batch_size, features, labels):l = loss(net(X, w), y)l.backward()sgd(w, lr)train_acc.append(accuracy(net(features, w), labels))# 繪制圖像查看準確率變化情況 plt.plot(list(range(num_epochs)), train_acc)

train_acc #[tensor(0.8970), # tensor(0.9040), # tensor(0.9120), # tensor(0.9170), # tensor(0.9190), # tensor(0.9150), # tensor(0.9150), # tensor(0.9150), # tensor(0.9150), # tensor(0.9150), # tensor(0.9150), # tensor(0.9150), # tensor(0.9150), # tensor(0.9140), # tensor(0.9140), # tensor(0.9150), # tensor(0.9150), # tensor(0.9150), # tensor(0.9150), # tensor(0.9150)]

能夠看出,增加迭代次數之后,損失函數逼近最小值點,每次迭代梯度取值較小,整體準確率趨于平穩

當然,如果我們將數據難度增加,也就是增加數據的離散程度,是否會對模型結果造成影響

tensorGenCla? #Signature: #tensorGenCla( # num_examples=500, # num_inputs=2, # num_class=3, # deg_dispersion=[4, 2], # bias=False, #) #Docstring: #分類數據集創建函數。 # #:param num_examples: 每個類別的數據數量 #:param num_inputs: 數據集特征數量 #:param num_class:數據集標簽類別總數 #:param deg_dispersion:數據分布離散程度參數,需要輸入一個列表,其中第一個參數表示每個類別數組均值的參考、第二個參數表示隨機數組標準差。 #:param bias:建立模型邏輯回歸模型時是否帶入截距 #:return: 生成的特征張量和標簽張量,其中特征張量是浮點型二維數組,標簽張量是長正型二維數組。 #File: f:\code file\pytorch實戰\torchlearning.py #Type: function torch.manual_seed(420) features, labels = tensorGenCla(num_class=2, bias=True, deg_dispersion=[4, 4])# 可視化展示 plt.scatter(features[:, 0], features[:, 1], c = labels)

# 設置隨機數種子 torch.manual_seed(420) # 迭代輪數 num_epochs = 20# 設置初始權重 w = torch.zeros(3, 1, requires_grad = True) # 設置列表容器 train_acc = []# 執行迭代 for i in range(num_epochs):for epoch in range(i):for X, y in data_iter(batch_size, features, labels):l = loss(net(X, w), y)l.backward()sgd(w, lr)train_acc.append(accuracy(net(features, w), labels))# 繪制圖像查看準確率變化情況 plt.plot(list(range(num_epochs)), train_acc)


能夠發現,隨著數據情況變復雜,相同模型的準確率發生了很大的變化。后續我們將介紹模型優化的相關方法,此處先熟悉代碼過程和基本結論。

train_acc #[tensor(0.5000), # tensor(0.7320), # tensor(0.7310), # tensor(0.7330), # tensor(0.7320), # tensor(0.7300), # tensor(0.7290), # tensor(0.7310), # tensor(0.7290), # tensor(0.7310), # tensor(0.7320), # tensor(0.7260), # tensor(0.7320), # tensor(0.7340), # tensor(0.7270), # tensor(0.7330), # tensor(0.7320), # tensor(0.7270), # tensor(0.7310), # tensor(0.7280)]

二、邏輯回歸的快速實現

1.構建模型

??接下來,我們練習使用PyTorch中的函數和類,進行邏輯回歸的快速構建。

  • 定義核心參數
batch_size = 10 # 每一個小批的數量 lr = 0.03 # 學習率 num_epochs = 3 # 訓練過程遍歷幾次數據
  • 數據準備
# 設置隨機數種子 torch.manual_seed(420) # 創建數據集 features, labels = tensorGenCla(num_class=2) labels = labels.float() # 損失函數要求標簽也必須是浮點型 data = TensorDataset(features, labels) batchData = DataLoader(data, batch_size = batch_size, shuffle = True) #<torch._C.Generator at 0x1d92af10cd0> features #tensor([[-2.0141, -0.9911], # [-0.6593, -2.7657], # [-1.9395, -1.2347], # ..., # [ 2.9623, 2.0861], # [ 0.4535, -0.2140], # [-2.6681, 3.3935]])
  • Stage 1.定義模型
class logisticR(nn.Module):def __init__(self, in_features=2, out_features=1): # 定義模型的點線結構super(logisticR, self).__init__()self.linear = nn.Linear(in_features, out_features)def forward(self, x): # 定義模型的正向傳播規則out = self.linear(x) return out# 實例化模型和 logic_model = logisticR()
  • Stage 2.定義損失函數
criterion = nn.BCEWithLogitsLoss()
  • Stage 3.定義優化方法
optimizer = optim.SGD(logic_model.parameters(), lr = lr)
  • Stage 4.模型訓練
def fit(net, criterion, optimizer, batchdata, epochs):for epoch in range(epochs):for X, y in batchdata:zhat = net.forward(X)loss = criterion(zhat, y)optimizer.zero_grad()loss.backward()optimizer.step()

和線性回歸相同,由于上述模型只有一層,因此也可以通過nn.Linear(2, 1)函數直接建模。由于我們所采用的BCEWithLogitsLoss類進行的損失函數求解,該類會自動對輸入對象進行sigmoid轉化,因此上述過程和線性回歸過程沒有區別。

接下來,即可執行模型訓練

# 設置隨機數種子 torch.manual_seed(420) fit(net = logic_model, criterion = criterion, optimizer = optimizer, batchdata = batchData, epochs = num_epochs) #<torch._C.Generator at 0x1d92af10cd0>

查看模型訓練結果

logic_model #logisticR( # (linear): Linear(in_features=2, out_features=1, bias=True) #) # 查看模型參數 list(logic_model.parameters()) #[Parameter containing: # tensor([[0.8394, 0.8016]], requires_grad=True), # Parameter containing: # tensor([-0.2617], requires_grad=True)] # 計算交叉熵損失 criterion(logic_model(features), labels) #tensor(0.2293, grad_fn=<BinaryCrossEntropyWithLogitsBackward>) def acc_zhat(zhat, y):"""輸入為線性方程計算結果,輸出為邏輯回歸準確率的函數:param zhat:線性方程輸出結果 :param y: 數據集標簽張量:return:準確率 """sigma = sigmoid(zhat)return accuracy(sigma, y) acc_zhat(logic_model(features), labels) #tensor(0.9130)

2.模型調試

同樣,我們首先嘗試多迭代幾次,看下準確率如何發生變化

#創建數據 torch.manual_seed(420) features, labels = tensorGenCla(num_class=2) labels = labels.float() data = TensorDataset(features, labels) batchData = DataLoader(data, batch_size = batch_size, shuffle = True) #<torch._C.Generator at 0x1d92af10cd0> # 設置隨機數種子 torch.manual_seed(420) # 初始化核心參數 num_epochs = 20 LR1 = logisticR() cr1 = nn.BCEWithLogitsLoss() op1 = optim.SGD(LR1.parameters(), lr = lr)# 創建列表容器 train_acc = []# 執行建模 for epochs in range(num_epochs):fit(net = LR1, criterion = cr1, optimizer = op1, batchdata = batchData, epochs = epochs)epoch_acc = acc_zhat(LR1(features), labels)train_acc.append(epoch_acc)# 繪制圖像查看準確率變化情況 plt.plot(list(range(num_epochs)), train_acc)

train_acc #[tensor(0.5170), # tensor(0.9040), # tensor(0.9180), # tensor(0.9180), # tensor(0.9150), # tensor(0.9150), # tensor(0.9150), # tensor(0.9150), # tensor(0.9150), # tensor(0.9150), # tensor(0.9150), # tensor(0.9150), # tensor(0.9150), # tensor(0.9150), # tensor(0.9140), # tensor(0.9150), # tensor(0.9150), # tensor(0.9150), # tensor(0.9150), # tensor(0.9150)]

接下來,和此前一樣,接下來嘗試增加數據難度來測試模型分類性能

#創建數據 torch.manual_seed(420) features, labels = tensorGenCla(num_class=2, deg_dispersion=[4, 4]) labels = labels.float() data = TensorDataset(features, labels) batchData = DataLoader(data, batch_size = batch_size, shuffle = True)plt.scatter(features[:, 0], features[:, 1], c = labels)

#創建數據 torch.manual_seed(420) # 數據封裝與加載 data = TensorDataset(features, labels) batchData = DataLoader(data, batch_size = batch_size, shuffle = True)# 初始化核心參數 num_epochs = 20 LR1 = logisticR() cr1 = nn.BCEWithLogitsLoss() op1 = optim.SGD(LR1.parameters(), lr = lr)# 創建列表容器 train_acc = []# 執行建模 for epochs in range(num_epochs):fit(net = LR1, criterion = cr1, optimizer = op1, batchdata = batchData, epochs = epochs)epoch_acc = acc_zhat(LR1(features), labels)train_acc.append(epoch_acc)# 繪制圖像查看準確率變化情況 plt.plot(list(range(num_epochs)), train_acc)

train_acc #[tensor(0.4970), # tensor(0.7250), # tensor(0.7260), # tensor(0.7290), # tensor(0.7300), # tensor(0.7260), # tensor(0.7260), # tensor(0.7300), # tensor(0.7260), # tensor(0.7250), # tensor(0.7290), # tensor(0.7310), # tensor(0.7320), # tensor(0.7340), # tensor(0.7300), # tensor(0.7300), # tensor(0.7320), # tensor(0.7290), # tensor(0.7290), # tensor(0.7330)]

和此前一樣,準確率在0.7-0.75之間徘徊。

【補充】實例化模型時參數的隨機取值

在手動創建模型類之后,每次實例化都會隨機生成一組參數值

class logisticR(nn.Module):def __init__(self, in_features=2, out_features=1): # 定義模型的點線結構super(logisticR, self).__init__()self.linear = nn.Linear(in_features, out_features)def forward(self, x): # 定義模型的正向傳播規則out = self.linear(x) return outlist(logisticR().parameters()) #[Parameter containing: # tensor([[-0.2511, -0.1878]], requires_grad=True), # Parameter containing: # tensor([-0.6789], requires_grad=True)] list(logisticR().parameters()) #[Parameter containing: # tensor([[0.0188, 0.0345]], requires_grad=True), # Parameter containing: # tensor([-0.1411], requires_grad=True)]

若需要完全復現模型訓練過程,則需要在實例化之前設置隨機數種子,或者在上一個隨機數種子之前規定有限次的隨機次數。

  • 隨機數種子可以在全域發揮作用
torch.manual_seed(420) #<torch._C.Generator at 0x1d92af10cd0> list(logisticR().parameters()) #[Parameter containing: # tensor([[ 0.4318, -0.4256]], requires_grad=True), # Parameter containing: # tensor([0.6730], requires_grad=True)] list(logisticR().parameters()) #[Parameter containing: # tensor([[-0.5617, -0.2157]], requires_grad=True), # Parameter containing: # tensor([-0.4873], requires_grad=True)] torch.manual_seed(420) #<torch._C.Generator at 0x1d92af10cd0> list(logisticR().parameters()) #[Parameter containing: # tensor([[ 0.4318, -0.4256]], requires_grad=True), # Parameter containing: # tensor([0.6730], requires_grad=True)] list(logisticR().parameters()) #[Parameter containing: # tensor([[-0.5617, -0.2157]], requires_grad=True), # Parameter containing: # tensor([-0.4873], requires_grad=True)]
  • torch.manual_seed不會對random中的隨機過程造成影響
l = list(range(5)) l random.shuffle(l) l #[0, 1, 2, 3, 4] #[1, 4, 2, 0, 3] torch.manual_seed(420) l = list(range(5)) l random.shuffle(l) l #<torch._C.Generator at 0x1d92af10cd0> #[0, 1, 2, 3, 4] #[4, 3, 1, 0, 2] torch.manual_seed(420) l = list(range(5)) l random.shuffle(l) l #<torch._C.Generator at 0x1d92af10cd0> #[0, 1, 2, 3, 4] #[2, 3, 0, 4, 1]
  • random中可以通過設置random.seed來控制隨機過程
random.seed(420) l = list(range(5)) l random.shuffle(l) l #[0, 1, 2, 3, 4] #[4, 3, 1, 2, 0] random.seed(420) l = list(range(5)) l random.shuffle(l) l #[0, 1, 2, 3, 4] #[4, 3, 1, 2, 0]

總結

以上是生活随笔為你收集整理的Lesson 12.4 逻辑回归建模实验的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。