我的主要问题是:我有200 GB的训练tfrecord文件,有200万张图像,28GB用于验证tf.record文件,302900张图像.培训一个时代需要8个小时,培训需要33天.我想通过使用多个线程和分片加快速度,但我对一些事情有点困惑.
在tf.data.Dataset API中有shard函数,所以在文档中他们提到了关于shard函数的以下内容:
创建仅包含此数据集的1/num_shards的数据集.
此数据集运算符在运行分布式培训时非常有用,因为它允许每个工作者读取唯一的子集.
读取单个输入文件时,可以跳过如下元素:
d = tf.data.TFRecordDataset(FLAGS.input_file)
d = d.shard(FLAGS.num_workers, FLAGS.worker_index)
d = d.repeat(FLAGS.num_epochs)
d = d.shuffle(FLAGS.shuffle_buffer_size)
d = d.map(parser_fn, num_parallel_calls=FLAGS.num_map_threads)
Run Code Online (Sandbox Code Playgroud)
重要提示:
在使用任何随机化运算符(例如shuffle)之前,请务必进行分片.通常,最好在数据集管道的早期使用分片运算符.>例如,从一组TFRecord文件中读取时,在转换之前将分片>数据集输入样本.这样可以避免读取每个工作人员的每个文件.以下是完整>管道中有效分片策略的示例:
d = Dataset.list_files(FLAGS.pattern)
d = d.shard(FLAGS.num_workers, FLAGS.worker_index)
d = d.repeat(FLAGS.num_epochs)
d = d.shuffle(FLAGS.shuffle_buffer_size)
d = d.repeat()
d = d.interleave(tf.data.TFRecordDataset,
cycle_length=FLAGS.num_readers, block_length=1)
d = d.map(parser_fn, num_parallel_calls=FLAGS.num_map_threads)
Run Code Online (Sandbox Code Playgroud)
这些是我的问题:
1- tf.records文件的数量与分片数量之间是否有任何关系?是碎片数量(工人)取决于你拥有的CPU数量,或者你拥有的tf.records文件的数量?以及如何创建它,只需将分片数设置为特定数字?,或者我们需要将文件拆分为多个文件,然后设置特定的分片数.请注意参考碎片数量的工人数量
2-创建多个tf.records文件有什么好处?有些人说这里是关于什么时候你需要以更好的方式改变tf.records,但是在tf.Dataset API中存在Shuufle方法我们不需要这样做,而其他人在这里说它只是分裂你的数据到较小尺寸的零件.我的问题我是否需要将我的tf.records文件拆分为多个文件
3-现在我们来到map函数中的num_threads(在新版本的tensorflwo中的num_paralle_calls)应该与你拥有它的碎片数量相同.当我搜索时,我发现有人说如果你有10个分片和2个线程,每个线程将需要5个分片.
4-关于d.interleave函数,我知道它是如何工作的,就像在这个例子中提到的那样.但是我再次错过了连接num_threads,例如循环长度
5-如果我想使用多个GPU,我应该使用分片吗?如此处接受的评论中所述
作为总结,我对(tf.records文件的数量,num_shards(工人),循环长度,num_thread(num_parallel_calls)之间的关系感到困惑.为了最大限度地缩短两种情况的训练时间,创建的情况更好(使用多个GPU,并使用单GPU)
我是tf.data开发人员。让我们看看我是否可以帮助您回答问题。
1)听起来您有一个大文件。要使用多个工作程序来处理它,将它分割成多个较小的文件是有意义的,以便tf.data输入管道可以在不同的工作程序上处理不同的文件(通过在shard文件名列表上应用该功能)。
2)如果您不将单个文件拆分为多个记录,则每个工作程序都必须读取整个文件,这会消耗IO带宽的n倍(其中n是workerS的数量)。
3)用于map转换的线程数与分片数无关。每个分片将由num_parallel_calls每个工人处理。通常,合理地设置num_parallel_calls与该工作线程上可用核心数成比例的位置。
4)interleave转换的目的是将多个数据集(例如,从不同的TFRecord文件读取)合并为一个数据集。给定您的用例,我认为您不需要使用它。
5)如果要使用多个GPU,建议您使用引用的注释中列出的第一个选项,因为这是最简单的。所述shard基于溶液需要创建上每个工人的多个管线(对每个GPU)。
为了最大程度地减少训练时间(对于单个或多个GPU,您要确保输入管道生成的数据快于GPU可以处理的速度。此处讨论了输入管道的性能调整。
| 归档时间: |
|
| 查看次数: |
1791 次 |
| 最近记录: |