我正在尝试使用tensorflow估计器api训练DNNRegressor,该数据库具有约1.2Tb的庞大数据集,其中包含5万个GZIP压缩的CSV文件。 我知道使用TFRecord文件的速度要快得多,但是转换5万个文件会花费很多时间。
每行数据都包含1035个浮动特征和2个我要预测的浮动标签(是的,它很大)。 映射函数创建输入,并使用包含每个要素的最大值和最小值的缩放器文件进行归一化。
我将parralel_interleave用于我的输入管道,因为每个文件的内容都包含相似的数据,但略有差异。要创建改组的批次,我从10个不同的文件中读取了5行,以创建大小为50的改组后的批次。
def tf_input_function():
files = tf.data.Dataset.list_files('D:/Data/training/*gz')
dataset = files.apply(
tf.data.experimental.parallel_interleave(
lambda filename: (tf.data.TextLineDataset(filename, compression_type="GZIP")).map(parse_csv,
num_parallel_calls=8).batch(
batch_size).prefetch(1),
cycle_length=10,
sloppy=True,
buffer_output_elements=10,
prefetch_input_elements=1))
iterator = dataset.make_one_shot_iterator()
features, labels = iterator.get_next()
return features, labels
def parse_csv(line):
fields = tf.decode_csv(line, FIELD_DEFAULTS)
labels = fields[-2:]
del fields[-2:]
# Pack the result into a dictionary
feats = dict(zip(COLUMNS, fields))
# Separate the label from the features
return scaleFeatures(feats), labels
def scaleFeatures(features):
index = 0
for x in features:
min_x = minmax[index][0]
max_x = minmax[index][1]
if max_x != min_x:
features[x] = (features[x] - min_x) / (max_x - min_x)
index += 1
return features
def run_model():
feature_columns = [
tf.feature_column.numeric_column(name)
for name in COLUMNS]
est = tf.estimator.DNNRegressor(
config=tf.estimator.RunConfig(
save_checkpoints_steps=100000,
keep_checkpoint_max=5000,
),
feature_columns=feature_columns,
hidden_units=[1500],
label_dimension=2,
optimizer=lambda: tf.train.AdamOptimizer(learning_rate=0.0001),
dropout=0.5,
activation_fn=tf.nn.leaky_relu,
model_dir="D:/Stock Data/n1"
)
train_spec = tf.estimator.TrainSpec(input_fn=lambda: tf_input_function('train'),
max_steps=TRAIN_STEPS)
eval_spec = tf.estimator.EvalSpec(input_fn=lambda: tf_input_function('validation'), steps=EVAL_STEPS)
tf.estimator.train_and_evaluate(est, train_spec, eval_spec)
问题是我用来馈送网络的管道超级慢。 对于100步(每步批量为50),需要约6秒钟的时间进行训练。 这是DNNRegressor培训的输出:
INFO:tensorflow:loss = 40.882965, step = 6365506 (13.298 sec)
INFO:tensorflow:global_step/sec: 19.33
INFO:tensorflow:loss = 25.407375, step = 6365606 (5.189 sec)
INFO:tensorflow:global_step/sec: 19.8323
INFO:tensorflow:loss = 80.53043, step = 6365706 (5.032 sec)
INFO:tensorflow:global_step/sec: 19.943
INFO:tensorflow:loss = 542.24744, step = 6365806 (5.011 sec)
INFO:tensorflow:global_step/sec: 19.9351
INFO:tensorflow:loss = 21.753256, step = 6365906 (5.046 sec)
INFO:tensorflow:global_step/sec: 23.0136
INFO:tensorflow:loss = 50.146282, step = 6366006 (4.321 sec)
INFO:tensorflow:global_step/sec: 19.9311
INFO:tensorflow:loss = 38.326336, step = 6366106 (5.012 sec)
INFO:tensorflow:global_step/sec: 14.869
INFO:tensorflow:loss = 56.946716, step = 6366206 (6.724 sec)
INFO:tensorflow:global_step/sec: 18.1742
INFO:tensorflow:loss = 33.119816, step = 6366306 (5.500 sec)
文件存储在HDD上,其读取速度至少为50MB / s,但是在训练过程中进行监视时,它以2MB / s的组合速度读取文件...是因为它必须读取多个文件,因此顺序读取? (移动硬盘磁头等的开销...) 我尝试使用SSD(SATA 3),它甚至更慢...
同样使用parrallel_interleave进行培训会消耗我100%的CPU。
所以我最重要的问题是,是否有一种方法可以大大加快培训速度?
以这种方式进行训练将使我花费30天的时间来完成一个单一的时间段...
注意:使用GPU的速度比使用CPU的速度稍慢,因此我认为问题在于管道的设置方式