当前位置: 首页 > news >正文

交通建设集团蓝商分公司网站广州骏域网站建设专家手机电脑版

交通建设集团蓝商分公司网站,广州骏域网站建设专家手机电脑版,家具网站开发任务书,深圳网络建设公司文章目录 引言正文目录解析README.md阅读Setup配置Training the model训练模型Pretrained Model Check Point预训练的模型训练方法 train.py文件的阅读model.py文件阅读h12_noup_smallkey_spec模型定义_base_noup_smallkey_spec模型实现一、定义因果卷积过程通过平移实现因果卷… 文章目录 引言正文目录解析README.md阅读Setup配置Training the model训练模型Pretrained Model Check Point预训练的模型训练方法 train.py文件的阅读model.py文件阅读h12_noup_smallkey_spec模型定义_base_noup_smallkey_spec模型实现一、定义因果卷积过程通过平移实现因果卷积的原理讲解一维向量实现因果卷积二维矩阵实现因果卷积 平移实现因果卷积nn.down_shifted_conv2d下卷积填充实现 权重归一化二维卷积实现自定义实现权重归一化卷积层使用pytorch自带的权重归一化修饰器 nn.down_right_shifted_conv2d:右下移卷积nn.down_shift:下移nn.right_shift:右移 二、门控残差网络三、因果自注意力机制实现四、使用pytorch实现 总结 引言 阅读了PixelSNAIL的相关论文具体链接如下论文学习链接这篇文章是一个自回归神经网络将自注意力机制和因果卷积进行结合我们在PixelCNN中学习过因果卷积的具体实现并且结合了相关代码进行阅读这里给出链接 PixelCNN的论文和代码学习连接 PixelSNAIL的效果是远比PixelCNN的效果好的而且这里并不知道如何实现自注意力机制所以需要好学习一下他的代码。很烦之前弄得深度学习环境因为系统快照的问题需要重新安装所以在做这个代码分析之前还是得重新安装对应的tensorflow深度学习环境。对应github项目的连接 正文 目录解析 data cifar10_data.py 下载并加载相关的数据集cifar10_plotdata.py 绘制对应的图片imagenet_data.py 下载并加载相关的数据集 pixel_cnn_pp linearize.py 优化tensorflow计算图的执行顺序model.py 模型定义函数nn.py 实现pixelCNN 模型的实用函数和层包括了自定义的损失函数plotting.py 绘制训练图 train.py 训练以及测试文件 README.md阅读 Setup配置 需要运行这个代码需要具有如下的内容 具有多个GPU的机器python3以上的编译器Numpy,TensorFlow Training the model训练模型 使用train.py脚本去训练模型 Pretrained Model Check Point预训练的模型 直接在对应的连接上进行下载 CIFAR10 modelImageNet model 训练方法 CIFAR-10的训练脚本 python train.py \--data_setcifar \--modelh12_noup_smallkey \--nr_logistic_mix10 \--nr_filters256 \--batch_size8 \--init_batch_size8 \--dropout_p0.5 \--polyak_decay0.9995 \--save_interval10ImageNet的训练脚本 python train.py \--data_setimagenet \--modelh12_noup_smallkey \--nr_logistic_mix32 \--nr_filters256 \--batch_size8 \--init_batch_size8 \--learning_rate0.001 \--dropout_p0.0 \--polyak_decay0.9997 \--save_interval1train.py文件的阅读 这个代码写的真的不敢苟同所有的处理逻辑都放在一个train.p中看起来很混乱。他的代码是tensorflow的而且是1.0系列的代码可读性并不是那么好所以这里就不 投入太多关注了仅仅阅读模型的生成部分。 调用并生成模型的代码 这里是调用了一个模型模板传入了model文件然后具体的模型名称是在训练脚本中指名的是参数modelh12_noup_smallkey这个键值对 # 创建模型 model_opt {nr_resnet: args.nr_resnet, nr_filters: args.nr_filters,nr_logistic_mix: args.nr_logistic_mix, resnet_nonlinearity: args.resnet_nonlinearity} # 生成一个模型模板模型可以多次重复使用不需要重复创建变量 model tf.make_template(model, getattr(pxpp_models, args.model _spec))# 用于依赖于数据的参数初始化 with tf.device(/gpu:0):gen_par model(x_init, h_init, initTrue,dropout_pargs.dropout_p, **model_opt)综上所述所以具体使用的模型是h12_noup_smallkey_spec model.py文件阅读 鉴于上一个文件这里直接从h12_noup_smallkey_spec这个函数开始看。 h12_noup_smallkey_spec模型定义 定义h12_noup_smallkey_spec的代码 functools.partial用于固定某个函数的一些参数然后生成一个新的函数实现创建了一个h12_noup_smalleky_spec的函数这个函数的逻辑和_base_noup_smallkey_spc的逻辑一样但是参数attn_rep是固定的12 h12_noup_smallkey_spec functools.partial(_base_noup_smallkey_spec, attn_rep12) h12_pool2_smallkey_spec functools.partial(_base_noup_smallkey_spec, attn_rep12, att_downsample2) h8_noup_smallkey_spec functools.partial(_base_noup_smallkey_spec, attn_rep8)所以下一步是仔细看_base_noup_smallkey_spec的具体实现逻辑。 _base_noup_smallkey_spec模型实现 参照论文我们看一下整个模型基本的定义图具体如下主要是两个模块分别是 门控残差网络的实现左下角蓝色的模块自注意力机制的实现右下角蓝色的模块 具体执行逻辑如下图 将图片进行2*2的因果卷积得到A重复执行一下模块M次 将A重复执行4次门控残差模块得到B两步执行 步骤一对B执行1*卷积得到C步骤二对B执行因果注意力模块得到D 将C和D进行拼接程序例又执行了一次因果卷积得到E,将E保存起来然后最终进行输出 下述为原程序代码 def h6_shift_spec(x, hNone, initFalse, emaNone, dropout_p0.5, nr_resnet5, nr_filters160, nr_logistic_mix10, resnet_nonlinearityconcat_elu):We receive a Tensor x of shape (N,H,W,D1) (e.g. (12,32,32,3)) and producea Tensor x_out of shape (N,H,W,D2) (e.g. (12,32,32,100)), where each fiberof the x_out tensor describes the predictive distribution for the RGB atthat position.h is an optional N x K matrix of values to condition our generative model oncounters {}with arg_scope([nn.conv2d, nn.deconv2d, nn.gated_resnet, nn.dense, nn.nin, nn.mem_saving_causal_shift_nin], counterscounters, initinit, emaema, dropout_pdropout_p):# parse resnet nonlinearity argumentif resnet_nonlinearity concat_elu:resnet_nonlinearity nn.concat_eluelif resnet_nonlinearity elu:resnet_nonlinearity tf.nn.eluelif resnet_nonlinearity relu:resnet_nonlinearity tf.nn.reluelse:raise(resnet nonlinearity resnet_nonlinearity is not supported)with arg_scope([nn.gated_resnet], nonlinearityresnet_nonlinearity, hh):# // up pass through pixelCNN xs nn.int_shape(x)background tf.concat([((tf.range(xs[1], dtypetf.float32) - xs[1] / 2) / xs[1])[None, :, None, None] 0. * x,((tf.range(xs[2], dtypetf.float32) - xs[2] / 2) / xs[2])[None, None, :, None] 0. * x,],axis3)# add channel of ones to distinguish image from padding later onx_pad tf.concat([x, tf.ones(xs[:-1] [1])], 3)ul_list [nn.causal_shift_nin(x_pad, nr_filters)] # stream for up and to the leftfor attn_rep in range(6):for rep in range(nr_resnet):ul_list.append(nn.gated_resnet(ul_list[-1], convnn.mem_saving_causal_shift_nin))ul ul_list[-1]hiers [1, ]hier hiers[attn_rep % len(hiers)]raw_content tf.concat([x, ul, background], axis3)key, mixin tf.split(nn.nin(nn.gated_resnet(raw_content, convnn.nin), nr_filters * 2 // 2), 2, axis3)raw_q tf.concat([ul, background], axis3)if hier ! 1:raw_q raw_q[:, ::hier, ::hier, :]query nn.nin(nn.gated_resnet(raw_q, convnn.nin), nr_filters // 2)if hier ! 1:key tf.nn.pool(key, [hier, hier], AVG, SAME, strides[hier, hier])mixin tf.nn.pool(mixin, [hier, hier], AVG, SAME, strides[hier, hier])mixed nn.causal_attention(key, mixin, query, causal_unit1 if hier 1 else xs[2] // hier)if hier ! 1:mixed tf.depth_to_space(tf.tile(mixed, [1, 1, 1, hier * hier]), hier)ul_list.append(nn.gated_resnet(ul, mixed, convnn.nin))x_out nn.nin(tf.nn.elu(ul_list[-1]), 10 * nr_logistic_mix)return x_out函数参数说明 x:输入张量形状为N,H,W,D1N为batch_sizeH,W为图像的高和宽D1为图像的通道数h:可选的N x K矩阵用于在生成模型上进行条件默认是不使用的。init:是否初始化默认不进行初始化ema:是否使用指数移动平均默认不进行指数平均dropout_p:dropout概率默认为0.5nr_resnet:残差网络的数量默认为5nr_filters:卷积核的数量默认为256attn_rep:注意力机制的重复次数默认重复12次nr_logistic_mix:logistic混合的数量默认混合采样10次att_downsample:注意力机制的下采样默认下采样一次resnet_nonlinearity:残差网络的非线性激活函数默认使用“concat_elu” 下述将根据代码和流程图列出因果卷积、门控残差网络和因果注意力模块的具体实现 一、定义因果卷积过程 这里因果卷积的定义方式和PixelCNN不一样他是定义掩码这里是定义了四种不同的卷积方式来实现因果卷积的分别是这个过程复杂的很。 nn.down_shifted_conv2d:下移卷积:nn.down_right_shifted_conv2d:右下移卷积nn.down_shift:下移nn.right_shift:右移 在二维因果卷积过程中要确保每一个输出像素仅受其左侧和上方元素的影响通常经过一下几种方式实现 零填充卷积之前将输入矩阵的周围填充零卷积操作从图像边缘开始不会看到未来消息。平移在卷积之后输出矩阵通常会沿着某个方向进行平移确保因果性。这个平移是需要将原来移空的位置设置为0. 在作者的代码通过了两个方法来确保每一个像素点只能获得上面和左边的信息。 对矩阵的上面进行padding,然后再将矩阵下移来确保每一个元素只能获得上边的元素信息对矩阵的左面进行padding,然后再将矩阵右移来确保每一个元素只能获得左边的元素信息 通过上述两个方法的结合确保元素只能获得左上部的未来信息。 通过平移实现因果卷积的原理讲解 一维向量实现因果卷积 一维输入序列 x [ x 0 , x 1 , . . . , x n − 1 ] x [x_0,x_1,...,x_{n-1}] x[x0​,x1​,...,xn−1​] 一维卷积核 h [ h 0 , h 1 , . . . . , h m − 1 ] h [h _0,h_1,....,h_{m-1}] h[h0​,h1​,....,hm−1​] 因果卷积的输出 y y y定义如下 y t ∑ i 0 m − 1 h i x t − i t i y_t \sum_{i 0}^{m-1} h_i x_{t-i} \ \ \ \ \ \ \ \ \ \ \ \ \ t i yt​i0∑m−1​hi​xt−i​             ti 具体样例如下 一维输入序列 x [ x 0 , x 1 , x 2 , x 3 , x 4 ] x [x_0,x_1,x_2,x_3,x_4] x[x0​,x1​,x2​,x3​,x4​]一维卷积核 h [ h 2 , h 1 , h 1 ] h [h _2,h_1,h_1] h[h2​,h1​,h1​]这个在卷积过程中完全是按他的公式进行卷积的 二维矩阵实现因果卷积 二维卷积因果性意味着输出矩阵中每一个元素只能依赖于其上方和左方的输入元素通过pading和平移实现。 就是通过填充和平移来实现。 平移实现因果卷积 nn.down_shifted_conv2d下卷积 这里使用了自定义的Conv2d卷积还有填充模式这里逐个进行分析 填充实现 def down_shifted_conv2d(x, num_filters, filter_size[2, 3], stride[1, 1], **kwargs):# 这里是对数据进行填充总共有四个维度分别是N,H,W,C# 第一个维度不进行填充他是batch_size# 第二个维度H进行填充开始的地方填充的大小是filter_size[0] - 1结束的地方填充的大小是0也就是仅仅扩充上部分# 第三个宽度是W进行填充开始的地方填充的大小是int((filter_size[1] - 1) / 2)结束的地方填充的大小是int((filter_size[1] - 1) / 2)也就是仅仅扩充左右两边# 第四个维度不进行填充他是channelx tf.pad(x, [[0, 0], [filter_size[0] - 1, 0], [int((filter_size[1] - 1) / 2), int((filter_size[1] - 1) / 2)], [0, 0]])# return conv2d(x, num_filters, filter_sizefilter_size, padVALID, stridestride, **kwargs)假设原始输入的矩阵是68的卷积核的大小是34,原矩阵、填充之后的矩阵和卷积之后的单个矩阵效果如下 原矩阵6*8 填充之后的矩阵8*10卷积之后的矩阵6*7 这里对于生成的序列在于需要将生成之后的矩阵和原来的矩阵进行对齐然后按照位置进行比对的这里有个样例将很好。具体截图如下。 上面一行是卷积之后的输出下面一行是原始的数据集左图是正确的timeB的时间序列仅仅获取timeA和timeB的序列但是右图就获取了timeC未来序列的数据所以左图是符合因果卷积的效果的。 权重归一化二维卷积实现 这里作者自己定义了一个带有权重归一化的二维卷积层因为正常卷积并不包含权重归一化的效果。 带权重归一化的二维卷积层的优势 训练稳定权重归一化之后模型的训练更加稳定快速收敛权重归一化能够加速模型收敛改进泛化在特定的任务中权重归一化有注意模型泛化 正常二维卷积的优势 效率更高、操作简单、广泛应用 缩放因子 g g g和偏置权重 b b b的作用 缩放因子 g g g: 使用广播机制将放缩因子与权重矩阵中的每一个数字按位相乘 S c a l e d W e i g h t g × N o r m a l i z e d W e i g h t Scaled \ Weight g \times Normalized \ Weight Scaled Weightg×Normalized Weight 主要是权重归一化之后所有权重的范围 都是单位范围内加上缩放因子能够适应更多范数。 注意权重归一化是在输出通道上进行操作的 偏置权重 b b b 是在卷积结果之后加上偏置让模型输出一个非零的值具体公式如下 O u t p u t C o n v 2 D ( x , S c a l e d W e i g h t ) b Output Conv2D(x,Scaled \ Weight) b OutputConv2D(x,Scaled Weight)b 这里我进行了两种实现方法一种是通过pytorch自定义权重归一化卷积层还有一种是通过pytorch内置的权重归一化装饰器实现类似的功能。 自定义实现权重归一化卷积层 这里需要继承nn.Moudle模块自己定义forward模块实现相关功能需要实现的基本步骤 基本的init初始化函数forward前向传播函数自定义计算缩放因子和偏置初值的函数具体计算公式如下 # 权重归一化卷积层 class WeightNormConv2d(nn.Module):def __init__(self, in_channels, out_channels,kernel_size, stride1, padding0, nonlinearityNone, init_scale1.):super(WeightNormConv2d, self).__init__()# 指定非线性激活函数self.nonlinearity nonlinearityself.init_scale init_scale# 定义卷积层self.conv nn.Conv2d(in_channels, out_channels, kernel_size, stride, padding)# 定义缩放因子g和偏置b# 将g和b声明为需要优化的参数卷积层默认的权重是(C-out,C-in,H,W)这四个维度self.g nn.Parameter(torch.ones(out_channels, 1, 1, 1))self.b nn.Parameter(torch.zeros(out_channels))# 声明初始化参数self.reset_parameters()# 数据依赖的参数初始化def reset_parameters(self):# 初始化权重为正太分布init.normal_(self.conv.weight, mean0, std0.05)# 初始化偏置为0init.zeros_(self.conv.bias)# 使用一次随机输入进行一次前向传播以计算初始的g和bwith torch.no_grad():x_init F.conv2d(torch.randn(1, *self.conv.weight.shape[1:]), self.conv.weight)m_init, v_init x_init.mean(), x_init.var()# 计算缩放因子scale_init self.init_scale / torch.sqrt(v_init 1e-8)self.g.data.fill_(scale_init)# 计算偏置# 将张量所有的元素都设定为特定的元素# data属性仅仅是修改对应的值但是不会计入梯度的改变self.b.data.fill_(-m_init * scale_init)def forward(self, x):# 应用权重归一化W self.conv.weight * (self.g / torch.sqrt((self.conv.weight ** 2).sum([1, 2, 3], keepdimTrue)))# 执行卷积操作x F.conv2d(x, W, self.b, self.conv.stride, self.conv.padding)# 应用非线性激活if self.nonlinearity is not None:x self.nonlinearity(x)return x# 测试函数 conv_layer WeightNormConv2d(3, 16, [3, 3], stride1, nonlinearityF.relu) x torch.randn(8, 3, 64, 64) # NCHW格式 out conv_layer(x) print(out.shape)使用pytorch自带的权重归一化修饰器 直接调用nn.utils中的weight.norm组件包括原来的卷积层即可具体如下 # 使用pytorch自定义的权重归一化层 import torch from torch import nn from torch.nn.utils import weight_norm# 创建一个标准的 Conv2d 层 conv_layer nn.Conv2d(3, 16, 3, 1)# 应用权重归一化 conv_layer weight_norm(conv_layer)# 测试该层 x torch.randn(8, 3, 64, 64) # 输入张量形状为 [batch_size, channels, height, width] out conv_layer(x)print(out.shape) # 输出张量的形状应为 [8, 16, 62, 62]nn.down_right_shifted_conv2d:右下移卷积 这个和上一个方式基本上都是相同的只不过对于W和这个维度而言仅仅是填充了左边并没有填充右边。就是在原来的代码上进行修改同时填充的数量也不一样。具体不再讲解 add_arg_scope def down_right_shifted_conv2d(x, num_filters, filter_size[2, 2], stride[1, 1], **kwargs):x tf.pad(x, [[0, 0], [filter_size[0] - 1, 0],[filter_size[1] - 1, 0], [0, 0]])return conv2d(x, num_filters, filter_sizefilter_size, padVALID, stridestride, **kwargs)nn.down_shift:下移 使用原始数据的一部分用零来替代确保最终生成的数据是。将原始的张量往下移动n行然后前n行全部替换成0 nn.right_shift:右移 具体实现和上面相同仅仅是在矩阵的作伴部分进行添加然后返回最终的矩阵 def right_shift(x, step1):xs int_shape(x)return tf.cobncat([tf.zeros([xs[0], xs[1], step, xs[3]]), x[:, :, :xs[2] - step, :]], 2)二、门控残差网络 由于篇幅有限这里具体看这篇文章和博客 门控残差网络的具体实现 三、因果自注意力机制实现 看对应文章的链接 因果自注意力机制实现 四、使用pytorch实现 之前每一个章节都有pytorch实现的版本这里将对所有的内容进行汇总使用pytorch对pixelSNAIL模型进行重构具体代码如下 # 实现最终的模型 class PixelSNAIL(nn.Module):pixelSNAIL模型def __init__(self,nr_resnet5, nr_filters32, attn_rep12, nr_logistic_mix10, att_downsample1):super(PixelSNAIL,self).__init__()# 声明类成员self.nr_resnet nr_resnetself.nr_filters nr_filtersself.attn_rep attn_repself.nr_logistic_mix nr_logistic_mixself.att_downsample att_downsample# 声明定义模型对象# 声明因果卷积的网络self.down_shifted_conv2d weight_norm(nn.Conv2d(3, self.nr_filters, kernel_size(1, 3)))self.down_right_shifted_conv2d weight_norm(nn.Conv2d(3, self.nr_filters, kernel_size(2, 1)))# 声明包含若干门控残差网络的modulelistself.gated_resnets nn.ModuleList([GatedResNet(self.nr_filters) for _ in range(self.nr_resnet)])# 声明线性模型self.nin1 nn.Linear(self.nr_filters, self.nr_filters // 2 16) # 假设q_size 16self.nin2 nn.Linear(self.nr_filters, 16) # 假设q_size 16# 声明因果注意力模块self.causal_attentions nn.ModuleList([CausalAttention() for _ in range(self.attn_rep)])# 最终的卷积网络self.final_conv nn.Conv2d(self.nr_filters, 10 * self.nr_logistic_mix, kernel_size1)def forward(self, x):ul_list []# 加上一个是四个# 按照左右上下的方式进行填充down_shifted F.pad(x, (1, 1, 0, 0)) # 自定义下移和右移操作right_shifted F.pad(x, (0, 0, 1, 0))# 因果卷积ds_conv self.down_shifted_conv2d(down_shifted)drs_conv self.down_right_shifted_conv2d(right_shifted)ul ds_conv drs_convul_list.append(ul)# 下采样从右下角开始for causal_attention in self.causal_attentions:for gated_resnet in self.gated_resnets:ul gated_resnet(ul)ul_list.append(ul)print(attention module)# 注意力机制last_ul ul_list[-1]# 准备原始内容raw_content torch.cat([x, last_ul], dim1) # 假设背景信息已经添加到x中# 生成key和valueprint(raw_content.shape)raw self.nin1(raw_content)print(raw data shape,raw.shape)key, mixin raw.split(18, dim1) # 假设q_size 16# 生成query查询键raw_q last_ulquery self.nin2(raw_q)# 计算注意力print(mixin.shape)print(query.shape)mixed causal_attention(key, mixin, query)ul_list.append(mixed)x_out F.elu(ul_list[-1])x_out self.final_conv(x_out)return x_outx torch.randn(64,3,32,32) model PixelSNAIL() x_out model(x) print(x_out.shape)这个代码多多少少有一点问题 但是我并不想在投入时间了因为我感觉我已经滞后了很多有点慌张这个模型完整的都已经知道了具体的实现细节。pytorch的大概实现逻辑也给了后续有空了可以继续调整。 总结 激活函数可以试一下concat_elu,能够识别更加复杂的特征。这个PixelSNAIL用了差不多一周看完虽然没有跑起来没有调试但是大部分代码自己都进行了重构学到了很多。以后在处理序列数据可以使用因果注意力机制而不仅仅是使用因果卷积。除此之外对于query、key和value的生成理解还有一些问题总是觉得怪怪的门控残差进行卷积一定次数之后设定特定的filter_num直接输出直接进行拆分就可以获得key和value,然后在点乘我想知道这个操作是怎么想出来的。我想将我所有的代码都放到我的github上现在还缺数据加载和最终生成模型的评价指标下一步还是回归我们的那个基础的模型然后将之模块化主要是为了适应以后的模块替换。
http://www.w-s-a.com/news/388889/

