请教关于一个batch内的数据如何并行训练的问题
Created by: adrain-huang
我使用的是GPU版本的fluid 1.5.1,GPU为1块NVIDIA GTX 1080TI,操作系统为Ubuntu 16.04。 因为看到一行代码,我不知道如何理解,故请教。 项目为AI Studio上的一个示例项目,名称为:课程4-深度学习入门CV-手写数字识别。 项目地址为:https://aistudio.baidu.com/aistudio/projectdetail/78958
在第127行处有一个代码块:
'''使用交叉熵损失函数,描述真实样本标签和预测概率之间的差值'''
cost = fluid.layers.cross_entropy(input=predict, label=label)
'''使用类交叉熵函数计算predict和label之间的损失函数'''
avg_cost = fluid.layers.mean(cost)
'''计算分类准确率'''
acc = fluid.layers.accuracy(input=predict, label=label)
我不知道如何理解avg_cost = fluid.layers.mean(cost)这一行代码。
我的问题有两点:
问题1、这个网络的输入部分为:
'''输入的原始图像数据,大小为1x28x28''' image = fluid.layers.data(name='image', shape=[1, 28, 28], dtype='float32')#单通道,28*28像素值 '''标签,名称为label,对应输入图片的类别标签''' label = fluid.layers.data(name='label', shape=[1], dtype='int64') #图片标签
这里已经定义了输入image的形状为[1, 28, 28],也即网络一次输入1张28*28的单色图像,就好像定义一个人一次只能吃一口饭。那么当我们一次输入一个batch时进行训练时(例如,BATCH_SIZE=128),请问如何真正做到并行训练?paddlepaddle好像屏蔽了并行处理的细节,我的问题是paddlepaddle如何利用一个net(这个net一次只能吃1张[1, 28, 28]的图片),而同时并行对一个batch(128张图片)的数据同时进行处理?虽然在训练时feed了一个batch的数据,但是我无法理解单个net怎么同时处理超过单张图片(整个batch的数据)。打个比方说,已经定义了一个人一次吃一口饭,而现在一次给他喂128口饭,这个人怎么同时吃呢?是不是在paddlepaddle内部,根据batch size的大小将net复制同样的份数,从而同时并行计算?
问题2、就是上面提到的那一行代码:
avg_cost = fluid.layers.mean(cost)
我理解的意思是对一个batch的cost计算平均值。但是从代码上我很难理解为什么这个cost就是整个batch的损失向量。原因为:
项目中定义了一个net,并对这个net输入图片进行训练。代码如下:
'''获取分类器'''
predict = multilayer_perceptron(image)
'''使用交叉熵损失函数,描述真实样本标签和预测概率之间的差值'''
cost = fluid.layers.cross_entropy(input=predict, label=label)
'''使用类交叉熵函数计算predict和label之间的损失函数'''
avg_cost = fluid.layers.mean(cost)
'''计算分类准确率'''
acc = fluid.layers.accuracy(input=predict, label=label)
但是,如前所述,单个net一次输入一张image,只能得到一个predict结果,这个predict和label计算cost(cross_entropy)也只能得到单个cost值,这个cost值本身是一个标量,如何再进一步计算整个batch的cost的平均值?(avg_cost = fluid.layers.mean(cost))?
更加直白地说,关键的是,代码中也是根据单个net和单张image计算的cost,代码如下:
image = fluid.layers.data(name='image', shape=[1, 28, 28], dtype='float32')
label = fluid.layers.data(name='label', shape=[1], dtype='int64')
predict = multilayer_perceptron(image)
cost = fluid.layers.cross_entropy(input=predict, label=label)
avg_cost = fluid.layers.mean(cost)
为什么突然这个cost就和整个batch联系起来了变成了整个batch中各个样本的cost向量呢?只有整个batch的cost向量才能进行求平均操作啊(mean)。
我请教了paddlepaddle官网的QQ群,管理员认为这个问题对于理解代码、理解网络的并行训练比较重要。所以建议我提issue问研发的工程师,还望抽时间帮忙看看,谢谢!