具有并行和GPU计算的神经网络

深度学习

方法可以训练卷积神经网络(CNN, ConvNet)或长短期记忆网络(LSTM或BiLSTM网络)trainNetwork函数。您可以选择使用的执行环境(CPU、GPU、多GPU和并行)trainingOptions

并行训练,或在GPU上,需要并行计算工具箱™。有关gpu和并行的深度学习的更多信息,请参见在cpu、gpu和云上并行地使用大数据进行深度学习

模式的并行性

神经网络本质上是并行算法。多核cpu,图形处理单元(gpu)和集群的计算机有多个cpu和gpu可以利用并行性。

当并行计算工具箱与深度学习工具箱(Deep Learning Toolbox)一起使用时,可以使神经网络训练和模拟利用并行的每种模式。

例如,下面展示了一个标准的单线程训练和模拟会话:

[x, t] = bodyfat_dataset;net1 = feedforwardnet (10);net2 = train(net1, x, t);y = net2 (x);

在此会话中可以并行化的两个步骤是火车隐含的调用sim卡(网络net2作为函数调用)。

在深度学习工具箱中,您可以划分任何数据,如xt在前面的示例代码中,跨示例。如果xt每个样本只包含一个样本,不存在并行性。但是,如果xt由于包含数百或数千个样本,并行性可以提供速度和问题规模方面的好处。

分布式计算

并行计算工具箱允许神经网络训练和模拟运行在单个PC上的多个CPU核,或跨多个CPU在一个网络上使用MATLAB®并行服务器™

使用多核可以加速计算。使用多台计算机可以让您使用过于庞大的数据集来解决问题,这些数据集无法装入一台计算机的RAM中。问题大小的唯一限制是所有计算机上可用的RAM总量。

要管理集群配置,请使用MATLAB中的集群配置文件管理器首页选项卡环境菜单平行>管理集群配置文件

要使用默认的集群配置文件(通常是本地CPU核心)打开MATLAB worker池,可以使用以下命令:

池= parpool
使用“本地”配置文件启动并行池(parpool)…与4名工人联系。

parpool运行时,它将显示池中可用的worker数量。确定worker数量的另一种方法是查询池:

pool.NumWorkers
4

现在您可以在所有工作人员中使用样本分割的数据来训练和模拟神经网络。为此,设置火车sim卡参数“useParallel”“是的”

net2 =火车(net1 x, t,“useParallel”,“是的”) y = net2,“useParallel”,“是的”)

使用“showResources”参数来验证计算遍历多个工作程序。

net2 =火车(net1 x, t,“useParallel”,“是的”,“showResources”,“是的”);y = net2 (x,“useParallel”,“是的”,“showResources”,“是的”);

MATLAB指出使用了哪些资源。例如:

计算资源:在我的计算机上并行Worker 1,在我的计算机上的PCWIN64 Worker 2的MEX,在我的计算机上的PCWIN64 Worker 3的MEX,在我的计算机上的PCWIN64 Worker 4的MEX,在PCWIN64上的MEX

火车sim卡在训练和模拟之前,它们将输入矩阵或单元数组数据划分为分布的复合值。当sim卡计算复合后,此输出将在返回之前转换回相同的矩阵或单元格数组形式。

然而,你可能想要手动执行这个数据分割,如果:

  • 问题的大小对主机来说太大了。按顺序手动定义组合值的元素可以定义更大的问题。

  • 众所周知,有些工人使用的计算机比其他人更快或内存更大。您可以使用每个工人不同的样本数量来分发数据。这称为负载平衡。

下面的代码顺序创建了一系列随机数据集,并将它们保存到单独的文件:

池=质量;i = 1:池。x = rand(2,1000);保存([“输入”num2str (i)),“x”);t = x(1,:) .* x(2,:) + 2 * (x(1,:) + x(2,:)));保存([“目标”num2str (i)),“t”);清晰的xt结束

因为数据是按顺序定义的,所以您可以定义主机PC内存无法容纳的总体数据集。PC内存必须一次只能容纳一个子数据集。

现在,您可以跨并行工作者顺序加载数据集,并在复合数据上训练和模拟网络。当火车sim卡被称为复合数据,“useParallel”参数将自动设置为“是的”。在使用复合数据时,将网络的输入和输出配置为手动匹配其中一个数据集配置函数前培训。

xc =复合;tc =复合;i = 1:池。数据= load([“输入”num2str (i)),“x”);xc{我}= data.x;data =负载([“目标”num2str (i)),“t”);tc{我}= data.t;清晰的数据结束net2 =配置(tc net1 xc {1}, {1});net2 =火车(xc net2, tc);yc = net2 (xc);

转换返回的复合输出sim卡,如果考虑到内存限制,可以单独访问它的每个元素。

i = 1:池。yi = yc{i}结束

如果不考虑内存限制,则将复合值组合为一个本地值。

y = {yc {:}};

当负载平衡时,会发生相同的过程,但是,不是每个数据集都有相同数量的样本(前一个示例中是1000),而是可以调整样本的数量,以最大限度地利用worker主机计算机的内存和速度差异。

