如何加速hadoop上的tensorflow执行?

时间:2017-06-14 13:34:26

标签: python hadoop tensorflow hdfs

以下脚本执行非常慢。我只想计算twitter-follwer-graph中的总行数(文本文件大约为26 GB)。

我需要执行机器学习任务。这只是一个通过tensorflow访问hdfs数据的测试。

import tensorflow as tf
import time

filename_queue = tf.train.string_input_producer(["hdfs://default/twitter/twitter_rv.net"], num_epochs=1, shuffle=False)

def read_filename_queue(filename_queue):
    reader = tf.TextLineReader()
    _, line = reader.read(filename_queue)
    return line

line = read_filename_queue(filename_queue)

session_conf = tf.ConfigProto(intra_op_parallelism_threads=1500,inter_op_parallelism_threads=1500)

with tf.Session(config=session_conf) as sess:
    sess.run(tf.initialize_local_variables())
    coord = tf.train.Coordinator()
    threads = tf.train.start_queue_runners(coord=coord)

    start = time.time()
    i = 0
    while True:
        i = i + 1
        if i%100000 == 0:
            print(i)
            print(time.time() - start)

        try:
            sess.run([line])
        except tf.errors.OutOfRangeError:
            print('end of file')
            break
    print('total number of lines = ' + str(i))
    print(time.time() - start)

前100000行的过程大约需要40秒。 我尝试将intra_op_parallelism_threadsinter_op_parallelism_threads设置为0,4,8,40,400和1500.但它并没有显着影响执行时间......

你能帮助我吗?

系统规格:

  • 16 GB RAM
  • 4个CPU核心

5 个答案:

答案 0 :(得分:2)

您可以将大文件拆分为较小的文件,这可能有所帮助。并将intra_op_parallelism_threads和inter_op_parallelism_threads设置为0;

对于许多系统来说,使用多进程读取单个原始文本文件并不容易,tensorflow仅使用一个线程读取一个文件,因此调整tensorflow线程不会有帮助。 Spark可以处理具有多线程的文件,因为它将文件分成块,每个线程以块的形式读取内容,并在第一个\n之前忽略字符,因为它们属于最后一个块的最后一行。对于批量数据处理,Spark是更好的选择,而tensorflow更适合机器学习/深度学习任务;

答案 1 :(得分:1)

https://github.com/linkedin/TonY

使用TonY,您可以提交TensorFlow作业并指定工作人员数量以及他们是否需要CPU或GPU。

当使用TonY(Inception v3模型)在多台服务器上运行时,我们能够获得几乎线性的加速: enter image description here

下面是自述文件中如何使用它的示例:

tony目录中,还有一个tony.xml,其中包含您的所有TonY作业配置。 例如:

$ cat tony/tony.xml
<configuration>
  <property>
    <name>tony.worker.instances</name>
    <value>4</value>
  </property>
  <property>
    <name>tony.worker.memory</name>
    <value>4g</value>
  </property>
  <property>
    <name>tony.worker.gpus</name>
    <value>1</value>
  </property>
  <property>
    <name>tony.ps.memory</name>
    <value>3g</value>
  </property>
</configuration>

有关配置的完整列表,请参见Wiki。

型号代码
$ ls src/models/ | grep mnist_distributed
  mnist_distributed.py

然后您可以开始工作:

$ java -cp "`hadoop classpath --glob`:tony/*:tony" \
            com.linkedin.tony.cli.ClusterSubmitter \
            -executes src/models/mnist_distributed.py \
            -task_params '--input_dir /path/to/hdfs/input --output_dir /path/to/hdfs/output --steps 2500 --batch_size 64' \
            -python_venv my-venv.zip \
            -python_binary_path Python/bin/python \
            -src_dir src \
            -shell_env LD_LIBRARY_PATH=/usr/java/latest/jre/lib/amd64/server

命令行参数如下: * executes描述了您的训练代码入口点的位置。 * task_params描述了将传递给您的入口点的命令行参数。 * python_venv在本地描述将调用您的python脚本的zip的名称。 * python_binary_path描述了您的python虚拟环境中的相对路径,其中包含python二进制文件,或者是使用已在所有工作程序节点上安装的python二进制文件的绝对路径。 * src_dir在本地指定包含所有python模型源代码的根目录的名称。该目录将被复制到所有工作节点。 * shell_env指定将在您的python worker / ps进程中设置的环境变量的键值对。

答案 2 :(得分:0)

  

我也是一名使用tensorflow的初学者,但是因为你在问   从可信和/或官方来源获取答案,以下是我发现并可能有所帮助:

  1. 从源代码构建和安装
  2. 利用队列读取数据
  3. 在CPU上进行预处理
  4. 使用NCHW图像数据格式
  5. 在GPU上放置共享参数
  6. 使用融合批次规范
  7. 注意tensorflow performance guide 更详细地解释了上面列出的要点

      

    您可能想要研究的另一件事是   quantization

    这可以解释如何使用量化来减少存储和运行时的模型大小。量化可以提高性能,尤其是在移动硬件上。

答案 3 :(得分:0)

我通过使用spark来绕过这个性能问题。

答案 4 :(得分:-1)

试试这个,它应该会改善你的时间:

session_conf = tf.ConfigProto   
(intra_op_parallelism_threads=0,inter_op_parallelism_threads=0)

当您不知道什么是最佳值时,自带手中的Config是不好的。