我目前正在将我的tf代码过渡到tfrecords和tf数据集。在我的应用程序中,训练后的模型通常会在看到所有训练样本之前收敛。因此,我通常将自己的数据生成器长度设置为我希望在一个纪元中放入的批次数量,并确保在我的生成器中,在下一个纪元中,该生成器在上一个纪元的最后一个样本之后开始提取。这样,所有回调都可以按需工作(尤其是提前停止),而我仍然可以在每个时期使用看不见的数据来训练我的模型。
如何使用tf数据集和tfrecords实现此行为?我已经阅读了tensorflow Github上的数据集定义,但不确定是否可行。
我认为如果设置steps_per_epoch
,有两种可能的解决方案:
但是,我也不知道该如何完成。因此,如果您对此有任何见解,我将不胜感激。
目前,我可以使用一种优雅的解决方法,在该方法中,我总是训练一个时期,然后使用新的tfrecord文件初始化一个新的数据集,但是我希望有更好的方法,尤其是在回调方面。
我不确定我是否完全理解您要达到的目标。您想要:
就是这样?
从我的角度来看,steps_per_epoch
参数是最好的选择。如果您有一个数据集,例如包含100个项目(样本或批次),并且您设置了steps_per_epoch=20
,则在第一个时期,您的模型将看到项目0到19,在第二个时期看到20到39,依此类推。无需覆盖代码的任何部分。
尝试模仿数据集的行为可能不是一个好主意(要注意的事情太多,涉及很多(艰巨的)工作)。
从您的上一段开始,我了解到您希望每个时期都来自特定TFRecord文件的数据。也许您可以看看tf.data.Dataset.flat_map
。建立您的TFRecord文件列表(同一文件可以多次出现),并在其上显示“ tf.data.Dataset.flat_map
” flat_map
:
TFRecordDataset
迭代数据集将为您提供来自文件1,然后来自文件2,然后又来自文件1,然后来自文件3的files = tf.data.Dataset.from_tensor_slices([
"file1.tfrecord", "file2.tfrecord",
"file1.tfrecord", "file3.tfrecord"
])
dataset = file.flat_map(TFRecordDataset)
。
希望这会有所帮助。