2016-06-14 78 views
1

我正在构建基于Tensorflow的skflow库的多个DNN模型。我将我的数据分成小型文件,并使用partial_fit进行拟合。在partial_fit的每个循环之后,我想将TensorFlowDNNClassifier模型的第一个隐藏层的权重复制到另一个TensorFlowDNNClassifier模型中。然后继续使用partial_fit进行学习/复制。 (两个模型的第一n隐藏层的拓扑结构是相同的。)如何在fit/partial_fit之后处理skflow模型的权重?

我知道如何检索来自classifier1权重:

classifier.get_tensor_value('DNN /层0 /线性/矩阵:0 “)

但我不知道如何将他们的值复制到classifier2!

的用例:

我试图建立一个基于skflow的TensorFlowDNNClassifier/TensorFlowDNNRegressor中号DNN模型的集合。我希望这些M模型分享彼此之间的前n层。也就是说,相同的输入,体系结构和。我想通过对skflow的原始代码进行最小限度的更改来完成此操作。为了做到这一点,我想到了将我的数据分成小型文件,并在当时训练模型中的一个小型文件。在每个步骤(使用minibatch)期间,我将partial_fit应用于一个模型,并将其第一个隐藏层的权重复制到合奏中的下一个模型。然后我使用相同的小批次partial_fit第二个模型,然后将权重的新值复制到下一个模型。我重复这个训练/复制,直到我到达合奏中的最后一个模型。训练完第M个模型后,我将其第一个隐藏层的权重复制到所有以前的(M-1)模型中。然后我用下一个小批次重复这个过程,直到所有M个模型的权重收敛。

编辑:感谢@Ismael和@ilblackdragon(通过另一个论坛)提供宝贵意见。他们建议的解决方案最适合模型创建。我不得不为TensorFlowEstimator添加额外的功能,这样我就可以轻松地将权重从一个模型复制到另一个模型中(在minibatches上进行多个步骤的训练)。我添加以下功能到类TensorFlowEstimator(在文件估计/ 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]) 

然后添加以下行到使用自创建模型的图表之后_setup_training功能。 model_fn(self._inp,self._out)

 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

您应该使用TensorFlowEstimator,您可以在其中定义自定义模型,基本上可以将任何TensorFlow代码插入到自定义模型中。

所以如果你知道如何检索您可以使用tf.Variable的权重,并通过权重到一个新的DNN作为其初始值,因为:

TF。变量可以具有可作为初始值转换为 张量的张量或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") 
相关问题