并不是要求每个worker都有数据。如果元素复合值的未定义,worker不会在计算中使用。

单一的GPU计算

每一代GPU卡的核心数量、内存大小和速度效率都在快速增长。视频游戏一直受益于GPU性能的提高,而这些卡现在已经足够灵活,可以执行一般的数值计算任务,比如训练神经网络。

有关最新的GPU要求,请参阅并行计算工具箱的网页;或查询MATLAB,以确定您的PC是否有一个支持的GPU。金宝app这个函数返回你的系统中gpu的数量:

数= gpuDeviceCount
数= 1

如果结果是一个或多个,你可以通过索引查询每个GPU的特征。这包括它的名字,多处理器的数量,SIMDWidth的每个多处理器,和总内存。

gpu1 = gpuDevice (1)
gpu1 = CUDADevice属性:名称:“GeForce 470 GTX公司”指数:1 ComputeCapability:“2.0”SupportsDouble: 1 Drive金宝apprVersion: 4.1000 MaxThreadsPerBlock: 1024 MaxShmemPerBlock: 49152 MaxThreadBlockSize: [1024 1024 64] MaxGridSize: [65535 65535 1] SIMDWidth: 32 TotalMemory: 1.3422 e + 09 AvailableMemory: 1.1056 e + 09 MultiprocessorCount: 14 ClockRateKHz: 1215000 ComputeMode:“违约”GPUOverlapsTransfers: 1 KernelExecutionTimeout: 1 CanMapHostMemory: 1 DeviceSupported: 1 DeviceSelected: 1

利用GPU最简单的方法是指定调用火车sim卡带参数“useGPU”设置为“是的”(“不”是默认的)。

net2 =火车(net1 x, t,“useGPU”,“是的”) y = net2,“useGPU”,“是的”)

如果net1是否有默认的训练功能trainlm,你会看到一个警告,GPU计算不支持雅可比矩阵训练,只支持梯度训练。金宝app这样训练函数就自动变成了梯度训练函数trainscg。为了避免通知,您可以在培训前指定函数:

net1。trainFcn =“trainscg”;

为了验证训练和模拟是在GPU设备上进行的,要求显示计算机资源:

net2 =火车(net1 x, t,“useGPU”,“是的”,“showResources”,“是的”) y = net2,“useGPU”,“是的”,“showResources”,“是的”)

上面的每一行代码输出以下资源摘要:

计算资源:GPU设备#1,GeForce GTX 470

当任何输入参数是gpuArray时,许多MATLAB函数会自动在GPU上执行。通常情况下,你用这些函数在GPU上来回移动数组gpuArray收集。然而,为了在GPU上高效地进行神经网络计算,矩阵需要被调换,列需要填充,以便在GPU内存中每列的第一个元素都正确地对齐。深度学习工具箱提供了一个特殊的函数调用nndata2gpu将一个数组移动到GPU并正确组织它:

xg = nndata2gpu (x);tg = nndata2gpu (t);

现在您可以使用GPU上已经转换的数据来训练和模拟网络,而不需要指定“useGPU”论点。然后用互补函数将得到的GPU数组转换并返回到MATLAB中gpu2nndata

在使用gpuArray数据进行训练之前,网络的输入和输出必须使用正则MATLAB矩阵手动配置配置功能:

net2 =配置(net1 x, t);%用MATLAB数组配置net2 =火车(net2 xg, tg);%在GPU上执行NNET格式化的gpuArraysyg = net2 (xg);GPU执行%y = gpu2nndata (yg);%将数组转移到本地工作区

在gpu和其他硬件上,你可能想要部署你的神经网络,它通常是指数函数经验值不是通过硬件实现的,而是通过软件库实现的。这可以减慢神经网络使用tansig乙状结肠传递函数。另一个函数是Elliot sigmoid函数,其表达式不包括对任何高阶函数的调用:

(方程)= n / (1 + abs (n))

在培训之前,网络的tansig层可以转换为elliotsig层如下:

我= 1:net.numLayers如果比较字符串(net.layers{我}.transferFcn,“tansig”) net.layers{}。transferFcn =“elliotsig”;结束结束

现在,在GPU上训练和模拟可能更快,部署硬件也更简单。

分布式GPU计算

分布式和GPU计算可以被组合在一起运行计算跨多个cpu和/或单个计算机上的GPU,或在一个集群上运行MATLAB并行服务器

最简单的方法是指定火车sim卡为此,使用由您使用的集群配置文件确定的并行池。的“showResources”在这种情况下,特别推荐使用选项,以验证正在使用预期的硬件:

net2 =火车(net1 x, t,“useParallel”,“是的”,“useGPU”,“是的”,“showResources”,“是的”) y = net2,“useParallel”,“是的”,“useGPU”,“是的”,“showResources”,“是的”)

这些代码行使用并行池中所有可用的工作者。每个独立的GPU都有一个工作人员使用该GPU,而其他工作人员则作为cpu运行。在某些情况下,只使用gpu可能会更快。例如,如果一台计算机有三个gpu和四个worker,三个gpu加速的三个worker的速度可能受到第四个CPU worker的限制。在这些情况下,您可以指定火车sim卡只使用具有独特gpu的工人。

