我正在尝试在Tensorflow中设置一个优化图,避免将feed_dict
与tf.FIFOQueue
一起使用 - 至少这似乎是时间序列数据的正确方向。
我将首先使用feed_dict
描述我的图表(以最小的术语),然后我尝试接受它。
假设我的时间序列存储在一个numpy数组time_series
中:
wnd = 10 # window size
data_wnd = np.array([time_series[n:n+wnd] for n in range(1,time_series.size()+1)])
现在data_wnd[k]
可以代表时间序列中的窗口k
。
假设step
是我的Tensorflow优化器,这可以通常如下工作:
for k in range(data_wnd.shape[0]):
for n in range(epochs):
sess.run(step, feed_dict={data_:data_wnd[k]})
# Do stuff after optimization and proceed to next window frame
# the optimized variable values for this frame are the initial values for the next frame
如果我没有窗口,那么我可以简单地使用data_
并删除tf.constant
,而不是使用占位符feed_dict
。所以这是不可能的。
所以来tf.FIFOQueue
:
q = tf.FIFOQueue(capacity=5, shapes=(wnd))
nq_op = q.enqueue(data_wnd[0])
qr = tf.train.QueueRunner(q, [nq_op]*1) # nq_op is not right
tf.train.add_queue_runner(qr)
data_ = q.dequeue() # instead of a placeholder
很好,所以现在我有一个队列,但这显然是错误的。 qr
需要根据k
将正确的数据框提供到队列中。有没有办法让enqueue
或QueueRunner
选择正确的框架?
更好的是,是否有一些专门的Tensorflow API以这种方式处理时间序列数据?
解决方案的一个重要约束要求我将所有内容保留在同一会话中,并且不会重新初始化变量,因为帧的优化解决方案接近前一帧的最佳解决方案。
提案不完整
我在考虑将几个nq_op
定义如下:
nq_op = []
for k in range(data_wnd.shape[0]):
nq_op = np.append(nq_op, q.enqueue(data_wnd[0]))
但这仍然需要QueueRunner
正确选择正确的enqueue
。
另一项提案
显然Tensorflow现在有一个tf.data
API,但我不知道从哪里开始 - 或者就此而言,结束 - 使用此API。
答案 0 :(得分:0)
我发现FIFOQueue不是正确的方向。
相反,this page在预加载数据下提供了正确的方法。
我们可以为data_
使用占位符和变量的组合,而不是简单地使用占位符:
data_init = tf.placeholder(tf.float32, data_wnd.shape[0])
data_ = tf.Variable(data_init, trainable=False, collection=0)
正确定义VarType
和TensorShape
。
然后在我们的循环中:
for k in range(data_wnd.shape[0]):
sess.run(data_.initializer, feed_dict={data_:data_wnd[k]})
for n in range(epochs):
sess.run(step)
请注意我们不再需要为每个n
提供数据,但仅限于我们向前移动窗口时。