Tensorflow多GPU使用详解

磐创AI

专注分享原创AI技术文章

翻译 | fendouai

编辑 | 磐石

【磐创AI导读】:本文编译自tensorflow官方网站,详细介绍了Tensorflow中多GPU的使用。欢迎大家点击上方蓝字关注我们的公众号:磐创AI

目录:

介绍

记录设备状态

手动分配状态

允许GPU内存增长

在多GPU系统是使用单个GPU

使用多个 GPU

一. 介绍

在一个典型的系统中,有多个计算设备。在 TensorFlow 中支持的设备类型包括 CPU 和 GPU。他们用字符串来表达,例如:

•"/cpu:0": 机器的 CPU

•"/device:GPU:0": 机器的 GPU 如果你只有一个

•"/device:GPU:1": 机器的第二个 GPU

如果 TensorFlow 操作同时有 CPU 和 GPU 的实现,操作将会优先分配给 GPU 设备。例如,matmul 同时有 CPU 和 GPU 核心,在一个系统中同时有设备 cpu:0 和 gpu:0,gpu:0 将会被选择来执行 matmul。

二. 记录设备状态

为了确定你的操作和张量分配给了哪一个设备,创建一个把 log_device_placement 的配置选项设置为 True 的会话即可。

# 创建一个计算图
a = tf.constant([1.0, 2.0, 3.0, 4.0, 5.0, 6.0], shape=[2, 3], name='a')
b = tf.constant([1.0, 2.0, 3.0, 4.0, 5.0, 6.0], shape=[3, 2], name='b')
c = tf.matmul(a, b)
# 创建一个 session,它的 log_device_placement 被设置为 True.
sess = tf.Session(config=tf.ConfigProto(log_device_placement=True))
# 运行这个操作
print(sess.run(c))

你将会看到一下输出:

Device mapping:
/job:localhost/replica:0/task:0/device:GPU:0 -> device: 0, name: Tesla K40c, pci bus
id: 0000:05:00.0
b: /job:localhost/replica:0/task:0/device:GPU:0
a: /job:localhost/replica:0/task:0/device:GPU:0
MatMul: /job:localhost/replica:0/task:0/device:GPU:0
[[ 22.  28.]
 [ 49.  64.]]

三. 手动分配设备

如果你希望一个特定的操作运行在一个你选择的设备上,而不是自动选择的设备,你可以使用 tf.device 来创建一个设备环境,这样所有在这个环境的操作会有相同的设备分配选项。

# 创建一个会话
with tf.device('/cpu:0'):
  a = tf.constant([1.0, 2.0, 3.0, 4.0, 5.0, 6.0], shape=[2, 3], name='a')
  b = tf.constant([1.0, 2.0, 3.0, 4.0, 5.0, 6.0], shape=[3, 2], name='b')
c = tf.matmul(a, b)
# 创建一个 session,它的 log_device_placement 被设置为 True
sess = tf.Session(config=tf.ConfigProto(log_device_placement=True))
# 运行这个操作
print(sess.run(c))

你将会看到 a 和 b 被分配给了 cpu:0。因为没有指定特定的设备来执行 matmul 操作,TensorFlow 将会根据操作和已有的设备来选择(在这个例子中是 gpu:0),并且如果有需要会自动在设备之间复制张量。

Device mapping:
/job:localhost/replica:0/task:0/device:GPU:0 -> device: 0, name: Tesla K40c, pci bus
id: 0000:05:00.0
b: /job:localhost/replica:0/task:0/cpu:0
a: /job:localhost/replica:0/task:0/cpu:0
MatMul: /job:localhost/replica:0/task:0/device:GPU:0
[[ 22.  28.]
 [ 49.  64.]]

四. 允许 GPU 内存增长

默认情况下,TensorFlow 将几乎所有的 GPU的显存(受 CUDA_VISIBLE_DEVICES 影响)映射到进程。 通过减少内存碎片,可以更有效地使用设备上宝贵的GPU内存资源。

在某些情况下,只需要分配可用内存的一个子集给进程,或者仅根据进程需要增加内存使用量。 TensorFlow 在 Session 上提供了两个 Config 选项来控制这个选项。

