PyTorch深度学习实践
根据学习情况随时更新。
2020.08.14更新完成。
参考课程-刘二大人《PyTorch深度学习实践》
文章目录
- (一)课程概述
- (二)线性模型
- (三)梯度下降算法
- (四)反向传播
- (五)用PyTorch实现线性回归
- (六)Logistic回归
- (七)多维特征输入的分类问题
- (八)加载数据集
- (九)多分类问题
- (十)卷积神经网络
- (十一)循环神经网络
(一)课程概述
本章知识部分涉及到计算图的正向传播(表达式计算)和反向传播(表达式求导),无需赘述。
(二)线性模型
机器学习的过程
训练时如果y值已知的学习是监督学习。
数据分为训练集(用于学习)和测试集(用于比对)。
在训练过程中,为了避免过拟合,将训练集中的一部分划分为开发集。
样本函数、代价函数(吴课程笔记已经记录)
(三)梯度下降算法
核心公式
梯度下降法的本质是贪心法。由于函数是凸函数,可以保证贪心法求解得到的是最优解,此时局部最优解即是全局最优解。
此外,学习率α不能过大,否则可能造成不收敛。
梯度下降算法的例子(还是要自己写写才学得会)
def compute(x):return w * xdef cost(xs, ys):sum = 0for x, y in zip(xs, ys):sum += (compute(x) - y) ** 2return sum / len(xs)def gradient(xs, ys):grad = 0for x, y in zip(xs, ys):grad += 2 * x * (w * x - y)return grad / len(xs)w = 1.0
xs = [1.0, 2.0, 3.0]
ys = [2.0, 4.0, 6.0]
print('f(4) before training:' + str(compute(4)))
for i in range(1000):tempCost = cost(xs, ys)tempGradient = gradient(xs, ys)w -= 0.01 * tempGradientprint('cost:' + str(tempCost) + '\t' + 'w:' + str(w))
print('f(4) after training:' + str(compute(4)))
- 随机梯度下降
采用单个输入而不是所有输入的均值。
梯度下降法计算x(i),x(i+1)的梯度时可以并行计算(因为采用均值),而随机梯度下降法计算x(i),x(i+1)的梯度时w存在前后依赖关系,不能并行。
和梯度下降法相比,性能更好但时间复杂度也更高。因此通常采用折中的方案(Batch:批量随机梯度下降)。
(四)反向传播
- 直观概念
正向传播是从输入向输出计算,反向传播是从输出向输入逐步求梯度(本质是求导链式法则)。
得到dL/dx后,x作为输出可以继续向前传播。
图中是一个两层的神经网络,在每层的输出中添加一个非线性函数(此处是sigmoid函数,在吴课程中有介绍)。
- 利用PyTorch构建计算图
PyTorch中,Tensor类是最基本的单元,主要存放 权值w(data) 和损失函数对w的导数 dLoss/dw(grad)。
需要注意的是,grad也是Tensor类型。Tensor类型在运算时会建立计算图,并在反向传播完成后释放计算图。如果单纯地使用x的grad的数值进行计算时,要写成x.grad.data的形式。
import torchdef compute(x):return w * x # 此处的w是Tensor类型,x由整型自动转为Tensor类型,并最终返回Tensordef loss(x, y):return (compute(x) - y) ** 2 # 返回Tensor类型x_data = [1.0, 2.0, 3.0]
y_data = [2.0, 4.0, 6.0]
w = torch.Tensor([1.0]) # 为Tensor赋初值时需要带方括号
w.requires_grad = True # 标明需要计算该权值的梯度值,则计算图中,w参与运算的结果同样具有梯度值
for i in range(100):for x, y in zip(x_data, y_data): # 采用随机梯度下降lossResult = loss(x, y)lossResult.backward() # 反向传播w.data -= 0.01 * w.grad.dataw.grad.data.zero_() # 对于每个输入数据,使用后将w梯度置0,避免梯度累加print('Time:' + str(i+1) + '\tw:' + str(w.data) + '\tresult:' + str(compute(4).data))
(五)用PyTorch实现线性回归
设计步骤:
-准备数据集
-设计模型,计算y的估计值(构造计算图)
-使用PyTorch API构造损失函数、优化器
-训练:前馈算损失、反馈算梯度、更新权值
一个Python传递参数的语法:
实例:
import torch# Step 1
x_data = torch.Tensor([[1.0], [2.0], [3.0]])
y_data = torch.Tensor([[2.0], [4.0], [6.0]])# Step 2
class LinearModule(torch.nn.Module): # 一定要继承自 神经网络模块基类 nn.Module类,并实现__init__()、forward()def __init__(self):super(LinearModule, self).__init__()self.linear = torch.nn.Linear(1, 1) # 参数分别代表初始的 权值w和偏移b(都是Tensor类)def forward(self, x):y_pred = self.linear(x) # linear是Linear类的实例,且该类实现了__call__()方法,在实例化后可以像函数一样调用,通常调用forward()return y_predmodel = LinearModule() # 实例化,model是可调用的
# model(1) 计算x=1时的估计值# Step 3
criterion = torch.nn.MSELoss(size_average=False) # 设置为True也可
optimizer = torch.optim.SGD(model.parameters(), lr=0.01) # lr即学习率# Step 4
for epoch in range(1000):# 前馈y_pred = model(x_data)loss = criterion(y_pred, y_data)print(epoch, loss.data)# 反馈optimizer.zero_grad() # 将梯度清零loss.backward()# 更新optimizer.step()# 输出结果
print(model.linear.weight.item()) # 输出w
print(model.linear.bias.item()) # 输出b
(六)Logistic回归
分类问题
-Logistic回归属于分类问题。分类问题求解是对应情况的概率,并取最大值作为分类结果。
-对于前例,输出由多少分转为能否通过/通过考试的概率。
-使用Logistic函数(标记为σ),将实数空间的输出值映射到 [0,1] 中。此时损失函数也需要改变-(ylog(y’)+(1-y)log(1-y’))。
# 记录LogisticRegressionModel的特点
import torchclass LogisticModel(torch.nn.Module):def __init__(self):super(LogisticModel, self).__init__()self.linear = torch.nn.Linear(1, 1)def forward(self, x):y_pred = torch.nn.functional.sigmoid(self.linear(x)) # 对原y'进行Sigmoid处理return y_predcriterion = torch.nn.BCELoss(size_average=False) # 二分类交叉熵,是否取平均值影响学习率大小
(七)多维特征输入的分类问题
多维输入的Logistic模型:每个样本对应一个向量,单个样本的输出y’仍然是概率(即y’∈[0,1])。相比一维输入,w*x由实数运算变为向量内积运算。
将N个方程合并成矩阵的运算,利用向量化的特性加速训练过程。
Sigmoid函数按向量计算的形式,依次应用到每个元素。
分层构造实例
import torch
import numpy as npxy = np.loadtxt('diabetes.csv.gz', delimiter=',', dtype=np.float32)
x_data = torch.from_numpy(xy[:, :-1])
y_data = torch.from_numpy(xy[:, [-1]])class MultiDimensionLogisticModel(torch.nn.Module):def __init__(self):super(MultiDimensionLogisticModel, self).__init__()self.linear1 = torch.nn.Linear(8, 6) # 输入维度为8(每个样本有8个特征),输出维度为6(每个结果有6个特征)self.linear2 = torch.nn.Linear(6, 4)self.linear3 = torch.nn.Linear(4, 1) # 经过三层处理最终输出一维self.sigmoid = torch.nn.Sigmoid() # Sigmoid函数为模型添加非线性变换,构建计算图def forward(self, x):x = self.sigmoid(self.linear1(x))x = self.sigmoid(self.linear2(x))x = self.sigmoid(self.linear3(x))return xmodel = MultiDimensionLogisticModel()
criterion = torch.nn.BCELoss(size_average=False)
optimizer = torch.optim.SGD(model.parameters(), lr=0.1)for epoch in range(1000):# 前馈y_pred = model(x_data) # 每次处理所有数据集,而下一章每次处理一个Batchloss = criterion(y_pred, y_data)print(epoch, loss.data)# 反馈optimizer.zero_grad()loss.backward()# 更新optimizer.step()
(八)加载数据集
采用DataLoader处理输入时,需要额外定义一个继承自Dataset(该类是抽象类)的类,并实现_init_(), _getitem_(), _len_()方法。
- 概念定义
-Epoch:对所有样本的一次正向传播和反向传播。
-Batch Size:每次正向传播的样本数。
-Iteration:Mini Batch的进行次数。
如:样本数为10000,BatchSize为1000,则Iteration为10
在Mini Batch下的训练步骤:
# Step 4
for epoch in range(training_epochs): # 对所有数据,共进行training_epochs次的训练for i in range(total_batch): # 对每个Batch进行处理#TODO
Dataset和DataLoader
DataLoader迭代时以Batch为基本元素,其中Batch的大小在创建Loader时指定。
Dataset每次获取一个样本,DataLoader每次获取Batch个样本。
实例
import torch
import numpy as np
from torch.utils.data import Dataset
from torch.utils.data import DataLoader# Step 1
class DiabetesDataset(Dataset):def __init__(self, filepath):xy = np.loadtxt(filepath, delimiter=',', dtype=np.float32)self.x_data = torch.from_numpy(xy[:, :-1])self.y_data = torch.from_numpy(xy[:, [-1]])self.len = xy.shape[0] # 和不采用Dataset相比增加的步骤def __getitem__(self, index):return self.x_data[index], self.y_data[index]def __len__(self):return self.lendataset = DiabetesDataset('diabetes.csv.gz')
# dataset是传入数据集,batch_size规定一个batch的样本数,shuffle代表是否打乱样本顺序,num_workers代表并行数目
train_loader = DataLoader(dataset=dataset, batch_size=32, shuffle=True, num_workers=2)# Step 2(未发生变化)
class MultiDimensionLogisticModel(torch.nn.Module):def __init__(self):super(MultiDimensionLogisticModel, self).__init__()self.linear1 = torch.nn.Linear(8, 6)self.linear2 = torch.nn.Linear(6, 4)self.linear3 = torch.nn.Linear(4, 1)self.sigmoid = torch.nn.Sigmoid() # Sigmoid函数为模型添加非线性变换,构建计算图def forward(self, x):x = self.sigmoid(self.linear1(x))x = self.sigmoid(self.linear2(x))x = self.sigmoid(self.linear3(x))return xmodel = MultiDimensionLogisticModel()# Step 3(未发生变化)
criterion = torch.nn.BCELoss(size_average=False)
optimizer = torch.optim.SGD(model.parameters(), lr=0.01)# Step 4
for epoch in range(100):for i, data in enumerate(train_loader, 0): # 每次获取index和一个Batchx, y = data # 其中x和y都是Tensor类型,x代表Batch个输入,y代表Batch个输出# 前馈y_pred = model(x)loss = criterion(y_pred, y)print(epoch, i, loss.item())# 反馈optimizer.zero_grad()loss.backward()# 更新optimizer.step()
(九)多分类问题
Softmax层的引入
相比较二分类问题,多分类需要输出每种情况的对应概率。如果按照二分类的方法,可能造成所有情况概率之和不为1的情况。改进措施是,将输出最终结果前的Sigmoid层转换成Softmax层。
引入Softmax层的具体操作
①使用numpy直接计算
import numpy as npy = np.array([1, 0, 0]) # 标签值
z = np.array([0.2, 0.1, -0.1]) # Softmax输入值
y_pred = np.exp(z)/np.exp(z).sum()
loss = (-y * np.log(y_pred)).sum()
②使用NLLLoss损失函数,输入Softmax和Log处理后的数据,以及标签值,输出Loss。
③使用CrossEntropyLoss(交叉熵损失)函数。
import torchy = torch.LongTensor([2, 0, 1]) # 注意此处是LongTensor
# z_1和z_2是最后一层输出,进入Softmax之前的值,所以每个分类之和不为1
# 每行元素代表对一个对象的分类情况,共三个对象
z_1 = torch.Tensor([[0.1, 0.2, 0.9],[1.1, 0.1, 0.2],[0.2, 2.1, 0.1]])
z_2 = torch.Tensor([[0.9, 0.2, 0.1],[0.1, 0.1, 0.5],[0.2, 0.1, 0.7]])
criterion = torch.nn.CrossEntropyLoss()
print(criterion(z_1, y), criterion(z_2, y))
- PyTorch图像多分类问题
①数据输入
一般读入形式为whc,在PyTorch中为了便于处理,将其转为cwh。
# 将PIL转为Tensor
transform = transforms.Compose([transforms.ToTensor(),transforms.Normalize((0.1307, ), (0.3081, ))
])
②设计模型
view将 N个 1维 28*28的输入,转化为 N个 1行 的数据(每行784个)。
注意最后一层不进行激活。
(十)卷积神经网络
图像存储形式
RGB:输入图片是3*w*h的形式,频道对应红/绿/蓝,每个元素取值0~255.
矢量:存储图像的绘制信息。特点是放大不会出现像素块。图像的卷积概述
对图像进行卷积操作,本质上是对图像的某块的所有频道(即一个Batch)进行操作。操作会改变图像的c,w,h值。
单通道的卷积操作
用Kernel阵遍历输入阵,对应进行数值乘法再求和,得到输出阵的一个元素。
多通道的卷积操作
本质上是将单通道的卷积累加。需要注意的是,输入Kernel的通道数要和输入的通道数相等。
该操作将n通道的输入转化成1通道的输出。
如果需要得到m通道的输出,则要准备m份的卷积阵。此时对应的权值是 m*n*k_width*k_height的四维量。
- 卷积操作实例
import torchin_channels, out_channels= 5, 10
width, height = 100, 100
kernel_size = 3
batch_size = 1input = torch.randn(batch_size, in_channels, width, height)
conv_layer = torch.nn.Conv2d(in_channels, out_channels, kernel_size=kernel_size)
output = conv_layer(input)
- 卷积层的Padding操作
在输入阵的周围进行填充(一般是0),以得到目标形状的输出。
import torchinput = [3,4,6,5,7,2,4,6,8,2,1,6,7,8,4,9,7,4,6,2,3,7,5,4,1]
input = torch.Tensor(input).view(1, 1, 5, 5) # 分别对应Batch、Channel、Width、Height
conv_layer = torch.nn.Conv2d(1, 1, kernel_size=3, padding=1, bias=False) # 分别对应输入Channel、输出Channel
kernel = torch.Tensor([1, 2, 3, 4, 5, 6, 7, 8, 9]).view(1, 1, 3, 3) #输出Channel、输入Channel、Width、Height
conv_layer.weight.data = kernel.data
output = conv_layer(input)
步长stride
将上述代码的padding=1改为stride=2,即可得到2*2的结果。Max Pooling层
kernel_size为2的MaxPooling可以将输入的行和列都减少为原来的1/2.
该操作和通道数无关,操作前后不改变通道数。
import torchinput = [3,4,6,5,2,4,6,8,1,6,7,8,9,7,4,6,]
input = torch.Tensor(input).view(1, 1, 4, 4)
maxpooling_layer = torch.nn.MaxPool2d(kernel_size=2)
output = maxpooling_layer(input)
- 卷积神经网络实例
注意:进行最后一次 Conv-Pooling-ReLU后进入线性层。
import torch
import torch.nn.functional as Fclass Net(torch.nn.Module):def __init__(self):super(Net, self).__init__()self.conv1 = torch.nn.Conv2d(1, 10, kernel_size=5) # 卷积层1self.conv2 = torch.nn.Conv2d(10, 20, kernel_size=5) # 卷积层2self.pooling = torch.nn.MaxPool2d(2)self.linear = torch.nn.Linear(320, 10) # 输入320个数据,输出10个数据(对应十种分类情况)def forward(self, x):batch_size = x.size(0)x = self.pooling(F.relu(self.conv1(x)))x = self.pooling(F.relu(self.conv2(x)))x = x.view(batch_size, -1) # 全连接网络输入x = self.linear(x)return xmodel = Net()
- 使用GPU进行计算
# 在上述代码添加
device = torch.device("cuda:0" if torch.cuda.is_available() else "cpu")
model.to(device)
# 并在训练、测试时,在 input, target = data的基础上增加
input, target = input.to(device), target.to(device)
1x1卷积
本质上是将多个通道的对应元素进行信息融合。
目的是,只改变通道数,不改变输入的宽度和高度,以减小运算量。
Inception Module
对同一输入进行不同卷积,合并最终结果,取最优解。
不同路径只能改变频道数,不能改变宽度和高度(因为最终需要合并)。
Concatenate操作将不同的卷积结果沿着通道方向合并。
# 上半部分是__init__的操作,下半部分是forward的操作
# 分支1
self.branch_pool = nn.Conv2d(in_channels, 24, kernel_size=1)branch_pool = F.avg_pool2d(x, kernel_size=3, stride=1, padding=1)
branch_pool = self.branch_pool(branch_pool)# 分支2
self.branch1x1 = nn.Conv2d(in_channels, 16, kernel_size=1)branch1x1 = self.branch1x1(x)# 分支3
self.branch5x5_1 = nn.Conv2d(in_channels,16, kernel_size=1)
self.branch5x5_2 = nn.Conv2d(16, 24, kernel_size=5, padding=2)branch5x5 = self.branch5x5_1(x)
branch5x5 = self.branch5x5_2(branch5x5)# 分支4
self.branch3x3_1 = nn.Conv2d(in_channels, 16, kernel_size=1)
self.branch3x3_2 = nn.Conv2d(16, 24, kernel_size=3, padding=1)
self.branch3x3_3 = nn.Conv2d(24, 24, kernel_size=3, padding=1)branch3x3 = self.branch3x3_1(x)
branch3x3 = self.branch3x3_2(branch3x3)# Concatenate
outputs = [branch1x1, branch5x5, branch3x3, branch_pool]
return torch.cat(outputs, dim=1) # (batch, channel, width, height)中channel对应index为1,按照channel对齐
使用实例
import torch
from torch import nn
import torch.nn.functional as F# 图中的Inception示例
class InceptionA(nn.Module):def __init__(self, in_channels):super(InceptionA, self).__init__()# 定义各分支的卷积部分:# 分支2self.branch1x1 = nn.Conv2d(in_channels, 16, kernel_size=1)# 分支3self.branch5x5_1 = nn.Conv2d(in_channels, 16, kernel_size=1)self.branch5x5_2 = nn.Conv2d(16, 24, kernel_size=5, padding=2)# 分支4self.branch3x3_1 = nn.Conv2d(in_channels, 16, kernel_size=1)self.branch3x3_2 = nn.Conv2d(16, 24, kernel_size=3, padding=1)self.branch3x3_3 = nn.Conv2d(24, 24, kernel_size=3, padding=1)# 分支1self.branch_pool = nn.Conv2d(in_channels, 24, kernel_size=1)def forward(self, x):# 分支2branch1x1 = self.branch1x1(x)# 分支3branch5x5 = self.branch5x5_1(x)branch5x5 = self.branch5x5_2(branch5x5)# 分支4branch3x3 = self.branch3x3_1(x)branch3x3 = self.branch3x3_2(branch3x3)branch3x3 = self.branch3x3_3(branch3x3)# 分支1branch_pool = F.avg_pool2d(x, kernel_size=3, stride=1, padding=1)branch_pool = self.branch_pool(branch_pool)# Concatenateoutputs = [branch1x1, branch5x5, branch3x3, branch_pool]return torch.cat(outputs, dim=1)# 采用Inception的模型
class Net(nn.Module):def __init__(self):super(Net, self).__init__()self.conv1 = nn.Conv2d(1, 10, kernel_size=5)self.conv2 = nn.Conv2d(88, 20, kernel_size=5) # 88是经过Inception1后的通道数self.incep1 = InceptionA(in_channels=10)self.incep2 = InceptionA(in_channels=20)self.mp = nn.MaxPool2d(2) # pooling操作不改变通道数self.linear = nn.Linear(1408, 10)def forward(self, x):in_size = x.size(0)x = F.relu(self.mp(self.conv1(x))) # 先后进行卷积、池化、激活x = self.incep1(x)x = F.relu(self.mp(self.conv2(x)))x = self.incep2(x)x = x.view(in_size, -1)x = self.linear(x)return x
- Residual Block
不改变输入的c,w,h.
例:进行两次卷积操作的网络
from torch import nn
import torch.nn.functional as Fclass ResidualBlock(nn.Module):def __init__(self, channel):super(ResidualBlock, self).__init__()self.conv1 = nn.Conv2d(channel, channel, kernel_size=3, padding=1)self.conv2 = nn.Conv2d(channel, channel, kernel_size=3, padding=1)def forward(self, x):y = F.relu(self.conv1(x))y = self.conv2(y) # 注意此处需要求和后再激活y = F.relu(x + y)return yclass Net(nn.Module):def __init__(self):super(Net, self).__init__()self.conv1 = nn.Conv2d(1, 16, kernel_size=5)self.conv2 = nn.Conv2d(16, 32, kernel_size=5)self.rb1 = ResidualBlock(16)self.rb2 = ResidualBlock(32)self.mp = nn.MaxPool2d(2)self.linear = nn.Linear(512, 10)def forward(self, x):in_size = x.size(0)x = self.mp(F.relu(self.conv1(x)))x = self.rb1(x)x = self.mp(F.relu(self.conv2(x)))x = self.rb2(x)x = x.view(in_size, -1)x = self.linear(x)return x
(十一)循环神经网络
RNN用于处理输入具有序列关系,且前项对后项有影响的问题。比如根据前几天的温度、气压、天气对未来的天气进行预测。
RNNCell
本质是线性层。同一个Cell在RNN中循环使用。
构造RNNCell需要输入inputSize和hiddenSize。
使用时需要明确输入、输出的维度关系。
设 batchSize=1,seqLen=3,inputSize=4,hiddenSize=2
则有 input.shape=(batchSize, inputSize),output.shape=(batchSize, hiddenSize),dataset.shape=(seqLen, batchSize, inputSize)
import torchbatch_size = 1
seq_len = 3
input_size = 4
hidden_size = 2
cell = torch.nn.RNNCell(input_size=input_size, hidden_size=hidden_size)dataset = torch.randn(seq_len, batch_size, input_size)
hidden = torch.zeros(batch_size, hidden_size)
- RNN
input.shape=(seqLen, batchSize, inputSize)
h0.shape=(numLayers, batchSize, hiddenSize)
output.shape=(seqLen, batchSize, hiddenSize)
hn.shape=(numLayers, batchSize, hiddenSize)
import torchbatch_size = 1
seq_len = 3
input_size = 4
hidden_size = 2
num_layers = 1
cell = torch.nn.RNN(input_size=input_size, hidden_size=hidden_size, num_layers=num_layers)inputs = torch.randn(seq_len, batch_size, input_size)
hidden = torch.zeros(num_layers, batch_size, hidden_size)
- 实例:使用RNNCell的字符串转化
对于每个输入字符,求解问题的整体结构:
将字符串"hello"转化为"ohlol"
首先将输入字符的每个字符进行向量化,得到RNNCell的输入。
此时inputSize=4,seqLen=5。
import torch# 处理输入
input_size = 4
hidden_size = 4
batch_size = 1
idx2char = ['e', 'h', 'l', 'o']
x_data = [1, 0, 2, 2, 3] # 'hello'
y_data = [3, 1, 2, 3, 2] # 'ohlol'
one_hot_lookup = [[1, 0, 0, 0],[0, 1, 0, 0],[0, 0, 1, 0],[0, 0, 0, 1]]x_one_hot = [one_hot_lookup[x] for x in x_data] # 得到RNNCell的输入
inputs = torch.Tensor(x_one_hot).view(-1, batch_size, input_size) # input.shape=(seqLen, batchSize, inputSize)
labels = torch.LongTensor(y_data).view(-1, 1) # labels.shape=(seqLen, 1)# 处理单个字符输入的RNNCell
class Model(torch.nn.Module):def __init__(self, input_size, hidden_size, batch_size):super(Model, self).__init__()self.batch_size = batch_sizeself.input_size = input_sizeself.hidden_size = hidden_sizeself.rnncell = torch.nn.RNNCell(input_size=self.input_size, hidden_size=self.hidden_size)def forward(self, input, hidden):hidden = self.rnncell(input, hidden) # input.shape=(batchSize, inputSize); hidden.shape=(batch, hiddenSize)return hiddendef init_hidden(self):return torch.zeros(self.batch_size, self.hidden_size) # h0net = Model(input_size, hidden_size, batch_size)
criterion = torch.nn.CrossEntropyLoss()
optimizer = torch.optim.Adam(net.parameters(), lr=0.1)for epoch in range(15):loss = 0optimizer.zero_grad()hidden = net.init_hidden()# 每轮对所有输入进行训练# inputs.shape=(
PyTorch深度学习实践相关推荐
- 【Pytorch深度学习实践】B站up刘二大人之SoftmaxClassifier-代码理解与实现(8/9)
这是刘二大人系列课程笔记的倒数第二个博客了,介绍的是多分类器的原理和代码实现,下一个笔记就是basicCNN和advancedCNN了: 写在前面: 这节课的内容,主要是两个部分的修改: 一是数据集: ...
- 【Pytorch深度学习实践】B站up刘二大人课程笔记——目录与索引(已完结)
从有代码的课程开始讨论 [Pytorch深度学习实践]B站up刘二大人之LinearModel -代码理解与实现(1/9) [Pytorch深度学习实践]B站up刘二大人之 Gradient Desc ...
- 《PyTorch 深度学习实践》第10讲 卷积神经网络(基础篇)
文章目录 1 卷积层 1.1 torch.nn.Conv2d相关参数 1.2 填充:padding 1.3 步长:stride 2 最大池化层 3 手写数字识别 该专栏内容为对该视频的学习记录:[&l ...
- PyTorch 深度学习实践 第13讲
PyTorch 深度学习实践 第13讲 引言 代码 结果 引言 近期学习了B站 刘二大人的PyTorch深度学习实践,传送门PyTorch 深度学习实践--循环神经网络(高级篇),感觉受益匪浅,发现网 ...
- 刘二大人 PyTorch深度学习实践 笔记 P6 逻辑斯蒂回归
刘二大人 PyTorch深度学习实践 笔记 P6 逻辑斯蒂回归 P6 逻辑斯蒂回归 1.torchversion 提供的数据集 2.基本概念 3.代码实现 P6 逻辑斯蒂回归 1.torchversi ...
- 《PyTorch深度学习实践》 课堂笔记 Lesson7 神经网络多维特征输入的原理推导与实现
文章目录 1.为什么使用多维的特征输入 2. 多维特征向量输入推导 3.实现过程 3.1源代码 3.2训练结果 写在最后 1.为什么使用多维的特征输入 对于现实世界来说,影响一个事物发展的因素有很多种 ...
- PyTorch深度学习实践概论笔记9-SoftMax分类器
上一讲PyTorch深度学习实践概论笔记8-加载数据集中,主要介绍了Dataset 和 DataLoader是加载数据的两个工具类.这一讲介绍多分类问题如何解决,一般会用到SoftMax分类器. 0 ...
- 【PyTorch深度学习实践】P9 kaggle otto商品分类作业(含注释)
<PyTorch深度学习实践>-刘二大人 Otto Group Product Classification作业 将商品进行十分类,输入为93个特征10个类别的商品数据集,输出为预测数据集 ...
- 《PyTorch深度学习实践》
[<PyTorch深度学习实践>完结合集] https://www.bilibili.com/video/BV1Y7411d7Ys/?share_source=copy_web&v ...
最新文章
- 开源库BearSSL介绍及使用
- adf盖怎么打开_打印机墨盒怎么更换,看我这篇文章就够了
- 跟小静读CLR via C#(02)-基元类型、引用类型、值类型
- Linux基础知识(一)
- MyBatis分页插件PageHelper使用练习
- IT知识架构和操作系统简介1
- mybatis的逆向工程
- java中IOUtil.readLong_使用io/ioutil进行读写文件
- LeetCode上读不懂题!看不懂测试用例的那些题(有生之年更新。。。)
- HBase 配置详解
- java 字符串contain_如何使用java.lang.String.contains()方法
- idea创建一个javaweb项目
- 远程桌面连接Windows后显示蓝屏
- css 背景图片虚化磨砂效果
- 计算机房要保持清洁 卫生,国家机房数据安全管理制度
- sqlserver 人名_一个用来统计相同姓名人数的SQl语句_sqlserver
- 下载jar源码时,出现:cannt not download source Sources not found for
- 编程难?零基础如何学好编程?
- 磁盘占用率100%——多番尝试
- vs2013 - 高亮设置 括号匹配 (方括号) 大括号匹配 Visual Studio 2013
热门文章
- 微软BUG Bounty悬赏项目扩展至.NET Core和ASP.NET Core
- 告别国外 IDE,阿里 蚂蚁自研 IDE 研发框架 OpenSumi 正式开源
- 微软Visual Studio 2019版本16.3 正式发布,支持 .NET Core 3.0
- Google 开源的 Android 排版库:FlexboxLayout
- Android之网络请求提示Cleartext HTTP traffic to dev*******.com not permitted
- C和指针之实现可变参数函数编译出现expanded from macro ‘va_arg‘ #define va_arg(ap, type) 解决办法
- Android之Color颜色值和RGB颜色对照表
- linux如何获取网卡计数信息,Linux下如何获取网卡信息
- pythonrequests说明_解决Python requests 报错方法集锦
- 第6章 C控制语句:循环