net2 =火车(net1 x, t,“useParallel”,“是的”,“useGPU”,“只”,“showResources”,“是的”) y = net2,“useParallel”,“是的”,“useGPU”,“只”,“showResources”,“是的”)

与简单的分布式计算一样,分布式GPU计算可以从手动创建的复合值中获益。自己定义复合值可以指示使用哪些worker、为每个worker分配多少样本以及哪些worker使用gpu。

例如,如果你有四个工作人员和只有三个GPU,你可以为GPU工作人员定义更大的数据集。在这里,创建一个随机数据集,每个复合元素有不同的样本负载:

numSamples = [1000 1000 1000 300];xc =复合;tc =复合;xi = rand(2,numSamples(i));: ti = xi(1)。^ 2 + 3 * xi (2:);xc{我}= xi;tc{我}=钛;结束

你现在可以指定它火车sim卡使用三种可用的gpu:

net2 =配置(tc net1 xc {1}, {1});net2 =火车(xc net2, tc,“useGPU”,“是的”,“showResources”,“是的”);yc = net2 (xc、“showResources”,“是的”);

为了确保前三个worker使用gpu,请手动将每个worker的复合元素转换为gpuarray。每个worker在一个并行执行中执行这个转换spmd块。

spmd如果labindex <= 3 xc = nndata2gpu(xc);tc = nndata2gpu (tc);结束结束

现在数据指定了什么时候使用gpu,所以你不需要告诉火车sim卡这样做。

net2 =配置(tc net1 xc {1}, {1});net2 =火车(xc net2, tc,“showResources”,“是的”);yc = net2 (xc、“showResources”,“是的”);

确保每个GPU只被一个工人使用,这样计算是最有效的。如果多个worker在同一个GPU上分配gpuArray数据,计算仍然会进行,但速度会变慢,因为GPU会顺序地对多个worker的数据进行操作。

并行时间序列

对于时间序列网络,只需使用单元格数组值xt,可选包括初始输入延迟状态西和初始层延迟状态人工智能,如需要。

net2 =火车(net1 x, t, xi,人工智能,“useGPU”,“是的”) y = net2 (x, xi,人工智能,“useParallel”,“是的”,“useGPU”,“是的”(i, i, i, i, i, i, i, i, i,“useParallel”,“是的”) y = net2 (x, xi,人工智能,“useParallel”,“是的”,“useGPU”,“只”(i, i, i, i, i, i, i, i, i,“useParallel”,“是的”,“useGPU”,“只”) y = net2 (x, xi,人工智能,“useParallel”,“是的”,“useGPU”,“只”)

注意,并行遇到样本,或在时间序列在不同的系列。但是,如果网络只有输入延迟,没有层延迟,则延迟的输入可以被预先计算,这样为了计算的目的,时间步长就变成不同的样本,可以并行化。这是网络的情况,如timedelaynet和开环版本narxnetnarnet。如果网络有层延迟,那么时间就不能为了计算的目的被“扁平化”,因此单个序列数据就不能并行化。这是网络的情况,如layrecnet和闭环版本narxnetnarnet。但是,如果数据由多个序列组成,它可以跨多个单独的序列并行化。

并行可用性、回退和反馈

如前所述,您可以查询MATLAB来发现当前并行资源可用。

看看什么gpu在主机上可用:

gpuCount = gpuDeviceCounti = 1: gpuCount gpuDevice(我)结束

要查看当前并行池中运行了多少个worker:

poolSize = pool.NumWorkers

要查看在PC集群上运行的并行池中可用的gpu,请使用MATLAB并行服务器:

spmd工人。我ndex = labindex; worker.name = system(的主机名);工人。gpuCount = gpuDeviceCount;试一试工人。gpuInfo = gpuDevice;工人。gpuInfo = [];结束工人结束

“useParallel”“useGPU”“是的”,但是并行或GPU工作者是不可用的,约定是当资源被请求时,他们被使用如果可用。即使有错误,计算也不会出错。从请求的资源退回到实际资源的过程如下:

  • 如果“useParallel”“是的”但并行计算工具箱不可用,或并行池未打开,则计算返回到单线程MATLAB。

  • 如果“useGPU”“是的”但是当前MATLAB会话的gpuDevice未被分配或不被支持,然后计算返回到CPU。金宝app

  • 如果“useParallel”“useGPU”“是的”,然后用一个独特的GPU每个工人使用GPU,和其他工人回到CPU。

  • 如果“useParallel”“是的”“useGPU”“只”,然后使用具有独特gpu的工人。其他工作人员不被使用,除非没有工作人员有gpu。在没有gpu的情况下,所有工作人员都使用cpu。

如果不确定实际使用的是什么硬件,请检查gpuDeviceCount,gpuDevice,pool.NumWorkers以确保所需的硬件可用,并调用火车sim卡“showResources”设置为“是的”来验证实际使用了哪些资源。