Keras - 替换功能模型中的中间层

问题描述 投票:0回答:1

我正在尝试为 Keras 定制 LoRA 实现,但在尝试让我的方法发挥作用时遇到了一些麻烦。我在 Google Collab 中使用 Keras 3.4.1。

首先,我尝试了这个 Stack Overflow 帖子中解释的解决方案,当我使用 VGG16 时它对我有用。然而,我正在尝试提出一个适用于功能模型的解决方案,而不仅仅是适用于 VGG16 等顺序模型。

因此,我尝试做类似于这个 Keras 教程中解释的事情,但它对我不起作用。首先,我创建没有最后一层的模型,禁用其训练并打印其摘要:

vgg16_lora  = tf.keras.applications.vgg16.VGG16(weights="imagenet", input_shape=(224, 224, 3))
vgg16_lora.trainable = False

lora_model = tf.keras.Model(inputs=vgg16_lora.inputs, outputs=vgg16_lora.layers[-2].output)
lora_model.summary()

输出: enter image description here

然后我尝试添加 LoRA 层,如下所示:

import math

class LoraLayer(tf.keras.Layer):
  def __init__(self, original_layer, rank=8, trainable=False, **kwargs):
    original_layer_config = original_layer.get_config()
    name = original_layer_config["name"]
    kwargs.pop('name', None)

    super().__init__(name=name, trainable=trainable, **kwargs)

    self.original_layer = original_layer
    self.original_layer.trainable = False

    self.A = tf.keras.layers.Dense(units=rank, use_bias=False, kernel_initializer=tf.keras.initializers.VarianceScaling(scale=math.sqrt(5), mode="fan_in", distribution="uniform"), trainable=trainable, name="lora_A")
    self.B = tf.keras.layers.Dense(units=original_layer.output.shape[-1], kernel_initializer="zeros", trainable=trainable, name="lora_B")

  def call(self, inputs):
    original_outputs = self.original_layer(inputs)
    lora_outputs = self.B(self.A(inputs))
    return original_outputs + lora_outputs

lora_model._tracker.unlock()
lora_model.layers[-2] = LoraLayer(lora_model.layers[-2], rank=8, trainable=False)
lora_model._tracker.lock()
lora_model.summary()

我使用这段代码的目的是用 LoRA 本身替换倒数第二层。然而,根据模型的摘要,这种情况并没有发生: enter image description here

最后一层仍然是密集层,可训练参数的数量完全没有变化。

我的实施过程中是否做错了什么?也许它与这个问题中解释的内容有关,并且在 Keras 中基本上不可能做到这一点,或者我是否缺少一些中间步骤来使其工作?

最后,我也尝试过这个解决方案,但代码对我不起作用(它失败说 Node 对象没有属性

outbound_layer

如有任何帮助,我们将不胜感激🙏

python tensorflow keras
1个回答
0
投票

我不确定这是否可行,但一个简单的解决方案可能是简单地循环原始模型的各层:

new_model = keras.Sequantial()
for i, layer in enumerate(lora_model.layers):
    if i == len(lora_model.layers) - 2:
        new_model.add(LoraLayer(...))
    else:
        new_model.add(layer)
© www.soinside.com 2019 - 2024. All rights reserved.