我正在构建基于Tensorflow的skflow库的多个DNN模型。我将数据分区为minibatches并使用partial_fit进行拟合。在partial_fit的每个循环之后,我想将TensorFlowDNNC分类器模型的第一个n隐藏层的权重复制到另一个TensorFlowDNNC分类器模型。然后使用partial_fit继续学习/复制。 (两个模型的前n个隐藏层的拓扑结构相同。)
我知道如何从classifier1中检索权重:
classifier.get_tensor_value( 'DNN /层0 /线性/矩阵:0')
但我不知道如何将其值复制到分类器2中!
用例:
我正在尝试基于skflow的TensorFlowDNNClassifier / TensorFlowDNNRegressor构建一个M DNN模型的集合。我希望这些M模型能够在彼此之间共享前n层。也就是说,相同的输入,体系结构和值。我想通过对skflow原始代码的最小改动来做到这一点。为此,我想把我的数据划分为小批量,并在当时训练模型一个小批量。在每个步骤(使用小批量)中,我在一个模型上应用partial_fit,并将其第一个n隐藏层的权重复制到整体中的下一个模型。然后我使用相同的minibatch对第二个模型进行partial_fit,然后将权重的新值复制到下一个模型。我重复这个训练/复制,直到我到达整体中的最后一个模型。在训练Mth模型之后,我将其第一个n隐藏层的权重复制到所有先前的(M-1)模型。然后我用下一个小批量重复这个,直到所有M型号的重量收敛。
编辑:感谢@Ismael和@ilblackdragon(通过其他论坛)提供的宝贵意见。他们建议的解决方案最适合模型创建。我不得不为TensorFlowEstimator添加额外的功能,这样我就可以在训练时轻松地将权重从一个模型复制到另一个模型(在微型计算机上进行多步训练)。我将以下函数添加到类 TensorFlowEstimator (在文件estimators / base.py中定义)
def extract_num_hidden_layers(self,graph_ops):
nhl = 0
are_there_more_layers = True
while are_there_more_layers:
are_there_more_layers = False
layerName = 'dnn/layer' + str(nhl) + '/Linear/Matrix'
for op in graph_ops:
if(op.name == layerName):
nhl+=1
are_there_more_layers = True
break
return nhl
def create_updaters(self):
self.weight_updaters = []
self.bias_updaters = []
for h in range(0,self.num_hidden_layers):
with tf.variable_scope('', reuse=True):
wName = 'dnn/layer' + str(h) + '/Linear/Matrix'
wUpOp = tf.assign(tf.get_variable(wName), self.nValues)
self.weight_updaters.append(wUpOp)
bName = 'dnn/layer' + str(h) + '/Linear/Bias'
bUpOp = tf.assign(tf.get_variable(bName), self.nValues)
self.bias_updaters.append(bUpOp)
def get_layer_weights(self, layer_num):
layer_name = 'dnn/layer' + str(layer_num) + '/Linear/Matrix:0'
return self.get_tensor_value(layer_name)
def get_layer_biases(self, layer_num):
layer_name = 'dnn/layer' + str(layer_num) + '/Linear/Bias:0'
return self.get_tensor_value(layer_name)
def get_layer_params(self, layer_num):
return [self.get_layer_weights(layer_num), self.get_layer_biases(layer_num)]
def set_layer_weights(self, layer_num, weights_values):
self._session.run(self.weight_updaters[layer_num],
feed_dict = {self.nValues: weights_values})
def set_layer_biases(self, layer_num, biases_values):
self._session.run(self.bias_updaters[layer_num],
feed_dict = {self.nValues: biases_values})
def set_layer_params(self, layer_num, params_values):
self.set_layer_weights(layer_num, params_values[0])
self.set_layer_biases(layer_num, params_values[1])
然后我使用self.model_fn(self._inp,self._out)创建模型图后,将以下行添加到函数 _setup_training 中
graph_ops = self._graph.get_operations()
self.num_hidden_layers = self.extract_num_hidden_layers(graph_ops)
self.nValues = tf.placeholder(tf.float32)
#self.weight_updaters & self.bias_updaters
self.create_updaters()
这里有如何使用getter和setter函数:
iris = datasets.load_iris()
classifier = skflow.TensorFlowDNNClassifier(hidden_units=[10,5,4], n_classes=3,continue_training=True)
classifier.fit(iris.data, iris.target)
l1b = classifier.get_layer_biases(1)
l1b[3] = 2 # here I manually change the value for demo
classifier.set_layer_biases(1,l1b)
答案 0 :(得分:0)
您应该使用TensorFlowEstimator,您可以在其中定义自定义模型,基本上您可以将任何TensorFlow代码插入到自定义模型中。
因此,如果您知道如何检索权重,则可以使用tf.Variable并将权重传递给新的dnn作为其初始值,因为:
.Variable可以将Tensor或Python对象转换为 张量为初始值
。所以我认为权重的转移应该是这样的:
weights_i = classifier_i.get_tensor_value('dnn/layer0/Linear/Matrix:0')
def my_model_i_plus_1(X, y):
W = tf.Variable(weights_i)
b = tf.Variable(tf.zeros([biases_size]))
layer = tf.nn.relu(tf.matmul(X, W) + b)
return skflow.models.logistic_regression(layer, y)
classifier_i_plus_1 = skflow.TensorFlowEstimator(model_fn=my_model_i_plus_1,
n_classes=3,
optimizer="SGD")