分类: 机器学习

  • 关于机器学习:神经网络与深度学习2机器学习概述

    概述

    • 机器学习,即从样本数据中寻找法则,建设模型对未知的数据进行观测。如辨认手写体数字,首先提供大量手写体数字图像(每张图像都通过人工标记了它是什么数字),咱们把这些图像作为训练数据,通过学习算法主动生成模型,依附模型辨认新的手写体数字

    基本概念

    • 咱们以买芒果作为例子:

    (1)首先,咱们选取一些芒果,列出它们的特色(色彩、大小、形态、产地、品牌)及要预测的标签。标签能够是间断值(芒果甜度、成熟度的综合打分),也能够是离散值(好、坏两类标签)。这样一个同时标记好特色和标签的芒果叫做样本
    (2)一组样本的汇合称为数据集,咱们通常将数据集分为两局部:训练集和测试集。训练集中的样本用来训练模型,失去模型;测试集中的样本用来测验训练失去样本的可靠性

    • 学习过程:

    咱们通常用一个????维向量????=[????1,????2,⋯,????????]T示意一个芒果的所有特色形成的向量,称为特征向量,其中每一维示意一个特色;用标量????来示意芒果的标签。这里要留神的是,并不是所有的样本特色都是数值型,有的须要通过转换示意为特征向量

    机器学习三要素

    机器学习办法能够粗略的分为三个基本要素:模型、学习准则、优化算法

    模型

    模型就是一个可能形容x、y关系的实在映射函数或者实在条件概率分布,模型分为线性模型和非线性模型

    • 线性模型的假如空间为一个参数化的线性函数族, 即

    ????(????;????)=????????+????,

    其中参数????蕴含了权重向量????和偏置????.

    • 狭义的非线性模型能够写为多个非线性基函数????(????)的线性组合

    ????(????;????)=????????(????)+????,

    其中????(????)=[????1(????),????2(????),⋯,????????(????)]T为????个非线性基函数组成的向量,参数???? 蕴含了权重向量????和偏置????.

    如果????(????)自身为可学习的基函数,比方

    ????(????)=ℎ(????????′(????)+????????),∀1≤????≤????,

    其中ℎ(⋅)为非线性函数,????′(????)为另一组基函数,????????和????????为可学习的参数,则 ????(????;????)就等价于神经网络模型.

    学习准则

    一个好的模型应该每一个(x,y)在空间中的取值都与实在映射函数统一,为了形容模型的好坏,咱们引入冀望谬误来掂量:

    损失函数

    损失函数是一个非负实数函数,用于量化模型预测值和实在标签值间的差别

    • 几种罕用的损失函数


    危险最小化准则
    • 一个好的模型,冀望谬误应该较小。然而因为咱们不可能晓得所有的数据分布,所以实际上无奈计算其冀望危险。咱们能计算的只能是教训谬误,即在训练集上的均匀损失:


    因而咱们规定,使得教训谬误最小的模型,就是好的模型,这就是教训危险最小化准则

    • 教训危险最小化准则带来的过拟合问题:依据大数定理,当训练集大小|????|趋向于无穷大时,教训危险就趋向于冀望危险.然而通常状况下,咱们无奈获取有限的训练样本,并且因为训练数据少、存在一些噪声数据,不能很好地反映全副数据的实在散布.这时,教训危险最小化准则很容易导致模型在训练集上错误率很低,然而在未知数据上错误率很高,这就是过拟合

    为了解决过拟合问题,个别在教训危险最小化的根底上再引入参数的正则化来限度模型能力,使其不要适度地最小化教训危险。这种准则就是构造危险最小化准则:

    • 与过拟合相同的概念是欠拟合,即模型在训练集上错误率比拟高,这个别是因为模型能力有余导致的(也可能是咱们正则化时适度限度模型能力)

    总之,学习准则能够了解为从一个无限、有噪声的数据集中,尽可能的升高泛化谬误,建设一个可能更好地预测未知样本的模型

    优化算法

    • 确定了学习准则后,如何找到最优模型就是一个最优化问题。
    • 在机器学习中,优化能够分为参数优化和超参数优化。模型 ????(????;????)中的????称为模型的参数,能够通过优化算法进行学习;除了可学习的参数????之外,还有一类参数是用来定义模型构造或优化策略的,这类参数叫作超参数

    常见的超参数包含 :聚类算法中的类别个数、梯度降落法中的步长、正则化项的系数、神经网络的层数、反对向量机中的核函数等.超参数的选取个别都是组合优化问题,很难通过优化算法来主动学习.因而,超参数优化是机器学习的一个经验性很强的技术,通常是依照人的教训设定,或者通过搜寻的办法对一组超参数组合进行一直试错调整.

    • 几种优化算法:



    机器学习的简略示例:线性回归

    简略了解,线性回归就是拟合成一个一次函数

    • 下边,介绍四种不同的参数估计办法:





    偏差方差合成

    在建模时,咱们须要在模型的拟合能力和复杂度之间衡量。拟合能力过强,复杂度较高,且易造成过拟合;拟合能力过低,复杂度尽管升高,但可能造成欠拟合。因而,咱们引入偏差-方差合成,以在模型的拟合水平和复杂度间获得较好的均衡
    P53~55

    机器学习算法的类型

    机器学习算法的规范分类多样,依照函数类型,可分为线性类型和非线性类型;依照学习准则,分为统计办法和非统计办法。

    一般来说,咱们依据训练样本以及反馈形式的不同,次要将算法分为以下几类:
    (1)监督学习,其训练集中每个样本都有标签。依据标签类型的不同,咱们又能够把监督学习分为以下三种:
    a.回归问题。标签是间断值,输入的模型也是间断值
    b.分类问题。标签是离散的,由依据类别数量分为二决裂和多分类
    c.结构化学习。标签是结构化的对象,如序列、树、图等
    (2)无监督学习。训练样本不含有标签,例如聚类、密度估计、特色学习、降维
    (3)强化学习。通过交互来学习,电脑做出一个动作,环境给予即时或延时的处分。电脑在和环境的交互中一直学习并调整策略,来获得最大化的冀望总回报

    值得注意的是,监督学习和无监督学习的区别在于训练集数据是否有标签,强化学习则不须要给出训练样本,是一种在线的学习机制

    数据的特色示意

    数据有文本、音频、图像、视频等多种类型,不同类型的数据,其原始特色的空间也不雷同.机器学习算法要求输出的样本特色是数学上可计算的,因而在机器学习之前咱们须要将这些不同类型的数据转换为向量示意。比方一张灰度图像(像素数量为????)的特色空间为[0,255]????,一个自然语言句子(长度为????)的特色空 间为|????|????,其中????为词表汇合.

    • 数据特色转换

    (1)图像特色。图像中每个像素点的灰度值+直方图、宽高比、笔画数、纹理特色、边缘特色等额定特色,形成一个向量
    (2)文本特色。一种办法是应用词袋模型,设训练汇合中的词都来自一个词表????,大小为|????|,则每个样本能够示意为一个|????|维的向量????∈ℝ|????|.向量???? 中第????维的值示意词表中的第????个词是否在????中呈现.如果呈现,值为1,否则为0.

    然而词袋模型仅仅将文本看做词的汇合,不思考词序信息,难以精准示意文本信息。因而咱们有了第二种办法:N元特色,即每N个间断词形成一个根本单元,而后用词袋模型表示。

    (3)示意学习。示意学习就是让机器主动的学习出无效的特色,从而防止了间接应用原始特色对机器学习能力的高要求,以及人工特征提取带来的人力物力节约

    传统的特色学习

    传统的特色学习,即通过人为的设计一些准则,而后依据这些准则选取无效的特色。特色学习次要有两种办法,特征选择和特色抽取

    特征选择

    特征选择,选取原始特色汇合的一个子集,使得基于这个子集训练的模型准确率最高。实际上就是保留无效特色,移除冗余特色

    • 子集搜寻。应用贪婪策略:由空集合开始,每一轮增加该轮最优的特色(前向搜索);或者从原始特色汇合开始,每次删除最冗余的特色(反向搜寻)

    子集搜寻又分为过滤式办法和包裹式办法:

    特色抽取

    特征选择和特色抽取能够在不失落原始特色信息的前提下,去掉噪声信息,缩小特色数量。也就进而缩小了特征向量的维度,所以特征选择和特征提取也常常称为降维

    深度学习

    传统的机器学习中,特征提取和预测模型的学习是拆散的,机器学习模型仅仅指后边依据提取到的特色学习模型。

    而深度学习则将特色学习和模型的预测学习有机对立到一个模型中,从而防止了两者准则的不一致性

    深度学习办法的难点在于如何评估示意学习对最终零碎输入后果的奉献或影响,即贡献度调配问题.目前比拟无效的模型是神经网络,行将最初的输入层作为预测学习,其余层作为示意学习.

    评估指标

    机器学习中的驰名实践和定理

    PAC学习实践

    在机器学习中,通常用教训或屡次试验来抉择适合的模型、训练样本数据等,然而这样往往不太牢靠,老本也较高。

    为此咱们提出了计算学习实践,来剖析问题难度、计算模型能力,领导机器学习模型和算法的设计。计算学习实践中,最根底的实践就是可能近似正确(PAC)学习实践

    • 机器学习中,一个要害的问题是冀望谬误和教训谬误间的差别,称为泛化谬误。泛化谬误决定了机器学习模型是否精准的预测未知数据

    因为咱们不可能晓得所有数据的实在散布,因而冀望学习到一个冀望谬误为0的函数是不切实际的。所以,咱们升高建模的冀望,只要求可能有肯定概率学习到一个近似正确的假如,这就是PAC学习。

    • PAC学习能够分为两局部了解:

    (1)近似正确(Approximately Correct):要求泛化谬误小于某个值,来保障模型能够较好的预测到未知数据
    (2)可能(Probably):机器学习有‘可能’(肯定概率)学习到这样一个近似正确的假如,不是肯定能学习到

    • 在机器学习中,模型越简单,模型泛化能力越差,达到雷同泛化能力须要的样本数量越多。当然,咱们也能够通过正则化来限度模型的复杂度
    没有收费午餐定理

    任何算法都有局限性,不存在一种算法适合于所有的畛域和工作

    奥卡姆剃刀原理:若无必要,勿增实体

    简略的模型泛化能力更好,因而有两个性能相近的模型时,咱们会抉择更为简略的模型。这也就是在机器学习的学习准则中,咱们常常引入参数正则化,来限度模型能力,防止过拟合

    在机器学习中,咱们在保障模型性能相近的状况下,要尽可能的是模型简略,这就是奥卡姆剃刀原理

    丑小鸭定理:丑小鸭与白天鹅之间的区别和两只白天鹅之间的区别一样大(这里的丑小鸭指的是白天鹅的幼雏,而不是俊俏的小鸭子)

    世界上不存在相似性的主观规范,所有相似性的规范都是主观的。

    如果从体型大小或外貌的角度来看,丑小鸭和白天鹅的区别大于两只白天鹅的区别;然而如果从基因的角度来看,丑小鸭与它父母的差异要小于它父母和其余白天鹅之间的差异.

    演绎偏置

    在机器学习中,很多学习算法常常会对学习的问题做一些假如,这些假如就 称为演绎偏置.

    比方在最近邻分类器中,咱们 会假如在特色空间中,一个小的部分区域中的大部分样本同属一类.在奢侈贝叶 斯分类器中,咱们会假如每个特色的条件概率是相互独立的.

    演绎偏置在贝叶斯学习中也常常称为先验.

    总结

    • 机器学习算法尽管品种繁多,然而基本要素就三个:模型、学习准则、优化算法。大部分机器学习算法,实际上就是这三个基本要素的不同组合。值得注意的是,雷同的模型也能够有不同的学习算法,比方线性分类模型有感知器、Logistic 回归和反对向量机,它们之间的差别在于应用了不同的学习准则和优化算法
    • 此外,机器学习的一个重要内容是示意学习。传统的示意学习办法包含特征选择和特色抽取
  • 关于机器学习:技术博客生成式对抗网络模型综述

    生成式反抗网络模型综述

    作者:张真源

    GAN

    GAN简介

    生成式反抗网络(Generative adversarial networks,GANs)的核心思想源自于零和博弈,包含生成器和判断器两个局部。生成器接管随机变量并生成“假”样本,判断器则用于判断输出的样本是实在的还是合成的。两者通过互相反抗来取得彼此性能的晋升。判断器所作的其实就是一个二分类工作,咱们能够计算他的损失并进行反向流传求出梯度,从而进行参数更新。

    GAN的优化指标能够写作:
    $$\large\min_G\max_DV(D,G)= \mathbb{E}_{x\sim p_{data}}[\log D(x)]+\mathbb{E}_{z\sim p_z(z)}[log(1-D(G(z)))]$$
    其中$$\log D(x)$$代表了判断器甄别实在样本的能力,而$$D(G(z))$$则代表了生成器坑骗判断器的能力。在理论的训练中,生成器和判断器采取交替训练,即先训练D,而后训练G,一直往返。

    WGAN

    在上一部分咱们给出了GAN的优化指标,这个指标的实质是在最小化生成样本与实在样本之间的JS间隔。然而在试验中发现,GAN的训练十分的不稳固,常常会陷入坍缩模式。这是因为,在高维空间中,并不是每个点都能够示意一个样本,而是存在着大量不代表实在信息的无用空间。当两个散布没有重叠时,JS间隔不能精确的提供两个散布之间的差别。这样的生成器,很难“捕获”到低维空间中的实在数据分布。因而,WGAN(Wasserstein GAN)的作者提出了Wasserstein间隔(推土机间隔)的概念,其公式能够进行如下示意:
    $$\large W(\mathbb P_r,\mathbb P_g)=\inf_{\gamma\sim\prod{\mathbb P_r,\mathbb P_g}}\mathbb E_{(x,y)~\gamma}[\|x-y\|]$$
    这里$$\prod{\mathbb P_r,\mathbb P_g}$$指的是实在散布$$\mathbb P_r$$和生成散布$$\mathbb P_g$$的联结散布所形成的汇合,$$(x,y)$$是从$$\gamma$$中获得的一个样本。枚举两者之间所有可能的联结散布,计算其中样本间的间隔$$\|x-y\|$$,并取其冀望。而Wasserstein间隔就是两个散布样本间隔冀望的下界值。这个简略的改良,使得生成样本在任意地位下都能给生成器带来适合的梯度,从而对参数进行优化。

    DCGAN

    卷积神经网络近年来获得了夺目的问题,展示了其在图像处理畛域独特的劣势。很天然的会想到,如果将卷积神经网络引入GAN中,是否能够带来成果上的晋升呢?DCGAN(Deep Convolutional GANs)在GAN的根底上优化了网络结构,用齐全的卷积代替了全连贯层,去掉池化层,并采纳批标准化(Batch Normalization,BN)等技术,使得网络更容易训练。

    用DCGAN生成图像

    为了更不便精确的阐明DCGAN的关键环节,这里用一个简化版的模型实例来阐明。代码基于pytorch深度学习框架,数据集采纳MNIST

    import torch
    import torch.nn as nn
    import torchvision
    from torchvision import transforms
    from torchvision.utils import save_image
    import os  
    #定义一些超参数
    nc = 1        #输出图像的通道数
    nz = 100          #输出噪声的维度
    num_epochs = 200  #迭代次数
    batch_size = 64      #批量大小
    sample_dir = 'gan_samples'
    # 后果的保留目录
    if not os.path.exists(sample_dir):
        os.makedirs(sample_dir)
    # 加载MNIST数据集
    trans = transforms.Compose([
                    transforms.ToTensor(),transforms.Normalize([0.5], [0.5])])
    mnist = torchvision.datasets.MNIST(root=r'G:\VsCode\ml\mnist',
                                       train=True,
                                       transform=trans,
                                       download=False)
    data_loader = torch.utils.data.DataLoader(dataset=mnist,
                                              batch_size=batch_size,  
                                              shuffle=True)

    判断器&生成器

    判断器应用LeakyReLU作为激活函数,最初通过Sigmoid输入,用于虚实二分类
    生成器应用ReLU作为激活函数,最初通过tanh将输入映射在[-1,1]之间

    # 构建判断器
    class Discriminator(nn.Module):
        def __init__(self, in_channel=1, num_classes=1):
            super(Discriminator, self).__init__()
            self.conv = nn.Sequential(
                # 28 -> 14
                nn.Conv2d(nc, 512, 3, stride=2, padding=1, bias=False),
                nn.BatchNorm2d(512),
                nn.LeakyReLU(0.2),
                # 14 -> 7
                nn.Conv2d(512, 256, 3, stride=2, padding=1, bias=False),
                nn.BatchNorm2d(256),
                nn.LeakyReLU(0.2),
                # 7 -> 4
                nn.Conv2d(256, 128, 3, stride=2, padding=1, bias=False),
                nn.BatchNorm2d(128),
                nn.LeakyReLU(0.2),
                nn.AvgPool2d(4),
            )
            self.fc = nn.Sequential(
                # reshape input, 128 -> 1
                nn.Linear(128, 1),
                nn.Sigmoid(),
            )
       
        def forward(self, x, label=None):
            y_ = self.conv(x)
            y_ = y_.view(y_.size(0), -1)
            y_ = self.fc(y_)
            return y_
    # 构建生成器
    class Generator(nn.Module):
        def __init__(self):
            super(Generator, self).__init__()
            self.fc = nn.Sequential(
                nn.Linear(nz, 4*4*512),
                nn.ReLU(),
            )
            self.conv = nn.Sequential(
                # input: 4 by 4, output: 7 by 7
                nn.ConvTranspose2d(512, 256, 3, stride=2, padding=1, bias=False),
                nn.BatchNorm2d(256),
                nn.ReLU(),
                # input: 7 by 7, output: 14 by 14
                nn.ConvTranspose2d(256, 128, 4, stride=2, padding=1, bias=False),
                nn.BatchNorm2d(128),
                nn.ReLU(),
                # input: 14 by 14, output: 28 by 28
                nn.ConvTranspose2d(128, 1, 4, stride=2, padding=1, bias=False),
                nn.Tanh(),
            )
           
        def forward(self, x, label=None):
            x = x.view(x.size(0), -1)
            y_ = self.fc(x)
            y_ = y_.view(y_.size(0), 512, 4, 4)
            y_ = self.conv(y_)
            return y_

    训练模型

    # 应用GPU
    device = torch.device('cuda' if torch.cuda.is_available() else 'cpu')
    D = Discriminator().to(device)
    G = Generator().to(device)
    # 损失函数及优化器
    criterion = nn.BCELoss()
    D_opt = torch.optim.Adam(D.parameters(), lr=0.001, betas=(0.5, 0.999))
    G_opt = torch.optim.Adam(G.parameters(), lr=0.001, betas=(0.5, 0.999))
    def denorm(x):
        out = (x + 1) / 2
        return out.clamp(0, 1)
    def reset_grad():
        d_optimizer.zero_grad()
        g_optimizer.zero_grad()
    for epoch in range(num_epochs):
        for i, (images, labels) in enumerate(data_loader):
            images = images.to(device)
            real_labels = torch.ones(batch_size, 1).to(device)
            fake_labels = torch.zeros(batch_size, 1).to(device)
            #————————————————————训练判断器——————————————————————
            #甄别实在样本
            outputs = D(images)
            d_loss_real = criterion(outputs, real_labels)
            real_score = outputs
            #甄别生成样本
            z = torch.randn(batch_size, nz).to(device)
            fake_images = G(z)
            outputs = D(fake_images)
            d_loss_fake = criterion(outputs, fake_labels)
            fake_score = outputs        
          #计算梯度及更新
            d_loss = d_loss_real + d_loss_fake      
            reset_grad()
            d_loss.backward()
            d_optimizer.step()
            #————————————————————训练生成器——————————————————————
            z = torch.randn(batch_size, nz).to(device)
            fake_images = G(z)
            outputs = D(fake_images)
            g_loss = criterion(outputs, real_labels)
            #计算梯度及更新
            reset_grad()
            g_loss.backward()
            g_optimizer.step()
           
            if (i+1) % 200 == 0:
                print('Epoch [{}/{}], Step [{}/{}], d_loss: {:.4f}, g_loss: {:.4f}, D(x): {:.2f}, D(G(z)): {:.2f}'  
                      .format(epoch, num_epochs, i+1, total_step, d_loss.item(), g_loss.item(),  
                              real_score.mean().item(), fake_score.mean().item()))
        # 保留生成图片
        fake_images = fake_images.reshape(fake_images.size(0), 1, 28, 28)
        save_image(denorm(fake_images), os.path.join(sample_dir, 'fake_images-{}.png'.format(epoch+1)))
    # 保留模型
    torch.save(G.state_dict(), 'G.ckpt')
    torch.save(D.state_dict(), 'D.ckpt')

    可视化后果

    reconsPath = './gan_samples/fake_images-200.png'
    Image = mpimg.imread(reconsPath)
    plt.imshow(Image)
    plt.axis('off')
    plt.show()

    cGAN

    在之前介绍的几种模型中,咱们留神到生成器的输出都是一个随机的噪声。能够认为这个高维噪声向量提供了一些要害信息,而生成器依据本人的了解将这些信息进行补充,最终生成须要的图像。生成器生成图片的过程是齐全随机的。例如上述的MNIST数据集,咱们不能管制它生成的是哪一个数字。那么,有没有办法能够对其做肯定的限度束缚,来让生成器生成咱们想要的后果呢?cGAN(Conditional Generative Adversarial Nets)通过增一个额定的向量y对生成器进行束缚。以MNIST分类为例,限度信息y能够取10维的向量,对于类别进行one-hot编码,并与噪声进行拼接一起输出生成器。同样的,判断器也将原来的输出和y进行拼接。作者通过各种试验证实了这个简略的改良的确能够起到对生成器的束缚作用。

    判断器&生成器

    只须要在前向流传的过程中退出限度变量y,咱们很容易就能失去cGAN的生成器和判断器模型

    class Discriminator(nn.Module):
        ...
        def forward(self, x, label):
            label = label.unsqueeze(2).unsqueeze(3)
            label = label.repeat(1, 1, x.size(2), x.size(3))
            x = torch.cat(tensors=(x, label), dim=1)
            y_ = self.conv(x)
            ...
    class Generator(nn.Module):
        ...
        def forward(self, x, label):
            x = x.unsqueeze(2).unsqueeze(3)
            label = label.unsqueeze(2).unsqueeze(3)
            x = torch.cat(tensors=(x, label), dim=1)
            y_ = self.fc(x)
            ...

    Pix2Pix

    在下面的cGAN例子中,咱们的管制信息取的是想要图像的标签,如果这个管制信息更加的丰盛,例如输出一整张图像,那么它是否实现一些更加高级的工作?Pix2Pix(Image-to-Image Translation with Conditional Adversarial Networks)将这一类问题演绎为图像到图像的翻译,其应用改良后的U-net作为生成器,并设计了新鲜的Patch-D判断器构造来输入高清的图像。Patch-D是指,不论网络所应用的输出图像有多大,都将其切割成若干个固定大小的Patch,判断器只需对这些Patch的虚实进行判断。因为L1损失曾经能够掂量生成图像和实在图像的全局差别,所以作者认为判断器只须要用Patch-D这样更关注于部分差别的构造即可。同时Patch-D的构造使得网络的输出变小,缩小了计算量并且增大了框架的扩展性。

    CycleGAN

    Pix2Pix尽管能够生成高清的图像,但其存在一个致命的毛病:须要互相配对的图片x与y。在现实生活中,这样成对的图片很难或者基本不可能收集到,这就大大的限度了Pix2Pix的利用。对此,CycleGAN(Unpaired Image-to-Image Translation using Cycle-Consistent Adversarial Networks)提出了不须要配对的图像翻译办法。

    CycleGAN其实就是一个X->Y的单向GAN上再加一个Y->X的单向GAN,形成一个“循环”。网络的构造和单次训练过程如下(图片来自于量子位):


    除了经典的根底GAN损失之外,CycleGAN还引入了Consistency loss的概念。循环统一损失使得X->Y转变的过程中必须保留有X的局部个性。循环损失的公式如下:
    $$\large L_{cyc}(G,F)=\mathbb E_{x\sim p_{data}(x)}[\|F(G(x))-x\|_1]+\mathbb E_{y\sim p_{data}(y)}[\|G(F(x))-y\|_1]$$
    两个判断器的损失示意如下:
    $$\large \textit{L}_{GAN}(G,D_Y,X,Y)=\mathbb E_{y\sim p_{data}(y)}[logD_Y(y)]+\mathbb E_{x\sim p_{data}(x)}[log(1-D_Y(G(x)))]$$$$\large \textit{L}_{GAN}(F,D_X,Y,X)=\mathbb E_{x\sim p_{data}(x)}[logD_X(x)]+\mathbb E_{y\sim p_{data}(y)}[log(1-D_X(F(y)))]$$
    最初网络的优化指标能够示意为
    $$\large \min _{G_{X\rightarrow Y},G_{Y\rightarrow X}}\max_{D_X,D_Y} L(G,F,D_x,D_y)=L_{GAN}(G,D_Y,X,Y)+L_{GAN}(F,D_X,Y,X)+\lambda L_{cyc}(G,F)$$
    Pix2Pix以及CycleGAN的官网复现入口:https://github.com/junyanz/pytorch-CycleGAN-and-pix2pix

    StarGAN

    Pix2Pix解决了有配对图像的翻译问题,CycleGAN解决了无配对图像的翻译问题,然而他们所作的图像到图像翻译,都是一对一。假如当初须要将人脸转换为喜怒哀乐四个表情,那么他们就须要进行4次不同的训练,这无疑会消耗微小的计算资源。针对于这个问题,StarGAN(StarGAN: Unified Generative Adversarial Networks for Multi-Domain Image-to-Image Translation)借助cGAN的思维,在网络输出中退出一个域的管制信息。对于判断器,其不仅须要甄别样本是否实在,还须要判断输出的图像来自哪个域。StarGAN的训练过程如下:

    1. 将原始图片c和指标生成域c进行拼接后丢入生成器失去生成图像G(x,c)
    2. 将生成图像G(x,c)和实在图像y别离丢入判断器D,判断器除了须要判断输出图像的真伪之外,还须要判断它来自哪个域
    3. 将生成图像G(x,c)和原始生成域c’丢入生成器生成重构图片(为了对生成器生成的图像做进一步的限度,与CycleGAN的重构损失相似)


    理解了StarGAN的训练过程,咱们很容易失去其损失函数各项的表达形式
    首先是GAN的个别损失,这里作者采纳了前文所述的WGAN的损失模式:
    $$\large L_{adv}=\mathbb E_x[D_{src}(x)]-\mathbb E_{x,c}[D_{src}(G(x,c)))]-\lambda_{gp}\mathbb E_{\hat x}[(\|\nabla _\hat xD_{src}(\hat x)\|_2-1)^2]$$
    对于判断器,咱们须要激励其将输出图像正确的分类到指标域c‘(原始生成域):
    $$\large L_{src}^r=\mathbb E_{x,c’}[-logD_{cls}(c’|x)]$$

    对于生成器,咱们须要激励其胜利坑骗判断器将图片分类到指标域c(指标生成域),此外,生成器还须要在以生成图像和原始生成域c’的输出下胜利将图像还原回去,这两局部的损失示意如下:
    $$\largeL_{src}^f=\mathbb R_{x,c}[-logD_{cls}(c|G(x,c))]$$
    $$\large L_{rec}=\mathbb E_{x,c,c’}[\|x-G(G(x,c),c’)\|_1]$$
    各局部损失乘上本人的权重加总后就形成了判断器和生成器的总损失:
    $$\largeL_D=-L_{adv}+\lambda_{cls}L_{cls}^{r} $$
    $$\large L_G=L_{adv}+\lambda_{cls}L_{clas}^f+\lambda_{rec}L_{rec}$$
    此外,为了更具备通用性,作者还退出了mask vector来适应不同的数据集之间的训练。

    总结

    名称 翻新点
    DCGAN 首次将卷积神经网络引入GAN中
    cGAN 通过拼接标签信息来管制生成器的输入
    Pix2Pix 提出了一种图像到图像翻译的通用办法
    CycleGAN 解决了Pix2Pix须要图像配对的问题
    StarGAN 提出了一种一对多的图像到图像的翻译办法
    InfoGAN 基于cGAN改良,提出一种无监督的生成办法,实用于不晓得图像标签的状况
    LSGAN 用最小二乘损失函数代替原始GAN的损失函数,缓解了训练不稳固、生成图像不足多样性的问题
    ProGAN 在训练期间逐渐增加新的高分辨率层,能够生成高分辨率的图像
    SAGAN 将注意力机制引入GAN当中,简洁高效利用了全局信息

    本文列举了生成式反抗网络在倒退过程中一些具备代表性的网络结构。GANs现在已广泛应用于图像生成、图像去噪、超分辨、文本到图像的翻译等各个领域,且在近几年的钻研中涌现了很多优良的论文。感兴趣的同学能够从上面的链接中pick本人想要理解的GAN~

    • THE-GAN-ZOO:汇总了各种GAN的论文及代码地址。
    • GAN Timeline:依照工夫线对不同的GAN进行了排序。
    • Browse state-of-the-art:将ArXiv上的最新论文与GitHub代码相关联,并做了比拟排序,波及了深度学习的各个方面。

    参考文献

    1. Goodfellow I, Pouget-Abadie J, Mirza M, et al. Generative adversarial nets[C]//Advances in neural information processing systems. 2014: 2672-2680.
    2. Arjovsky M, Chintala S, Bottou L. Wasserstein gan[J]. arXiv preprint arXiv:1701.07875, 2017.
    3. Radford A, Metz L, Chintala S. Unsupervised representation learning with deep convolutional generative adversarial networks[J]. arXiv preprint arXiv:1511.06434, 2015.
    4. Mirza M, Osindero S. Conditional generative adversarial nets[J]. arXiv preprint arXiv:1411.1784, 2014.
    5. Isola P, Zhu J Y, Zhou T, et al. Image-to-image translation with conditional adversarial networks[C]//Proceedings of the IEEE conference on computer vision and pattern recognition. 2017: 1125-1134.
    6. Zhu J Y, Park T, Isola P, et al. Unpaired image-to-image translation using cycle-consistent adversarial networks[C]//Proceedings of the IEEE international conference on computer vision. 2017: 2223-2232.
    7. Choi Y, Choi M, Kim M, et al. Stargan: Unified generative adversarial networks for multi-domain image-to-image translation[C]//Proceedings of the IEEE conference on computer vision and pattern recognition. 2018: 8789-8797.
    8. Mao X, Li Q, Xie H, et al. Least squares generative adversarial networks[C]//Proceedings of the IEEE international conference on computer vision. 2017: 2794-2802.
    9. Karras T, Aila T, Laine S, et al. Progressive growing of gans for improved quality, stability, and variation[J]. arXiv preprint arXiv:1710.10196, 2017.
    10. Chen X, Duan Y, Houthooft R, et al. Infogan: Interpretable representation learning by information maximizing generative adversarial nets[C]//Advances in neural information processing systems. 2016: 2172-2180.
    11. Zhang H, Goodfellow I, Metaxas D, et al. Self-attention generative adversarial networks[C]//International Conference on Machine Learning. 2019: 7354-7363.

    对于咱们

    Mo(网址:https://momodel.cn) 是一个反对 Python的人工智能在线建模平台,能帮忙你疾速开发、训练并部署模型。

    近期 Mo 也在继续进行机器学习相干的入门课程和论文分享流动,欢送大家关注咱们的公众号(MomodelAI)获取最新资讯!

  • 关于机器学习:自研数据标注服务平台数据服务商科技化转型关键一步丨曼孚科技

    人工智能行业次要以有监督学习的模型训练形式为主,对于标注数据有着强依赖性需要。

    数据标注是对未经解决的高级数据, 包含语音、图片、文本、视频等进行加工解决, 并转换为机器可辨认信息的过程。​

    原始数据个别通过数据采集取得, 随后的数据标注相当于对数据进行加工, 而后输送到人工智能算法和模型里实现调用。

    简略来说,数据标注就是数据标注员借助标注工具,对图像、文本、语音、视频等数据进行拉框、描点、转写等操作,以产出满足AI机器学习标注数据集的过程。

    在这个过程中,数据标注工具是外围,为原始数据赋予了新的意义。目前,数据标注工具平台化是行业倒退的重要趋势之一。所谓工欲善其事,必先利其器,一款优质的数据标注服务平台该当具备如下特色:

    1.全流程工作流体系

    广义的数据标注是指对原始数据进行拉框、描点、转写等操作,但在一个残缺的标注我的项目里,标注过程只是我的项目中的一部分。

    失常状况下,一个残缺的标注我的项目,从开始到完结要历经我的项目创立、标注、审核、质检、数据导出等多个流程。每个独自流程下又能够分为更为具体的工作流。

    以我的项目创立为例,从新建到公布须要实现以下环节的设置:

    新建我的项目-上传数据-需要治理-标注计划-团队设置-角色权限计划-标注后果导出设置-公布我的项目。

    对于项目经理与我的项目方而言,一个欠缺且运行顺畅的工作流体系,对于项目管理意义重大。

    全流程工作流体系,能够无效加强我的项目方对于我的项目整体的把控,躲避无意义的额定工作老本,成倍晋升我的项目运行效率。

    2.可视化数据管理

    从角色配置角度来看,数据标注平台的使用者大抵能够分为标注员、审核员、质检员、管理员(项目经理、甲方代表)等。

    不同的角色领有不同的权限,同时也对应不同的工作内容。以标注员为例,标注员的工作就是根底的标注,所以其比较关心的是数据实现量、数据驳回量、数据合格量,因为这些事关本身的支出。

    而项目经理关怀的内容就比拟多了,比方我的项目的实现量、残余量、数据品质、角色权限调配、我的项目工期等等。

    一个人的精力总是无限的,当接触到的数据越多,脱漏数据、出问题的概率就会越大,所以平台数据可视化就显得尤为重要。

    通过对不同角色的相干数据进行自动化整顿剖析,生成专属角色的个性化数据分析统计,简练直观展示外围重要数据,帮忙不同角色疾速把握我的项目运行状况,不仅无效缩短理解我的项目所须要的工夫,同时也能够躲避诸多谬误问题的产生。

    3.AI技术加持

    数据标注为AI行业的倒退提供数据反对,AI技术也会反哺数据标注行业的晋升。

    在数据处理环节,以语音转写为例,标注员须要凝听每个词语的发音,进行判断并转写,这对标注员在长时间多任务下的专一力有着极高要求。通过在标注环节引入AI预标注技术,平台自身会自动识别转写语音内容,标注员只须要在预标注的后果上稍微修改即可。

    除了在标注环节引入AI技术,审核与质检环节AI同样能够施展重要作用。AI技术的加持,不仅能够大幅加重人力老本,而且能够成倍晋升效率,实现更少的人实现更多的工作。

    随着数据标注行业业务需要的多样化以及复杂度的晋升,以往性能繁多的标注工具在能力和效率上愈发显得顾此失彼,不仅制约了产能的晋升,还会因为扩充规模而陷入边际效益低的漩涡,为企业的经营减少了很多不确定的因素。

    因而,领有一套贯通数据标注各环节,并且能对我的项目进行全流程治理的一站式数据标注服务平台,能够助力企业更好地晋升效率,灵便适配标注需要,并精确把控数据安全与品质,为AI行业提供更多、更高质量的标注数据集,助力提速AI商业化落地过程。

  • 关于机器学习:深度学习中的正则化一

    • 本文首发自公众号:RAIS,点击间接关注。

    前言

    本系列文章为《Deep Learning》读书笔记,能够参看原书一起浏览,成果更佳。本文咱们聊一聊深度学习中的正则化。

    深度学习中的正则化

    一般来说,深度学习所要做的事件是用已有的训练集训练一个网络模型,而后针对新的数据给出预测,咱们冀望咱们的模型在训练集和测试集上都有良好的体现,然而有的时候两者不可兼得。一种状况是在训练集上体现很好,在测试集上体现不好或体现个别;另一种状况是在训练集上体现不好或体现个别,在测试集上体现很好。相比较而言咱们更偏向于后者,因为这是咱们训练模型的目标。

    为什么会呈现这种状况,难道不是应该训练集上体现的越好在测试集上体现越好吗?不是的,咱们在后面的文章中剖析过,适度的拟合一个训练集往往会放大哪些没有那么重要的向量或因素,过拟合会导致泛化能力的降落,正则化就是为了减小测试误差的,尽管有的时候可能会以增大训练误差为代价,然而这是值得的,这些策略统称为正则化。上面给出一个简略的非谨严的正则化定义:

    正则化:减小泛化误差而不是训练误差所做的对算法的批改

    咱们常常会对预计进行正则化,预计的正则化采取的形式是以偏差的增大来换取方差的减小,尤其是显著的减小方差而较小的增大偏差往往是咱们谋求的指标。接下来咱们就别离剖析介绍一下正则化的策略。

    正则化的策略

    参数范数惩办

    $$
    \widetilde{J}(θ; X, y) = J(θ; X, y) + αΩ(θ), α∈[0, ∞)
    $$

    α 是惩办参数,当 α 为 0 时代表没有惩办;Ω 是范数惩办项;J 为指标。神经网络中,参数包含每一层的仿射变换的权重和偏置,咱们只对权重做惩办。

    L2 正则化(权重衰减)

    感知有较高方差输出,与输入指标协方差较小的特色的权重会膨胀。

    $$
    指标函数:\widetilde{J}(θ; X, y) = J(θ; X, y) + \frac{α}{2}w^Tw,Ω(θ)=\frac{1}{2}||w||^2_2
    $$

    $$
    梯度:\nabla_w\widetilde{J}(θ;X,y)=αw+\nabla_wJ(θ;X,y)
    $$

    $$
    单步梯度降落更新权重:w\leftarrow w-\epsilon(αw+\nabla_wJ(θ;X,y))
    $$

    L1 正则化

    $$
    指标函数:\widetilde{J}(θ; X, y) = J(θ; X, y) + α||w||_1
    $$

    $$
    梯度:\nabla_w\widetilde{J}(θ;X,y)=αsign(w)+\nabla_wJ(θ;X,y)
    $$

    总结

    本文形容了正则化策略中最常见的一种,参数范数惩办,并介绍了 L2 和 L1 两种最常见的范数惩办策略。

    • 本文首发自公众号:RAIS,点击间接关注。
  • 关于机器学习:如何用R语言在机器学习中建立集成模型

    原文链接:http://tecdat.cn/?p=6608

    介绍

     大多数时候,我可能破解特色工程局部,但可能没有应用多个模型的汇合。 

    在本文中,我将向您介绍集成建模的基础知识。 另外,为了向您提供无关汇合建模的实践经验,咱们将应用R对hackathon问题进行集成。

    1.什么是集成?

    通常,集成是一种组合两种或多种相似或不同类型算法的技术,称为根底学习者。这样做是为了建设一个更加强壮的零碎,其中蕴含了所有根底学习者的预测。能够了解为多个交易者之间的会议室会议,以决定股票的价格是否会上涨。

    因为他们都对股票市场有不同的了解,因而从问题陈说到冀望的后果有不同的映射性能。因而,他们应该依据本人对市场的了解对股票价格做出各种预测。

    2.汇合的类型

    在进一步具体介绍之前,您应该理解的一些基本概念是:

    • 均匀:它被定义为 在回归问题的状况下或在预测分类问题的概率时从模型中获取预测的平均值。 
    • 少数投票:它被 定义为 在预测分类问题的后果的同时,从多个模型预测中以最大投票/举荐进行预测。 
    • 加权平均值:在此,不同的权重利用于来自多个模型的预测,而后取平均值 。 

     这些是一些次要应用的技术:

    1. Bagging: Bagging也称为bootstrap聚合。 

    加强的一些例子是XGBoost,GBM,ADABOOST等。

    1. 重叠:在重叠多层机器时,学习模型彼此叠加,每个模型将其预测传递给下面层中的模型,顶层模型依据模型上面的模型输入做出决策。

    3.汇合的长处和毛病

    3.1长处

    • 集成是一种通过验证的办法,能够进步模型的准确性,实用于大多数状况。
    •  集成使模型更加持重和稳固,从而确保在大多数状况下测试用例具备良好的性能。
    • 您能够应用集成来捕捉数据中的线性和简略以及非线性简单关系。这能够通过应用两个不同的模型并造成两个汇合来实现。

    3.2毛病

    • 集成缩小了模型的可解释性,并且很难在最初绘制任何要害的业务见解。
    • 这十分耗时,因而可能不是实时应用程序的最佳抉择。

    4.在R中施行汇合的实用指南

    #让咱们看一下数据集数据的构造 'data.frame':614 obs。13个变量:$ ApplicantIncome:int 5849 4583 3000 2583 6000 5417 2333 3036 4006 12841 ...$ CoapplicantIncome:num 0 1508 0 2358 0 ...$ LoanAmount:int NA 128 66 120 141 267 95 158 168 349 ...$ Loan_Amount_Term:int 360 360 360 360 360 360 360 360 360 360 ...$ Credit_History:int 1 1 1 1 1 1 1 0 1 1 ...#应用中位数输出缺失值preProcValues < -  preProcess(data,method = c(“medianImpute”,“center”,“scale”))
    #Spliting训练依据后果分为两局部:75%和25%index < -  createDataPartition(data_processed $ Loan_Status,p = 0.75,list = FALSE)trainSet < -  data_processed [index,]testSet < -  data_processed [-index,]

    我将数据分成两局部,我将用它来模拟训练和测试操作。咱们当初定义训练控件以及预测变量和后果变量:

    #定义多个模型的训练控件fitControl < -  trainControl(  method =“cv”, savePredictions ='final',classProbs = T)#Defining预测器和后果

    当初让咱们开始训练随机​​森林并在咱们创立的测试集上测试其准确性:

    #查看随机森林模型的准确性 混同矩阵和统计参考预测N Y.N 28 20Y 9 96准确度:0.8105         95%CI:(0.7393,0.8692)无信息率:0.7582         P值[Acc> NIR]:0.07566        Kappa:0.5306         Mcnemar的测试P值:0.06332        灵敏度:0.7568         特异性:0.8276         Pos Pred价值:0.5833         Neg Pred值:0.9143         患病率:0.2418         检测率:0.1830         检测风行率:0.3137         均衡准确度:0.7922         '侧面'类:N

     咱们应用随机森林模型取得了0.81的准确度。让咱们看看KNN的体现:

    #训练knn模型 #Predicting应用knn模型testSet $ pred_knn <-predict(object = model_knn,testSet [,predictors])#查看随机森林模型的准确性 混同矩阵和统计参考预测N Y.N 29 19是2 103准确度:0.8627        95%CI:(0.7979,0.913)无信息率:0.7974        P值[Acc> NIR]:0.0241694      Kappa:0.6473        Mcnemar的测试P值:0.0004803     灵敏度:0.9355        特异性:0.8443        Pos Pred价值:0.6042        Neg Pred值:0.9810        患病率:0.2026        检测率:0.1895        检测风行率:0.3137        均衡准确度:0.8899        '侧面'类:N

     咱们可能通过独自的KNN模型取得0.86的准确度。在咱们持续创立这三者的汇合之前,让咱们看看Logistic回归的体现。

    #Training Logistic回归模型 #Predicting应用knn模型testSet $ pred_lr <-predict(object = model_lr,testSet [,predictors])#查看随机森林模型的准确性 混同矩阵和统计参考预测N Y.N 29 19是2 103准确度:0.8627        95%CI:(0.7979,0.913)无信息率:0.7974        P值[Acc> NIR]:0.0241694     Kappa:0.6473        Mcnemar的测试P值:0.0004803     灵敏度:0.9355        特异性:0.8443        Pos Pred价值:0.6042        Neg Pred值:0.9810        患病率:0.2026        检测率:0.1895        检测风行率:0.3137        均衡准确度:0.8899        '侧面'类:N

    逻辑回归也给出了0.86的准确度。

    当初,让咱们尝试用这些模型造成汇合的不同办法,如咱们所探讨的:

    • 均匀:在此,咱们将均匀三个模型的预测。因为预测是“Y”或“N”,因而平均值对于此二进制分类没有多大意义。然而,咱们能够对察看概率的平均值进行均匀解决。
    #Predicting概率testSet $ pred_rf_​​prob <-predict(object = model_rf,testSet [,predictors],type ='prob')testSet $ pred_knn_prob <-predict(object = model_knn,testSet [,predictors],type ='prob')testSet $ pred_lr_prob <-predict(object = model_lr,testSet [,predictors],type ='prob') #Spits到0.5的二进制类 少数表决:在少数表决中,咱们将为大多数模型预测的察看指定预测。因为咱们有三个模型用于二进制分类工作,因而无奈实现平局。
    #少数投票 加权平均值:咱们能够采纳加权平均值,而不是采纳简略平均值。通常,对于更精确的模型,预测的权重很高。让咱们将0.5调配给logistic回归,将0.25调配给KNN和随机森林。
    #Taking加权均匀预测 #Spits到0.5的二进制类 在持续探讨之前,我想回顾一下咱们之前探讨过的对于个体模型精度和模型间预测相关性的两个重要规范,这些规范必须失去满足。在下面的汇合中,我曾经跳过查看三个模型的预测之间的相关性。我随机抉择了这三个模型来演示这些概念。如果预测高度相干,那么应用这三个预测可能不会比单个模型提供更好的后果。但你明确了。对?

    到目前为止,咱们在顶层应用了简略的公式。相同,咱们能够应用另一种机器学习模型,这实际上就是重叠。咱们能够应用线性回归来制作线性公式,用于在回归问题中进行预测,以便在分类问题的状况下将底层模型预测映射到后果或逻辑回归。

    在同一个例子中,让咱们尝试将逻辑回归和GBM利用为顶层模型。请记住,咱们将采取以下步骤:

    1. 在训练数据上训练各个根底层模型。
    2. 预测应用每个根底层模型来训练数据和测试数据。
    3. 当初,再次对顶层模型进行训练,对底层模型进行训练数据的预测。
    4. 最初,应用顶层模型预测底层模型的预测,这些模型是为测试数据而做出的。

    在步骤2中须要留神的一件十分重要的事件是,您应始终对训练数据进行包预测,否则根底层模型的重要性将仅取决于根底层模型能够如何调用训练数据。

    • 步骤1:在训练数据上训练各个根底层模型

    #Defining 管制fitControl < -  trainControl(method =“cv”, savePredictions ='final',#保留最佳参数组合的折叠预测classProbs = T#保留折叠预测的类概率)#Defining预测器和后果 #Training随机森林模型 #训练knn模型 #Training逻辑回归模型  
    • 步骤2:应用每个根底层模型预测训练数据和测试数据

    #Predicting训练数据的折叠预测概率 #Predicting测试数据的概率
    • 步骤3:当初再次训练顶层模型对底层模型的预测曾经对训练数据进行了预测

    首先,让咱们从GBM模型开始作为顶层模型。

     

    #Predictors用于顶层模型 predictors_top <-c( 'OOF_pred_rf', 'OOF_pred_knn', 'OOF_pred_lr') #GBM作为顶层模型 

    同样,咱们也能够应用逻辑回归创立一个汇合作为顶层模型。

     

    #Logistic回归作为顶层模型model_glm < -  ( [,predictors_top],  trControl = fitControl,tuneLength = 3)
    • 步骤4:最初,应用顶层模型预测曾经为测试数据而做出的底层模型的预测

    #predict应用GBM顶层模型测试集$ gbm_stacked <-predict(model_gbm,测试集[,predictors_top])#predict应用logictic回归顶层模型测试集$ glm_stacked <-predict(model_glm,测试集[,predictors_top])

    请留神, 抉择模型十分重要,以便从整体中获得最佳成果。咱们探讨的 拇指规定将极大地帮忙你。

     还有问题?分割咱们!

  • 关于机器学习:AWS-为机器学习推理开发的专用芯片你不想体验一下

    生存中很多教训通知咱们,很多状况下,一些「专用」的货色,往往比「通用」的在执行具体任务时成果更好,例如为了分担 CPU 负载,实现更强图形处理性能,电脑开始配置专用的图形处理器 GPU。这两年,随着机器学习技术的炽热,人们发现,用 GPU 来进行 ML 模型的训练也是一种比拟好的做法,速度更快,性能更强。

    然而毕竟 GPU 诞生的本意就是用于解决计算机图像的,并非「AI」专用,那么有没有专供机器学习应用的芯片,能够实现比 GPU 训练更快的速度,以及更低的老本?

    2019年底进行的年度 AWS re:Invent 大会上,最令人激动的新公布之一就是正式推出 AWS 本人设计和打造的 Inferentia 芯片,以更低成本提供更高性能的机器学习推理能力。

    机器学习推理是应用经过训练的模型做出预测的流程。经统计,在机器学习应用程序中,推理最多可能占到总成本的90%。其起因有二:

    1. 独立 GPU 实例通常专为模型训练而设计,而非用于推理。尽管训练作业可并行批量解决大量数据样本,但推理作业往往会实时处理单个输出,因此仅占用大量 GPU 计算。这使得独立 GPU 推理老本高且效率低。
    2. 独立 CPU 实例并非专门用于矩阵运算,因而对于深度学习推理而言通常太慢。其次,不同模型对 CPU、GPU 和内存有不同要求,对一种资源进行优化可能导致对其余资源的利用有余和更高的老本。

    对于机器学习推理而言,AWS Inferentia 芯片的劣势能够总结为:高性能,低提早,高易用。

    • 每个 AWS Inferentia 芯片有4个解决外围 Neuron Core,能在低功率下反对高达 128 TOPS 的性能。
    • AWS Inferentia 反对 FP16、BF16 和 INT8 数据类型,并且可接管 FP32 的训练模型输出,并应用 BF16 高速运行该模型。
    • AWS Inferentia 具备大容量片上存储,可用于缓存大型模型,从而无需将它们存储到片外,这使得 Neuron Core 可对模型进行高速拜访,对于升高推理提早具备显著影响。
    • AWS Inferentia 附带了 AWS Neuron SDK,可应用 AWS Inferentia 在风行框架中创立和训练简单的神经网络模型。
    • Neuron 由编译器、运行时和剖析工具组成,并事后集成到风行的机器学习框架中,包含 TensorFlow、Pytorch 和 MXNet。

    基于 AWS Inferentia 芯片,AWS 在云端提供了 EC2 Inf1 实例,将 Inferentia 芯片与 AWS Nitro 虚拟化管理程序、最新的第二代定制 Intel Xeon 可扩大处理器,以及高达 100Gbps 的网络相结合,以实现高吞吐量推理。这一配置使 Inf1 实例提供了 Amazon EC2 G4 实例3倍的吞吐量和40%推理老本的升高(基于应用 TensorFlow 端到端运行 BERT 模型的后果)。

    Inf1 实例的规格如下表所示。

    应用 AWS Inferentia 进行机器学习的典型流程如下图所示。通常,咱们会在 GPU 实例上训练机器学习模型,之后把训练好的模型利用 AWS Neuron 从新编译,而后将此模型交付给 Inf1 实例(AWS Inferentia 芯片)执行机器学习推理。

    上面,咱们通过一个样例来看看如何应用 AWS Neuron 在 AWS Inferentia 芯片上进行机器学习推理。

    在这里,咱们会用到 AWS Deep Learning AMI,它能够在 Amazon EC2 上一键式装置机器学习的各种框架工具,从而放慢在云中进行机器学习的速度。最新的 Deep Learning AMI 已反对 AWS Inferentia,并附带 AWS Neuron 开发所需的工具包(Neuron SDK)。

    咱们在 us-west-2 区域以 Deep Learning AMI (Ubuntu 18.04) Version 27.0 – ami-008d8ed4bd7dc2485 做为零碎镜像,启动 Inf1.2xlarge 实例。启动 Inf1 实例后,应用以下命令降级到最新版 Neuron 运行时环境和工具包:

    $ sudo apt-get update
     
    $ sudo apt-get install aws-neuron-runtime
     
    $ sudo apt-get install aws-neuron-tools

    随后咱们就能用 neuron-ls 命令显示 Inf1 实例上的 Inferentia 芯片数量和信息:

    $ neuron-ls
     
    +--------------+---------+--------+-----------+-----------+------+------+
     
    |   PCI BDF    | LOGICAL | NEURON |  MEMORY   |  MEMORY   | EAST | WEST |
     
    |              |   ID    | CORES  | CHANNEL 0 | CHANNEL 1 |      |      |
     
    +--------------+---------+--------+-----------+-----------+------+------+
     
    | 0000:00:1f.0 |       0 |      4 | 4096 MB   | 4096 MB   |    0 |    0 |
     
    +--------------+---------+--------+-----------+-----------+------+------+

    在输入的表格中,第一列显示了 PCI 总线设施性能 ID。第二列显示调配给设施的逻辑 ID。这个逻辑 ID 在 Neuron 运行时守护过程 (Runtime Daemon)(Neuron rtd)配置期间应用。第三列显示可用的 Neuron Core 数量。最初两列显示与任何其余 Inferentia 设施的连贯。

    因为咱们抉择的 Inf1.2xlarge 只有一个 Inferentia 芯片,所以这两列为空(如果启动 Inf1.6xlarge 或 Inf1.24xlarge 这两种带有多个 Inferentia 芯片的实例,这两列会显示 Inferentia 芯片的互联信息)。

    搭建好环境后,来看一下如何应用 AWS Neuron 和 Tensorflow 进行深度学习推理。整个过程分为两个阶段:编译阶段和推理阶段。

    在第一阶段,咱们将编译 TensorFlow Neuron 中预训练的 Keras ResNet50 模型,并将其导出为 SavedModel,一种 TensorFlow 模型的替换格局。

    首先激活 TensorFlow-Neuron conda 虚拟环境。应用虚拟环境可能确保在应用深度学习框架时对包的治理有最佳的灵活性,这也是深度学习的一个最佳实际。

    $ source activate aws_neuron_tensorflow_p36

    随后应用以下命令更新 Neuron 包到最新版本:

    $ conda update tensorflow-neuron

    接下来,创立一个名为 tensorflow_compile_resnet50.py 的 Python 脚本,此 Python 脚本应用 AWS Neuron 编译 Keras ResNet50 模型,并将其导出为 TensorFlow SavedModel 格局。

    import os
     
    import time
     
    import shutil
     
    import tensorflow as tf
     
    import tensorflow.neuron as tfn
     
    import tensorflow.compat.v1.keras as keras
     
    from tensorflow.keras.applications.resnet50 import ResNet50
     
    from tensorflow.keras.applications.resnet50 import preprocess_input
     
     
     
    # Create a workspace
     
    WORKSPACE = './ws_resnet50'
     
    os.makedirs(WORKSPACE, exist_ok=True)
     
     
     
    # Prepare export directory (old one removed)
     
    model_dir = os.path.join(WORKSPACE, 'resnet50')
     
    compiled_model_dir = os.path.join(WORKSPACE, 'resnet50_neuron')
     
    shutil.rmtree(model_dir, ignore_errors=True)
     
    shutil.rmtree(compiled_model_dir, ignore_errors=True)
     
     
     
    # Instantiate Keras ResNet50 model
     
    keras.backend.set_learning_phase(0)
     
    model = ResNet50(weights='imagenet')
     
     
     
    # Export SavedModel
     
    tf.saved_model.simple_save(
     
     session            = keras.backend.get_session(),
     
     export_dir         = model_dir,
     
     inputs             = {'input': model.inputs[0]},
     
     outputs            = {'output': model.outputs[0]})
     
     
     
    # Compile using Neuron
     
    tfn.saved_model.compile(model_dir, compiled_model_dir, compiler_args =['--num-neuroncores', '4'])
     
     
     
    # Prepare SavedModel for uploading to Inf1 instance
     
    shutil.make_archive(compiled_model_dir, 'zip', WORKSPACE, 'resnet50_neuron')

    这里有两点须要留神:

    • Resnet50 的模型有2000多万个参数。应用 FP32格局,每个参数4字节。AWS Neuron 编译器主动将它们转换为 BF16,每个参数2字节,这是一种更无效的数据格式,Neuron Core 在硬件上原生反对这种格局;
    • 因为启用的 inf1.2xlarge 实例有4个 Neuron Core,设置 compiler_args =[‘–num-neuroncores’, ‘4’],会将模型定位并优化于4个 Neuron Core 上运行。此参数的默认值为1,咱们须要确保参数设置为启动的 Inf1 实例上的 Neuron Core 的数量。

    随后应用以下命令编译模型:

    $ python tensorflow_compile_resnet50.py

    编译过程大概须要几分钟工夫,输入应蕴含如下信息:

    ...
     
    INFO:tensorflow:fusing subgraph neuron_op_d6f098c01c780733 with neuron-cc
     
    INFO:tensorflow:Number of operations in TensorFlow session: 4638
     
    INFO:tensorflow:Number of operations after tf.neuron optimizations: 556
     
    INFO:tensorflow:Number of operations placed on Neuron runtime: 554
     
    INFO:tensorflow:Successfully converted ./ws_resnet50/resnet50 to ./ws_resnet50/resnet50_neuron
     
    ...

    编译后,保留的模型以压缩格局存储在 ws_resnet50/resnet50_neuron.zip,应用以下命令解压缩模型:

    $ unzip ws_resnet50/resnet50_neuron.zip -d .

    在第二阶段,咱们会应用在第一阶段编译的推理模型在示例图像上运行推理。

    首先,下载一幅用于推理的示例图像:

    $ curl -O https://raw.githubusercontent.com/awslabs/mxnet-model-server/master/docs/images/kitten_small.jpg

    随后创立一个名为 tensorflow_infer_resnet50.py 的 Python 脚本,该脚本蕴含以下内容,应用在第一阶段编译好的模型在 AWS Inferentia 上进行推理。

    import os
     
    import numpy as np
     
    import tensorflow as tf
     
    from tensorflow.keras.preprocessing import image
     
    from tensorflow.keras.applications import resnet50
     
     
     
    # Create input from image
     
    img_sgl = image.load_img('kitten_small.jpg', target_size=(224, 224))
     
    img_arr = image.img_to_array(img_sgl)
     
    img_arr2 = np.expand_dims(img_arr, axis=0)
     
    img_arr3 = resnet50.preprocess_input(img_arr2)
     
     
     
    # Load model
     
    COMPILED_MODEL_DIR = './resnet50_neuron/'
     
    predictor_inferentia = tf.contrib.predictor.from_saved_model(COMPILED_MODEL_DIR)
     
     
     
    # Run inference
     
    model_feed_dict={'input': img_arr3}
     
    infa_rslts = predictor_inferentia(model_feed_dict);
     
     
     
    # Display results
     
    print(resnet50.decode_predictions(infa_rslts["output"], top=5)[0])

    这样,咱们就能够应用以下命令运行推理操作:

    $ python tensorflow_infer_resnet50.py

    输入应该如下所示:

    ...
     
    [('n02123045', 'tabby', 0.6918919),
     
     ('n02127052', 'lynx', 0.12770271),
     
     ('n02123159', 'tiger_cat', 0.08277027),
     
     ('n02124075', 'Egyptian_cat', 0.06418919),
     
     ('n02128757', 'snow_leopard', 0.009290541)]

     

    总结

    通过上述样例,咱们看到了应用 AWS Neuron SDK 在 AWS Inferentia 芯片上进行机器学习推理的全过程,也心愿借此可能帮忙大家把更多的机器学习利用在云端部署以获得最佳的体验。

  • 实战-利用机器学习实现一个多分类任务

    对于机器学习而言,如果你曾经大抵理解了相干算法的原理、实践推导,你也不是大家口中刚入门的小白了。接下来你须要将本人所学的常识利用起来,最好的形式应该就是独立实现几个我的项目实战,我的项目难度入门级即可,因为重点是帮忙你理解一个我的项目的流程,比方缺失值和异样值的解决、特色降维、变量转换等等。

    Kaggle毋庸置疑是一个很好的平台,外面的泰坦尼克号、屋宇价格预测、手写数字都是十分十分经典的入门实战我的项目,如果你独立实现这三个我的项目后感觉能够晋升一下难度,就能够持续在Playground中寻找适宜本人的我的项目。但如果你感觉还须要几个简略的我的项目坚固一下,这里给大家安利一下SofaSofa比赛平台。

    业余水平尽管不迭Kaggle,但练习赛中十个简略我的项目用来练手还是不错的,品种也是十分全的,包含分类、回归预测、自然语言解决、图像识别等等,本文在练习赛【8】——地震后修建修复倡议的根底上实现。

    理解数据集

    首先肯定要做的是理解数据集,因为大多数据集的特色名都是以英文或者以英文简写搭配命名,只有真正理解一个特色的意义,能力更好地剖析该特色与标签变量之前存在的关系。SofaSofa在每个较量中都会有一个表格,给出所有变量对应的解释。

    能够看到这个数据集的特色并不是很多,但训练集共有65万个样本,咱们都晓得数据多对于建模是有益处的,因为数据越多覆盖面就越广,会进步模型的准确率,当然这可能会就义一些内存和计算工夫。标签变量y,共有四种可能取值,阐明这是一个多元分类问题。

    没有缺失值是不错的音讯,除标签变量y之外,共有9个数值型比变量和5个类别型变量。

    可视化剖析

    可视化剖析一方面是帮忙咱们找出样本中的异样点和离群点,一方面也是帮忙剖析特色与标签变量之间的关系。但下面提及了这个训练集足足有65万条数据,如果同时利用所有样本绘制图像,图像可能会被样本点填满,很难从中得出有用的信息。

    所以这里能够抉择随机抽样的形式,每次抽取1000-2000个样本绘制图像进行剖析,能够多抽取几次,避免数据的必然性。这里抉择用散点图可视化数值型特色,用area和age为例。

    area特色中有一些数值偏大,但不能说其是异样点,因为一些大型建筑物占地面积3000不是不可能的,但2000个样本,仅有不到20个样本的占地面积大于1500,所以能够将其视为离群点,离群点在建模时是会影响拟合的,所以抉择舍去。

    对于建筑物的年限age而言,可视化后会发现有很多样本在age这一特色的数值都为999,两头却有很大的空缺,比方没有一个样本点的age位于500-900之间,所以这类样本被视为异样点,再联合离群点剖析,能够抉择一个阈值进行过滤。其余数值型特色能够做同样的操作,这里不再过多介绍。

    这个数据集还有个奇怪的中央就是有很多样本地震后的楼层、高度都要高于地震产生之前,这显然是不可能产生的,可能是在数据填充时呈现了谬误,利用布尔索引过滤掉此类特色。

    #布尔索引
    data1 = data1[data1['floors_before']>=data1['floors_after']]
    data1 = data1[data1['height_before']>=data1['height_after']]
    data1.reset_index(drop = True)#重置索引

    而后利用相关矩阵对所有的数值型特色进行一下相关性剖析,通过观察相关性舍去一些没有必要的特色达到降维的目标。

    这里”district_id”和”area_id”是齐全相干的,能够轻易留下一个,或者都删去,因为相关性的确小的可怜;能够看到这里减少了两个新的变量”floors_diff”和”height_diff”,就是地震前后的建筑物层数和高度的差值,能够察看一下标签变量”y”和这六个属性的相关性,与地震前的信息相关性极低,也就是说,标签变量很少关注一个建筑物震前的信息,而是着重关注通过地震之后建筑物发生变化的信息。

    类别型变量转换

    类别型变量不不便前期建模时传入数据,所以咱们须要提前将类别型变量转换为算法能辨认的数值型,变量转换形式有很多种,比方有序变量、哑变量、虚构变量。

    对于”position”这一特色,能够进行有序变量,因为仅有一个特色,所以没有调用sklearn中的API,而是间接利用自定义函数联合apply函数进行转换。

    def pos(e):
        if e == "Not attached":
            return 0
        elif e == "Attached-1 side":
            return 1
        elif e=="Attached-2 side":
            return 2
        else:
            return 3
    data1['position'] = data1['position'].apply(pos)

    而剩下的几个类别型变量皆为无序变量,能够将其转化为哑变量,再进一步转化为虚构变量。相比于sklearn中的API,pandas自带的办法看起来更加简洁。

    #哑变量编码
    dummy_df = pd.get_dummies(data1.iloc[:,6:10])


    如果你感觉这种形式简略,并没有懂哑变量编码的意思和过程,能够试着理解一下上面这个函数,同样是实现哑变量编码。

    def dummy_code(var):
        #获取特色中所有变量
        var_unique = var.unique()
        #新建一个DataFrame
        dummy = pd.DataFrame()
        #最初一个不设置虚构变量,可用之前所有变量示意
        for val in var_unique:
            #利用一个布尔型数组存储编码后的变量
            bo = (val==var)
            #命名,并将True转为1,False转为0
            dummy[var.name+"_"+str(val)] = bo.astype(int)
        return dummy

    将哑变量进一步转化为虚构变量合并至数据集中,代码如下:

    #每个特色删去一个类别,失去虚构变量
    dummy_df1 = dummy_df.drop(['land_condition_S','foundation_type_O','roof_type_H','ground_floor_type_T'],axis = 1)
    #删去原特色,合并虚构变量
    data1 = data1.drop(['land_condition','foundation_type','roof_type','ground_floor_type'],axis = 1)
    data1 = pd.concat([data1,dummy_df1],axis = 1)

    可能很多搭档不太理解为什么虚构变量能够这样转换,虚构变量与哑变量相比,缩小了特色的维度,实质是相似的,以”roof_type”这一特色举例,通过哑变量转换造成三个新特色:[“roof_type_H”,”roof_type_L”,”roof_type_R”],如果在”roof_type”为”R”的样本,在哑变量的表达方式应该是[0,0,1],然而如果从哑变量中删去”roof_type_R”这一特色,表达方式就能够变成[0,0],通过唯一性就能够利用前两个特色推出第三个特色的值,所以缩小了不必要的特色以实现降维。

    当然这里还能够做一下方差过滤、相关性剖析等操作进一步实现特色降维,各位在实操的时候能够本人试一下。

    建模工作

    后面说过了这个是一个多元分类我的项目,所以在建模的时候能够有两种抉择,一是利用多元分类器,比方随机森林、奢侈贝叶斯,二就是利用二元分类器实现多元分类工作,比方逻辑回归、SVM。

    前面文章会写一篇对于二元分类器实现多元分类的文章,本文就集中于多元分类器的实现,次要用到的两个分类器是随机森林和LGBM。

    个别建模的流程大抵是在训练集上切分训练集和测试集,有的数据须要标准化解决,而后训练模型,利用测试集进行预测,获取模型的准确率或其余掂量模型好坏的指标,上面以随机森林分类器模仿一下该流程。

    首先进行数据切分,能够抉择管制训练集和测试集的比例:

    from sklearn.model_selection import train_test_split
    features = data2.iloc[:,0:-1].values
    label = data2.iloc[:,-1].values
    X_train,X_test,y_train,y_test = train_test_split(features,label,test_size = 0.3)

    这里介绍一下能够缩小代码量的管道流,如果失常来说,咱们可能要别离实例化标准化和PCA的API,而后再传入训练集和测试集,这些操作能够利用管道流封装到一起,让代码看起来更加简洁。

    from sklearn.ensemble import RandomForestClassifier
    from sklearn.decomposition import PCA
    from sklearn.pipeline import make_pipeline,Pipeline
    #管道流简化工作流
    pipe_rf = make_pipeline(StandardScaler(),
                            PCA(n_components=10),
                            RandomForestClassifier())
    pipe_rf.fit(X_train,y_train)
    #失去每个类别的概率
    pred_y_rf = pipe_rf.predict_prob(X_test)

    利用predict_prob计算出标签变量失去每个类别的概率,而后利用索引排序能够失去概率最大的两个类别:

    pred_df = pd.DataFrame(data=pred_y_rf.argsort()[:, -2:][:, ::-1], columns=['y1', 'y2'])
    pred_df.to_csv("eq_submission.csv",index=False)

    因为数据量比拟大,调参比拟费时,在没有调参的状况下,随机森林模型的概率大抵为68%,LGBM模型的准确率大抵为70%,准确率并不是太好,除准确率外还能够通过查全率、查准率、F1-score掂量一下模型的好坏,上文大体上提供了一个建模前及建模的思路而已,搭档们能够利用本人的思路,再加上调参应该会失去一个不错的模型。

    这幅图是对于特色重要度的饼图,能够依据饼图再调节特色,其中area占比是比最大的,而后”distict_id”占比也是不小的,然而上文关系矩阵中与标签变量的相关性又很小,所以剖析要互相联合、更加全面一些才好。

    说在最初

    下面的一系列操作都是为了最初的模型,但如果作为一个比赛,你须要提交一份文件,而这份文件从何来?比赛会给出一个不含标签变量的测试集!留神与测试集中宰割出的测试集不同。咱们同样须要对测试集做一些数据处理,操作和训练集相似,而后将训练出的模型利用在测试集上,会得出最初的后果保留成一个新的csv文件,这就是你最初须要提交的文件啦。

    公众号【奶糖猫】后盾回复”地震”可获取源码供参考

  • 或许是东半球最好用的超参数优化框架-Optuna-简介

    今年夏天参加了一个我很喜爱的超参数框架 Optuna (Optuna – A hyperparameter optimization framework)的文档翻译工作。当初翻译曾经根本实现(https://zh-cn.optuna.org),而 Optuna 更成熟的 2.0 版本最近也要公布了。于是咱们决定写一个介绍,心愿让更多的中文用户理解和应用这个框架,并且能参加到社区两头来。


    Tensorflow 和 Pytorch 曾经将实现深度学习模型变成一个 10 分钟不到的过程:申明模型,定义参数、优化器,载入训练数据,启动梯度降落。而后一个接着一个 epoch, 模型在测试集上的精度稳步晋升… 然而等等,在事实中,训练一个模型从来不会这么顺利,你总会碰到各种各样的问题,比方:

    • 后果和paper上写的不一样(优化)
    • 有些参数组合基本训练不进去,还把训练脚本搞解体了,你却不晓得起因所在
    • 训进去也不晓得这个参数范畴是否稳固(参数关系)

    下面这些状况阐明了超参数抉择对于模型性能的重要性。于是为了调参,你开始手动往脚本里加内容:超参数优化不就是 for 循环里套 for 循环嘛,很简略。可很快,你又会其余碰到问题:

    • 有一台好机器,for 循环一次却只能执行一个模型,节约性能
    • 优化完的参数输入到了一个 txt,还得本人写解析来剖析
    • for 循环里有些参数只是运气好,理论部署下来并不一样

    总之你会碰到十分多问题,它们会节约你的工夫。而 Optuna 则是帮忙你解决下面所有这些问题的一个工具,解放你的双手和工夫,让你能更加专一于模型实现。它将定义一个超参数优化过程变得 非常简单,而且易于保留不便剖析,还反对无缝扩大

    Talk is cheap, show me the code. 咱们将通过一个例子来展现 Optuna 的上述长处。


    定义简略

    一个极简的 optuna 的优化程序中只有三个最外围的概念,指标函数(objective),单次试验(trial),和钻研(study). 其中 objective 负责定义待优化函数并指定参/超参数数范畴,trial 对应着 objective 的单次执行,而 study 则负责管理优化,决定优化的形式,总试验的次数、试验后果的记录等性能。

    如果要在 $x,y \in(-10,10)$ 的范畴内找到 $f(x,y)=(x+y)^2$ 这个函数的最大值对应的 $x,y$,那咱们只须要上面的代码:

    import optuna
    
    def objective(trial):
        x = trial.suggest_uniform('x', -10, 10)
        y = trial.suggest_uniform('y', -10, 10)
        return (x + y) ** 2
    
    study = optuna.create_study(direction='maximize')
    study.optimize(objective, n_trials=100)
    
    print(study.best_params)
    print(study.best_value)

    在上例中,咱们首先定义了一个 objective. 在它外部, $f(x,y)=(x+y)^2$ 的后果被作为返回值,其参数空间的 x 和 y 从两个均匀分布中采样。
    而后,Optuna 创立了一个“钻研” (study), 指定了优化的方向为最大化并且最大试验次数为100,而后将指标函数传入其中,开始优化 (optimize) 过程。最初脚本输入在100次试验中找到的最佳参数组合。

    命令行工具

    因为 Optuna 还提供了命令行工具,下面的优化过程也能够通过在shell 中间接执行语句来进行。应用命令行工具的话,咱们能够省略掉全副其余代码,只需在脚本中申明指标函数的定义即可。

    而后,在终端中执行上面的 `optuna` 命令即可开始优化过程:

    $ STUDY_NAME=`optuna create-study --storage sqlite:///example.db`
    $ optuna study optimize foo.py objective --n-trials=100 --storage sqlite:///example.db --study-name $STUDY_NAME

    这一过程和下面的脚本是齐全等价的(其中 storage 的局部下文会介绍)。该命令的输入如下:

    ...
    [I 2020-07-01 02:41:34,311] Trial 96 finished with value: 3.1406709262042694 and parameters: {'x': -7.882810516401339, 'y': 9.65500433373743}. Best is trial 92 with value: 383.4423553199605.
    [I 2020-07-01 02:41:34,314] Trial 97 finished with value: 353.54920261705433 and parameters: {'x': -8.876138448320777, 'y': -9.926765652297679}. Best is trial 92 with value: 383.4423553199605.
    [I 2020-07-01 02:41:34,316] Trial 98 finished with value: 319.81596197762224 and parameters: {'x': -9.502045119809319, 'y': -8.381353941264676}. Best is trial 92 with value: 383.4423553199605.
    [I 2020-07-01 02:41:34,319] Trial 99 finished with value: 295.705727918292 and parameters: {'x': -8.387075346077019, 'y': -8.809020952743014}. Best is trial 92 with value: 383.4423553199605.
    
    {'x': -9.984261379947354, 'y': -9.59742279991727}
    383.4423553199605

    你可能感觉下面的代码和命令,尤其是指标函数的定义平平无奇,因为它结构优化过程的形式十分天然,十分 pythonic. 作为比照,让咱们看看另一个超参数优化框架 Hyperopt 实现同样性能须要怎么写:

    from hyperopt import hp
    from hyperopt import fmin, tpe, space_eval, Trials
    
    # define an objective function
    def objective(args):
        return -(args['x'] + args['y'])**2
    
    space = {
        "x": hp.uniform('x', -10, 10),
        "y": hp.uniform('y', -10, 10),
    }
    
    trials = Trials()
    
    best = fmin(objective, space, algo=tpe.suggest, max_evals=100, trials=trials)
    print(best)
    print(space_eval(space, best))

    首先,参数空间必须在指标函数内部定义。其次,要存储试验记录的话,须要在内部独自实例化一个 `Trials` 对象。最初,如果须要最大化指标函数的话,你只能在返回值上增加一个负号,因为

    >>> from hyperopt import fmax
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
    ImportError: cannot import name 'fmax' from 'hyperopt'

    总的来说,Hyperopt 还算不错,然而从易用性上来说,显然 Optuna 还是更胜一筹。

    但你可能问,就这?不就是多写两行代码的事件吗?当然不是了,下面只是一个 toy model, 实际上 Optuna 有更多的个性让它在实在的超参数优化环境中十分好用。


    易于保留

    出于各种目标,咱们常常有保留优化过程的需要。比方你可能须要追踪或者debug 一个指标函数的优化过程,比方指标函数的参数空间太大,而一旦机器解体,你的优化过程必须从头再来。又或者,你想实现多台机器并行优化一个指标函数,这时候一个能保留优化试验历史并且能从中复原/持续优化的个性就显得尤其重要。而 Optuna 反对这种个性。

    初始化记录

    默认状况下,Optuna 应用内存存储来记录试验过程。然而如果在创立 study 时增加一个 storage 参数,Optuna 能够依据你的参数类型应用 SQLite, MySQL 或者 Redis 等风行的数据库来记录你的试验历史。上面是一个应用SQLite 的例子

    study_name = 'example-study'  # 不同的 study 不能应用雷同的名字。因为当存储在同一个数据库中时,这是辨别不同 study 的标识符.
    study = optuna.create_study(study_name=study_name, storage='sqlite:///example.db')
    
    study.optimize(objective, n_trials=300)

    如果 ‘sqlite:///example.db’ 这一 URL 对应的数据库文件不存在,Optuna将创立一个对应的数据库文件并开始新的优化过程。

    当初,假如优化过程被打断了,你齐全能够从新运行下面的脚本来从上次中断的地位持续优化。只有 optuna 监测到 `’sqlite:///example.db’` 在门路上存在且该数据库中有 study_name 为 ‘example-study’ 的记录,它就会持续未实现的优化过程。

    存储有了,如何提取呢?无需手动进数据库写 query 语句,你只需用一行命令即可提取所有的试验记录

    df = study.trials_dataframe(attrs=('number', 'value', 'params', 'state'))

    这个语句会返回一个 pandas dataframe

    # 来自第一个例子
    
        number       value  params_x  params_y     state
    0        0   97.081081 -4.012360 -5.840613  COMPLETE
    1        1  110.359399  8.495576  2.009632  COMPLETE
    2        2  270.740964 -9.909762 -6.544446  COMPLETE
    3        3   41.726647 -6.698396  0.238780  COMPLETE
    4        4   12.735788  4.018620 -7.587344  COMPLETE
    ..     ...         ...       ...       ...       ...

    在下面介绍的根底上,Optuna 还提供了一系列可视化接口,让查看不同参数之间的关系变得非常容易。因为集成到了库办法中,过来须要专门写一个脚本来做的事件当初只须要一两行命令即可。

    等高线图

    在 study.optimize 执行完结当前,通过调用 optuna.visualization.plot_contour,并将 study 和须要可视化的参数传入该办法,Optuna 将返回一张等高线图。例如,当在下面的例子中,咱们想要查看参数 x 和 y 的关系以及它们对于函数值奉献的话,只须要执行上面的语句即可:

    optuna.visualization.plot_contour(study, params=['x', 'y'])
    # 如果不指定 params 也是能够的,optuna 将画出所有的参数之间的关系,在这里两者等价。
    optuna.visualization.plot_contour(study)

    它输入:

    除了等⾼线图之外,Optuna 还提供了⼀系列其余⾮常实⽤的可视化选项,⽐如每个 trial 训练的两头值折线图。 这对了解优化过程细节⾮常有用。上面的折线图来自于 Optuna 的官网文档。

    相似地,Optuna 还提供了诸如优化过程历史记录多维度参数-指标函数关系等绘图接口。


    优化过程历史记录


    多维度参数-指标函数关系

    多维度参数-指标函数关系图十分有用,和后面的等高线图不同,多维度参数-指标函数关系图一次性能够展现任意多个参数和指标函数值之间的关系。

    其实在上述接口之外,Optuna 还提供了一系列其余绘图接口,比方超参数重要性评估图,参数关系切片图等。具体细节参见其中文文档的API reference-Visualization 局部。

    不难看出,作为一个超参数优化框架,Optuna 应用起来很简略,其提供的存储接口、可视化套件也让用户对优化过程进行记录和剖析变得非常容易。

    其实,这些特色中的每一个都只是解决了超参数优化过程中一个或者数个很小的“痒点”,然而至多在我看来,它们的组合却让 Optuna 变成一个十分适于疾速上手的全功能框架。

    而且,本文中展现的个性仅仅是 Optuna 全副个性的一小部分。介绍它们只是为了不便你疾速上手 Optuna。因为在这些根底个性之外,它还提供了以下性能:

    • 极其不便的分布式优化(同一机器上不同线程或者不同机器节点通过关系型数据库共享优化过程)
    • 粗疏的剪枝过程(Optuna 提供了一系列的各种剪枝算法,能提前革除 trial 中有望的局部,节俭计算资源)
    • 插件机制(Optuna 提供了一系列插件,能和目前市面上风行的很多机器学习框架,比方 Tensorflow 和 Pytorch 等深度整合,让用户无需扭转太多现存代码,便可将 Optuna 整合进老模型的优化中)

    这些性能咱们将在下一篇文章中一一介绍。如果你曾经急不可待了,也能够间接参考 Optuna 的官网文档和对应的中文翻译。


    哪里能够找到 OPtuna?

    Optuna 官网:https://optuna.org
    Optuna 中文文档:https://zh-cn.optuna.org

  • 基于LeNet网络的细胞识别

    基于LeNet网络的细胞辨认

    作者:陈玥

    背景

    目前,寰球疫情仍处于严厉时刻,许多计算机相关畛域工作者也都参加到钻研病毒、疫情等工作中。足量的高质量的COVID-19 图像数据集能用无效地帮忙医院放慢筛选和检测新冠肺炎,但因为隐衷爱护,目前难以获得足量的数据集。因能够先通过疟疾数据集训练细胞检测模型,前面能够利用迁徙学习来训练COVID-19。本文应用深度学习框架Keras 在疟疾数据集上训练感化病毒检测器,能够依据细胞图像无效地辨认出是否受到感染,是一篇应用深度学习框架Keras 进行疾病诊断的残缺入门教程,也能够为日后新冠肺炎图像检测提供参考。

    数据集

    Malaria Datasets来自疟疾筛查钻研流动的血液涂片图像存储库,收集了150 名受疟疾感化的患者和50 名衰弱人员的细胞涂片,数据具备真实性和利用价值。图像由医学钻研人员手动标注,使得分类具备可靠性和专业性,数据集总共蕴含27,558 个细胞图像,蕴含感化细胞图像细胞和未被感化的图像集。
    数据集下载地址:https://lhncbc.nlm.nih.gov/publication/pub9932

    图像预处理

    为了减少网络辨认的图像数量,本次试验执行了数据加强操作。应用ImageDataGenerator 类的.flow_from_directory(directory)  的办法在训练期间,执行随机裁剪、缩放和旋转图像等变换,以便在每个期间,通过实时数据加强生成张量图像数据批次,数据将按批次一直循环,网络会看到同一图像的不同变动,进步试验的准确性,加强模型泛化能力。
    官网文档:https://keras.io/zh/preprocessing/image/

    train_datagen = ImageDataGenerator(
            rescale=1./255,
            rotation_range=20,
            shear_range=0.2,
            zoom_range=0.2,
            horizontal_flip=True,
            validation_split=0.1)
    
    train_generator = train_datagen.flow_from_directory(
        path,target_size = (128, 128),
        batch_size = BATCH_SIZE,
        class_mode = 'categorical', 
        subset = 'training',seed = 0)
    
    test_datagen = ImageDataGenerator(
        rescale = 1./255,
        validation_split = 0.1)
    
    val_generator = test_datagen.flow_from_directory(
        path,target_size = (128, 128),
        batch_size = BATCH_SIZE,
        class_mode = 'categorical', 
        subset='validation', seed=0)

    CNN 模型

    构建LeNet 网络

    利用深度学习做图像分类通常会采纳卷积神经网络CNN ,但在试验之前也很难确定哪一类CNN 网络会在本人的分类工作体现最好,因而这里搭建的是最经典的LeNet 网络,首先察看一下分类成果。图1 形容了LeNet 的网络结构,其蕴含了卷积层、池化层和全连贯层
    图1 LeNet网络

    model = Sequential()
    
    # 输出层
    model.add(Conv2D(8, kernel_size=(3, 3), 
                     padding="same",
                     input_shape=input_shape,
                     activation='relu'))
    model.add(MaxPooling2D(pool_size=(2, 2)))
    
    # 暗藏层
    
    model.add(Conv2D(16, kernel_size=(3, 3), 
                     padding="same",
                     activation='relu'))
    model.add(MaxPooling2D(pool_size=(2, 2)))
    
    model.add(Conv2D(32, kernel_size=(3, 3), 
                     activation='relu'))
    model.add(MaxPooling2D(pool_size=(2, 2)))
    
    # 展平
    model.add(Flatten())
    model.add(Dense(units=64, activation='relu'))
    model.add(Dropout(0.5))  # 增加抛弃层
    
    model.add(Dense(units=2, activation='softmax'))

    网络的搭建从输出->卷积->池化->卷积->池化->卷积->池化->Dense(relu)>Dense(softmax),其中Con2D 示意执行卷积操作,MaxPooling2D 是最大池化,展平层Flatten 将输出“开展”为一层,用于卷积层到全连贯层的过渡,Dense 示意全连贯层,增加抛弃层Dropout 避免过拟合。

    模型编译

    这个实验室是二分类问题,因而抉择 binary_crossentrop 作为损失函数,若是多类别分类问题,损失函数能够抉择 categorical_crossentropyAdagrad 为优化器。

    model.compile(loss=keras.losses.binary_crossentropy,
                  optimizer=keras.optimizers.Adagrad(),
                  metrics=['accuracy'])

    模型训练

    _history = model.fit_generator(
        train_generator,
        validation_data=val_generator,
        steps_per_epoch=2750//BATCH_SIZE,
        validation_steps=200//BATCH_SIZE,
        epochs = EPOCHS)

    可视化训练后果

    模型训练过程中的数据会寄存在_history中,为了更好地察看迭代过程,将其可视化输入。

    N = EPOCHS
    
    plt.style.use("ggplot")#matplotlib的丑化款式
    plt.figure()
    plt.plot(np.arange(0,N),_history.history["loss"],label ="train_loss")
    plt.plot(np.arange(0,N),_history.history["val_loss"],label="val_loss")
    plt.plot(np.arange(0,N),_history.history["accuracy"],label="train_acc")
    plt.plot(np.arange(0,N),_history.history['val_accuracy'],label="val_acc")
    
    plt.title("loss and accuracy")
    plt.xlabel("epoch")
    plt.ylabel("loss/acc")
    plt.legend(loc="best")
    plt.savefig("./results/result.png")
    plt.show()


    图2 损失和精度曲线
    从图中的训练后果能够看到,随着迭数的减少,准确率逐步减少,当迭代次数超过15次后,趋向于稳固,证实模型的收敛性良好,在验证集上的精度能够达到90%以上,且与训练集精度差异不大,阐明分类成果良好,模型的泛化能力不错。
    val_loss曲线震荡不平滑的起因可能是因为Batch_size太小或样本分布不平均等其余起因,至于val_loss比train_loss小的起因很可能是样本数量不足够或者是random variables,若想模型要达到更好的成果,还要下功夫在超参的设置上。

    分类后果

    图3 分类后果(局部)
    图3的分类后果,pred是预测的分类,truth是图像理论的分类,整体来看,对于一个简略的CNN网络来看,分类成果还是不错的。

    总结与瞻望

    在本试验中,应用了CNN经典网络LeNet网络结构,为细胞分类检测提供了一套残缺的处理过程,能够用作其余类别图像分类的通用框架。若将来要将模型使用到COVID-19检测中并将探测器部署在实地中,能够采纳迁徙学习的办法将模型利用到其余数据集下来。

    我的项目地址:https://momodel.cn/explore/5ef8135a2d3fa37593d47b3b?blob=master%252Fcoding_here.ipynb&type=app

  • MnasNet经典轻量级神经网络搜索方法-CVPR-2019

    论文提出了挪动端的神经网络架构搜寻办法,该办法次要有两个思路,首先应用多指标优化办法将模型在理论设施上的耗时融入搜寻中,而后应用合成的档次搜寻空间,来让网络放弃层多样性的同时,搜寻空间仍然很简洁,可能使得搜寻的模型在准确率和耗时中有更好的trade off

    起源:【晓飞的算法工程笔记】 公众号

    论文: MnasNet: Platform-Aware Neural Architecture Search for Mobile

    • 论文地址:https://arxiv.org/abs/1807.11626
    • 代码地址:https://github.com/tensorflow/tpu/tree/master/models/official/mnasnet

    Introduction


      在设计挪动端卷积网络时,经常会面临着速度与准确率的取舍问题,为了设计更好的挪动端卷积网络,论文提出挪动网络的神经网络架构搜寻办法,大略步骤如图1所示。比照之前的办法,该办法主奉献有3点:

    • 将设计问题转化为多指标优化问题(multi-objective optimization),同时思考准确率和理论推理耗时。因为计算量FLOPS其实和理论推理耗时并不总是统一的(MobileNet,575M,113ms vs NASNet,564 M,183ms),所以论文通过理论挪动设施上运行来测量推理耗时
    • 之前的搜寻办法大都先搜寻最优的单元,而后重叠成网络,尽管这样能优化搜寻空间,但克制了层多样性。为了解决这个问题,论文提出合成的档次搜寻空间(factorized hierarchical search space),使得层能存在构造差别的同时,依然很好地均衡灵活性和搜寻空间大小

    • 在合乎挪动端应用的前提下,达到ImageNet和COCO的SOTA,且速度更快,模型更轻量。如图2所示,在准确率更高的前提下,MansNet速度比MobieNet和NASNet-A别离快1.8倍和2.3倍

    Problem Formulation


      对于模型$m$,$ACC(m)$为模型准确率,$LAT(m)$为指标挪动平台的推理耗时,$T$为指标耗时,公式1为在合乎耗时前提下,最大化准确率

      但公式1仅最优准确率,没有进行多指标优化(multiple Pareto optimal),于是论文改用公式2的加权乘积办法来近似进行多指标优化

      $w$是权重因子,$\alpha$和$\beta$为利用特定常数(application-specific constants),这两个值的设定是用来保障合乎accuracy-latency trade-offs的有类似的reward,即高准确率稍高耗时和稍低准确率低耗时有雷同的reward。例如,凭教训认为两倍耗时通常能带来5%准确率晋升,对于模型M1(耗时$l$,准确率$a$),模型M2(耗时$2l$,准确率$a(1+5\%)$),他们应该有雷同的reward:$Reward(M2)=a\cdot (1+5\%)\cdot (2l/T)^\beta\approx Reward(M1)=a\cdot (l/T)^\beta$,失去$\beta=-0.07$。前面试验没阐明都应用$\alpha=\beta=-0.07$

      图3为不同常数下的指标函数曲线,上图$(\alpha=0,\beta=-1)$意味着合乎耗时的间接输入准确率,超过耗时的则鼎力惩办,下图$(\alpha=\beta=-0.07)$则是将耗时作为软束缚,平滑地调整指标函数

    Mobile Neural Architecture Search


    Factorized Hierarchical Search Space

      论文提出别离的档次搜寻空间,整体结构如图4所示,将卷积神经网络模型分解成独立的块(block),逐渐升高块的输出以及减少块中的卷积核数。每个块进行独立块搜寻,每个块蕴含多个雷同的层,由块搜寻来决定。搜寻的目标是基于输出和输入的大小,抉择最合适的算子以及参数(kernal size, filter size)来达到更好的accurate-latency trade-off

      每个块的子搜寻蕴含下面6个步骤,例如图4中的block 4,每层都为inverted bottleneck 5×5 convolution和residual skip path,共$N_4$层

      搜寻空间抉择应用MobileNetV2作为参考,图4的block数与MobileNetV2对应,MobileNetV2的构造如上。在MobileNetV2的根底上,每个block的layer数量进行$\{0,+1,-1\}$进行加减,而卷积核数则抉择$\{0.75,1.0,1.25\}$
      论文提出的合成的档次搜寻空间对于均衡层多样性和搜寻空间大小有特地的益处,假如共$B$blocks,每个block的子搜寻空间大小为$S$,均匀每个block有$N$层,总共的搜寻空间则为$S^B$,比照按层搜寻的空间$S^{B*N}$小了很多

    Search Algorithm

      论文应用NAS的强化学习办法来优化公式2的rewadr冀望,在每一轮,controller依据以后参数$\theta$一批模型,每个模型$m$训练后取得准确率$ACC(m)$以及理论推理耗时$LAT(m)$,依据公式2失去reward,而后应用Proximal Policy Optimization来更新controller的参数$\theta$最大化公式5

    Experimental Setup


      论文先尝试在CIFAR-10上进行架构搜寻,而后迁徙到大数据集上,然而发现这样不见效,因为思考了理论耗时,而利用到大数据集时,网络通常须要放大,耗时就不精确了。因而,论文间接在ImageNet上进行搜寻,但每个模型只训练5轮来减速。RNN controller与NASNet保持一致,总共须要64 TPUv2搜寻4.5天,每个模型应用Pixel 1手机进行耗时测试,最终大略测试了8K个模型,别离抉择了top 15和top 1模型进行残缺的ImageNet训练以及COCO迁徙,输出图片的分辨率别离为$224\times 224$和$320\times 320$

    Results


    ImageNet Classification Performance

      $T=75ms$,$\alpha=\beta=-0.07$,后果如Table 1所示,MnasNet比MobileNetV2(1.4)快1.8倍,准0.5%,比NASNet-A快2.3倍,准1.2%,而稍大的模型MnasNet-A3比ResNet-50准,但少用了4.8x参数和10x计算量

      因为之前的办法没有应用SE模块,论文补充了个比照训练,MnasNet成果仍然比之前的办法要好

    Model Scaling Performance

      缩放模型是调整准确率和耗时的来适应不同设施的常见操作,能够应用depth multiplier(如同叫width multiplier?)来缩放每层的channels数,也能够间接升高输出图片的分辨率。从图5能够看到,MansNet始终保持着比MobileNetV2好的体现

      此外,论文提出的办法可能搜寻不同耗时的模型,为了比拟性能,论文比照了缩放模型和搜寻模型的准确率。从Table4看出,搜寻进去的模型有更好的准确率

    COCO Object Detection Performance

      论文比照了MnasNet在COCO上的体现,能够看到MnasNet准确率更高,且少用了7.4x参数和42x计算量

    Ablation Study and Discussion


    Soft vs. Hard Latency Constraint

      多指标搜寻办法容许通过设定$\alpha$和$\beta$进行hard和soft的耗时束缚,图6展现了$(\alpha=0,\beta=-1)$和$(\alpha=\beta=-0.07)$,指标耗时为75ms,能够看到soft搜寻更广的区域,构建了很多靠近75ms耗时的模型,也构建了更多小于40ms和大于110ms的模型

    Disentangling Search Space and Reward

      论文将多指标优化和合成的档次搜寻空间进行比照试验,从后果来看,多指标优化能很好均衡低耗和准确率,而论文提出的搜寻空间能同时升高耗时和进步准确率

    MnasNet Architecture and Layer Diversity

      图7(a)为MnasNet-A1的构造,蕴含了不同的层构造,能够看到该网络同时应用了5×5和3×3的卷积,之前的办法都只应用了3×3卷积

      Table 6展现了MansNet模型及其变体,变体上仅用某一层的来构建网络,能够看到MnasNet在准确率和耗时上有了更好的trade-off

    CONCLUSION


      论文提出了挪动端的神经网络架构搜寻办法,该办法应用多指标优化办法将模型在理论设施上的耗时融入搜寻中,可能使得搜寻的模型在准确率和耗时中有更好的trade off。另外该办法应用合成的档次搜寻空间,来让网络放弃层多样性的同时,搜寻空间仍然很简洁,也进步了搜寻网络的准确率。从试验后果来看,论文搜寻到的网络MansNet在准确率和耗时上都比目前的人工构建网络和主动搜寻网络要好



    如果本文对你有帮忙,麻烦点个赞或在看呗~
    更多内容请关注 微信公众号【晓飞的算法工程笔记】