第一个是 allow_growth 选项,它根据运行时的需要分配 GPU 内存:它开始分配很少的内存,并且随着 Sessions 运行并需要更多的 GPU 内存,我们根据 TensorFlow 进程需要继续扩展了GPU所需的内存区域。请注意,我们不释放内存,因为这会导致内存碎片变得更糟。要打开此选项,请通过以下方式在 ConfigProto 中设置选项:

config = tf.ConfigProto()
config.gpu_options.allow_growth = True
session = tf.Session(config=config, ...)

第二种方法是 per_process_gpu_memory_fraction 选项,它决定了每个可见GPU应该分配的总内存量的一部分。例如,可以通过以下方式告诉 TensorFlow 仅分配每个GPU的总内存的40%:

config = tf.ConfigProto()
config.gpu_options.per_process_gpu_memory_fraction = 0.4
session = tf.Session(config=config, ...)

如果要真正限制 TensorFlow 进程可用的GPU内存量,这非常有用。

五. 在多GPU系统上使用单个GPU

如果您的系统中有多个GPU,则默认情况下将选择具有最低ID的GPU。 如果您想在不同的GPU上运行,则需要明确指定首选项:

# 创建一个计算图
with tf.device('/device:GPU:2'):
  a = tf.constant([1.0, 2.0, 3.0, 4.0, 5.0, 6.0], shape=[2, 3], name='a')
  b = tf.constant([1.0, 2.0, 3.0, 4.0, 5.0, 6.0], shape=[3, 2], name='b')
  c = tf.matmul(a, b)
# 创建一个 log_device_placement 设置为True 的会话
sess = tf.Session(config=tf.ConfigProto(log_device_placement=True))
# 运行这个操作
print(sess.run(c)) 

你会看到现在 a 和 b 被分配给 cpu:0。 由于未明确指定设备用于 MatMul 操作,因此 TensorFlow 运行时将根据操作和可用设备(本例中为 gpu:0)选择一个设备,并根据需要自动复制设备之间的张量。

如果指定的设备不存在,将得到 InvalidArgumentError:

InvalidArgumentError: Invalid argument: Cannot assign a device to node 'b':
Could not satisfy explicit device specification '/device:GPU:2'
   [[Node: b = Const[dtype=DT_FLOAT, value=Tensor<type: float shape: [3,2]
   values: 1 2 3...>, _device="/device:GPU:2"]()]]

如果希望 TensorFlow 在指定的设备不存在的情况下自动选择现有的受支持设备来运行操

作,则可以在创建会话时在配置选项中将 allow_soft_placement 设置为 True。

# 创建计算图
with tf.device('/device:GPU:2'):
  a = tf.constant([1.0, 2.0, 3.0, 4.0, 5.0, 6.0], shape=[2, 3], name='a')
  b = tf.constant([1.0, 2.0, 3.0, 4.0, 5.0, 6.0], shape=[3, 2], name='b')
  c = tf.matmul(a, b)
# 创建一个 allow_soft_placement 和 log_device_placement 设置为 True 的会话
 
sess = tf.Session(config=tf.ConfigProto(
      allow_soft_placement=True, log_device_placement=True))
# 运行这个操作
print(sess.run(c))

六. 使用多个 GPU

如果您想要在多个 GPU 上运行 TensorFlow ,则可以采用多塔式方式构建模型,其中每个塔都分配有不同的 GPU。 例如:

# 创建计算图
c = []
for d in ['/device:GPU:2', '/device:GPU:3']:
  with tf.device(d):
    a = tf.constant([1.0, 2.0, 3.0, 4.0, 5.0, 6.0], shape=[2, 3])
    b = tf.constant([1.0, 2.0, 3.0, 4.0, 5.0, 6.0], shape=[3, 2])
    c.append(tf.matmul(a, b))
with tf.device('/cpu:0'):
  sum = tf.add_n(c)
# 创建一个 log_device_placement 设置为 True 的会话
sess = tf.Session(config=tf.ConfigProto(log_device_placement=True))
# 运行这个操作
print(sess.run(sum))