相关文章:

  • 电子商务类网站建设山西自助建站系统怎么用
  • odoo做网站网站设置专栏有什么好处
  • 局域网内个人网站建设查询企业的网站有哪些
  • 网站建设属于技术开发吗网页制作团队
  • 做家常菜的网站哪个好哪个网站做图片外链
  • 眼科医院网站设计怎么做6深圳宝安是什么风险等级
  • 网站制作容易吗logo免费生成网站
  • 建设厅官方网站下载专区网络托管公司
  • 祥云平台官方网站网线制作实验原理
  • 把网站做成app的软件下载国外做兼职的网站有哪些
  • 网站建设 海豚弯专业的网站开发服务商
  • 那个网站有免费模板中国家装公司十大排名
  • 中铁建设集团有限公司门户网站余杭区建设规划局网站
  • 天猫网站建设的目标是什么做网站常见问题模板
  • 做php网站需要什么软件天津建设网官方网站
  • 南漳网站开发上海网站推广方法
  • 深圳seo网站大连旅顺房价
  • dede网站 地图什么做有没有做黑市网站
  • 做网站参考文献域名如何做网站
  • 怎么选择网站开发英文网站建设用途
  • 怎样做电子商务网站织梦生成手机网站
  • 公司网站建设选什么服务器网站里怎样添加关键词
  • 深圳建设局网站深业中城绿化项目营销型网站开发流程包括
  • 找销售的网站九江市建设项目服务中心
  • 东原ARC网站建设公司合肥seo网站推广外包
  • 那个网站是做房产中介的网站制作软件小学
  • 做网页怎么建站点视频解析网站
  • 做网站的系统设计网站设计论文前言
  • 做外贸网站多久更新汕头市建设局网站首页
  • 如何建设专业化的网站手机管理网站模板