Python 如何在Keras中使用reset_状态(states)功能?
我试图在训练每个批次之前设置LSTM内部状态。 我正在分享我的测试代码和发现,希望找到答案,并帮助解决类似问题的其他人 特别是,对于每个数据,我都有一个特征X(不会随时间变化)和一个序列p=p1,p2,p3,。。。第30页。 目标是:给定X和p1,p2,p3预测p4,p5。。第30页 为此,我想用X初始化LSTM的隐藏状态,正如在一些工作中所做的那样(例如neuraltalk),然后LSTM必须与p1、p2、p3相匹配,以预测p4、…、p30。 每次批处理之前都需要进行初始化(batch_size=1),因此我需要控制LSTM状态初始化。 考虑到这个问题,我已经测试了以下代码: 首先,我在recurrent.py中定义的reset_states()函数中添加了一些打印,以便了解到底发生了什么Python 如何在Keras中使用reset_状态(states)功能?,python,deep-learning,keras,lstm,rnn,Python,Deep Learning,Keras,Lstm,Rnn,我试图在训练每个批次之前设置LSTM内部状态。 我正在分享我的测试代码和发现,希望找到答案,并帮助解决类似问题的其他人 特别是,对于每个数据,我都有一个特征X(不会随时间变化)和一个序列p=p1,p2,p3,。。。第30页。 目标是:给定X和p1,p2,p3预测p4,p5。。第30页 为此,我想用X初始化LSTM的隐藏状态,正如在一些工作中所做的那样(例如neuraltalk),然后LSTM必须与p1、p2、p3相匹配,以预测p4、…、p30。 每次批处理之前都需要进行初始化(batch_siz
def reset_states(self, states=None):
if not self.stateful:
raise AttributeError('Layer must be stateful.')
batch_size = self.input_spec[0].shape[0]
if not batch_size:
raise ValueError('If a RNN is stateful, it needs to know '
'its batch size. Specify the batch size '
'of your input tensors: \n'
'- If using a Sequential model, '
'specify the batch size by passing '
'a `batch_input_shape` '
'argument to your first layer.\n'
'- If using the functional API, specify '
'the time dimension by passing a '
'`batch_shape` argument to your Input layer.')
# initialize state if None
if self.states[0] is None:
self.states = [K.zeros((batch_size, self.units))
for _ in self.states]
print "reset states A (all zeros)"
elif states is None:
for state in self.states:
K.set_value(state, np.zeros((batch_size, self.units)))
print "reset states B (all zeros)"
else:
if not isinstance(states, (list, tuple)):
states = [states]
print "reset states C (list or tuple copying)"
if len(states) != len(self.states):
raise ValueError('Layer ' + self.name + ' expects ' +
str(len(self.states)) + ' states, '
'but it received ' + str(len(states)) +
' state values. Input received: ' +
str(states))
for index, (value, state) in enumerate(zip(states, self.states)):
if value.shape != (batch_size, self.units):
raise ValueError('State ' + str(index) +
' is incompatible with layer ' +
self.name + ': expected shape=' +
str((batch_size, self.units)) +
', found shape=' + str(value.shape))
K.set_value(state, value)
print "reset states D (set values)"
print value
print "\n"
以下是测试代码:
import tensorflow as tf
from keras.layers import LSTM
from keras.layers import Input
from keras.models import Model
import numpy as np
import keras.backend as K
input = Input(batch_shape=(1,3,1))
lstm_layer = LSTM(10,stateful=True)(input)
>>> reset states A (all zeros)
如您所见,第一次打印是在创建lstm层时执行的
model = Model(input,lstm_layer)
model.compile(optimizer="adam", loss="mse")
with tf.Session() as sess:
tf.global_variables_initializer().run()
h = sess.run(model.layers[1].states[0])
c = sess.run(model.layers[1].states[1])
print h
>>> [[ 0., 0., 0., 0., 0., 0., 0., 0., 0., 0.]]
print c
>>> [[ 0., 0., 0., 0., 0., 0., 0., 0., 0., 0.]]
内部状态已设置为全零。
也可以使用函数reset_states()
model.layers[1].reset_states()
>>> reset states B (all zeros)
在这种情况下,已打印第二条消息。一切似乎都正常工作。
现在我想用任意值设置状态
new_h = K.variable(value=np.ones((1, 10)))
new_c = K.variable(value=np.ones((1, 10))+1)
model.layers[1].states[0] = new_h
model.layers[1].states[1] = new_c
with tf.Session() as sess:
tf.global_variables_initializer().run()
h = sess.run(model.layers[1].states[0])
c = sess.run(model.layers[1].states[1])
print h
>>> [[ 1., 1., 1., 1., 1., 1., 1., 1., 1., 1.]]
print c
>>> [[ 2., 2., 2., 2., 2., 2., 2., 2., 2., 2.]]
好的,我已经成功地用所有1和所有2的向量设置了两个隐藏状态。
但是,值得利用类函数reset_states(),它将状态作为输入。
此函数利用函数K.set_values(x,values),该函数期望“values”为numpy数组
new_h_5 = np.zeros((1,10))+5
new_c_24 = np.zeros((1,10))+24
model.layers[1].reset_states([new_h_5,new_c_24])
这似乎是可行的,事实上,输出是:
>>> reset states D (set values)
>>> [[ 5. 5. 5. 5. 5. 5. 5. 5. 5. 5.]]
>>>
>>>
>>>
>>>
>>> reset states D (set values)
>>> [[ 24. 24. 24. 24. 24. 24. 24. 24. 24. 24.]]
但是,如果我想检查状态是否已初始化,我会找到以前的初始化值(全部一个,全部两个)
这里到底发生了什么?为什么函数似乎根据打印工作,但不更改内部状态的值?正如您所读到的,value参数设置了一个值,通过该值可以初始化变量。因此,当您调用tf.global\u variables\u initializer().run()
时,您的状态将使用此处定义的值进行初始化:
new_h = K.variable(value=np.ones((1, 10)))
new_c = K.variable(value=np.ones((1, 10))+1)
编辑:
这对我来说似乎很明显,但我将再次解释为什么reset\u states
不起作用
Variable\u initializer
时,都会设置该特定值好的,但这并不能解释当我使用reset_states函数mmm时会发生什么。。我仍然不清楚如何通过reset_states函数使用第二种方法设置状态您的主要目标是什么?我在问题中解释过,我想在使用上下文向量(即与该批次的输入序列相关的功能)训练每个批次之前重置状态然后,您应该只在开始时初始化变量一次,并在每个批次之前使用
reset\u states
。
new_h = K.variable(value=np.ones((1, 10)))
new_c = K.variable(value=np.ones((1, 10))+1)