你将会看到以下的输出:

Device mapping:
/job:localhost/replica:0/task:0/device:GPU:0 -> device: 0, name: Tesla K20m, pci bus
id: 0000:02:00.0
/job:localhost/replica:0/task:0/device:GPU:1 -> device: 1, name: Tesla K20m, pci bus
id: 0000:03:00.0
/job:localhost/replica:0/task:0/device:GPU:2 -> device: 2, name: Tesla K20m, pci bus
id: 0000:83:00.0
/job:localhost/replica:0/task:0/device:GPU:3 -> device: 3, name: Tesla K20m, pci bus
id: 0000:84:00.0
Const_3: /job:localhost/replica:0/task:0/device:GPU:3
Const_2: /job:localhost/replica:0/task:0/device:GPU:3
MatMul_1: /job:localhost/replica:0/task:0/device:GPU:3
Const_1: /job:localhost/replica:0/task:0/device:GPU:2
Const: /job:localhost/replica:0/task:0/device:GPU:2
MatMul: /job:localhost/replica:0/task:0/device:GPU:2
AddN: /job:localhost/replica:0/task:0/cpu:0
[[  44.   56.]
 [  98.  128.]]

(编译自:

https://www.tensorflow.org/programmers_guide/using_gpu)

原文发布于微信公众号 - 磐创AI(xunixs)

原文发表时间:2018-06-13

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏ATYUN订阅号

将Keras深度学习模型部署为Web应用程序

建立一个很酷的机器学习项目确实很不错,但如果你希望其他人能够看到你的作品怎么办呢?当然,你可以将整个项目放在GitHub上,但这只能给程序员看,如果你想给自己家...

2471
来自专栏用户2442861的专栏

Caffe学习系列(12):训练和测试自己的图片

学习caffe的目的,不是简单的做几个练习,最终还是要用到自己的实际项目或科研中。因此,本文介绍一下,从自己的原始图片到lmdb数据,再到训练和测试模型的整个...

991
来自专栏深度学习思考者

Python常用第三方模块PIL(anaconda下载)

前提:针对深度学习的用户,推荐下载anaconda,其下载地址如下: https://repo.continuum.io/archive/.winzip/ ...

2819
来自专栏简书专栏

深度学习环境搭建-CUDA9.0、cudnn7.3、tensorflow_gpu1.10的下载

本文作者接触深度学习2个月后,开始进行目标检测实践。 本文作者的专题《目标检测》链接:https://www.jianshu.com/c/fd1d6f784c...

2162
来自专栏Deep learning进阶路

caffe随记(八)---使用caffe训练FCN的pascalcontext-fcn32s模型(pascal-context数据集)

本篇讨论利用caffe进行FCN训练(采用的是pascal-context数据集) 1、下载FCN的框架 https://github.com/shelham...

4740
来自专栏calvin

SSH通过SSH代理连接到内网机器

操作步骤: 1.实现本地机器到代理机器的SSH连接。 ssh ftpuser@proxyip

2023
来自专栏SeanCheney的专栏

《Scikit-Learn与TensorFlow机器学习实用指南》 第12章 设备和服务器上的分布式 TensorFlow

在第 11 章,我们讨论了几种可以明显加速训练的技术:更好的权重初始化,批量标准化,复杂的优化器等等。 但是,即使采用了所有这些技术,在具有单个 CPU 的单台...

881
来自专栏梦里茶室

TensorFlow深度学习笔记 Tensorboard入门

Github工程地址:https://github.com/ahangchen/GDLnotes 官方教程:https://www.tensorflow.org...

2038
来自专栏非著名程序员

Android二维码扫描开发(一):实现思路与原理

? 现在二维码已经非常普及了,那么二维码的扫描与处理也成为了Android开发中的一个必要技能。网上有很多关于Android中二维码处理的帖子,大都是在讲开源...

2417
来自专栏一个会写诗的程序员的博客

安装 TensorFlow安装 TensorFlow

我们已在如下配置的 64 位笔记本电脑/台式机操作系统中构建并测试过 TensorFlow:

762

扫码关注云+社区