改变内核权重的包装层
Wrapper layer to change kernel weights
我正在尝试编写一个自定义包装层,例如以下(已简化),我想在其中修改包装层的内核权重:
import tensorflow as tf
class MyWrapper(tf.keras.layers.Wrapper):
def __init__(self, layer: tf.keras.layers, **kwargs):
super().__init__(layer, **kwargs)
def call(self, inputs, **kwargs):
self.layer.kernel = self.layer.kernel + 1
outputs = self.layer(inputs)
return outputs
def main():
# setup model
input_shape = (8, 8, 1)
xin = tf.keras.layers.Input(shape=input_shape)
xout = MyWrapper(tf.keras.layers.Conv2D(4, (3, 3), padding="same"))(xin)
model = tf.keras.models.Model(inputs=xin, outputs=xout)
model.compile()
# run with output
x_shape = (1, *input_shape)
x = tf.random.uniform(x_shape, dtype=tf.float32)
xout = model(x)
print(xout)
if __name__ == "__main__":
main()
但是,代码在调用函数的第一行中断,输出如下:
TypeError: An op outside of the function building code is being passed
a "Graph" tensor. It is possible to have Graph tensors
leak out of the function building context by including a
tf.init_scope in your function building code.
For example, the following function will fail:
@tf.function
def has_init_scope():
my_constant = tf.constant(1.)
with tf.init_scope():
added = my_constant * 2
The graph tensor has name: my_wrapper/add:0
我已经检查过 https://www.tensorflow.org/addons/api_docs/python/tfa/layers/WeightNormalization 但不确定是否有帮助。虽然他们似乎也重新定义了内核,但他们是基于单独的变量而不是内核本身(以我的理解)重新定义它。任何帮助将不胜感激!
一层的内核是tf.Variable
。要更改其值,请使用 assign
方法。
def call(self, inputs, **kwargs):
self.layer.kernel.assign(self.layer.kernel + 1)
outputs = self.layer(inputs)
return outputs
用 Tensor 覆盖 tf.Variable
是一个常见的错误。您可以在指南中阅读有关 Variables
的更多信息:Introduction to Variables.
A Variable
甚至有一些方便的方法,如assign_add
,可以将上面的代码缩短为 self.layer.kernel.assign_add(tf.ones_like(self.layer.kernel))
我正在尝试编写一个自定义包装层,例如以下(已简化),我想在其中修改包装层的内核权重:
import tensorflow as tf
class MyWrapper(tf.keras.layers.Wrapper):
def __init__(self, layer: tf.keras.layers, **kwargs):
super().__init__(layer, **kwargs)
def call(self, inputs, **kwargs):
self.layer.kernel = self.layer.kernel + 1
outputs = self.layer(inputs)
return outputs
def main():
# setup model
input_shape = (8, 8, 1)
xin = tf.keras.layers.Input(shape=input_shape)
xout = MyWrapper(tf.keras.layers.Conv2D(4, (3, 3), padding="same"))(xin)
model = tf.keras.models.Model(inputs=xin, outputs=xout)
model.compile()
# run with output
x_shape = (1, *input_shape)
x = tf.random.uniform(x_shape, dtype=tf.float32)
xout = model(x)
print(xout)
if __name__ == "__main__":
main()
但是,代码在调用函数的第一行中断,输出如下:
TypeError: An op outside of the function building code is being passed
a "Graph" tensor. It is possible to have Graph tensors
leak out of the function building context by including a
tf.init_scope in your function building code.
For example, the following function will fail:
@tf.function
def has_init_scope():
my_constant = tf.constant(1.)
with tf.init_scope():
added = my_constant * 2
The graph tensor has name: my_wrapper/add:0
我已经检查过 https://www.tensorflow.org/addons/api_docs/python/tfa/layers/WeightNormalization 但不确定是否有帮助。虽然他们似乎也重新定义了内核,但他们是基于单独的变量而不是内核本身(以我的理解)重新定义它。任何帮助将不胜感激!
一层的内核是tf.Variable
。要更改其值,请使用 assign
方法。
def call(self, inputs, **kwargs):
self.layer.kernel.assign(self.layer.kernel + 1)
outputs = self.layer(inputs)
return outputs
用 Tensor 覆盖 tf.Variable
是一个常见的错误。您可以在指南中阅读有关 Variables
的更多信息:Introduction to Variables.
A Variable
甚至有一些方便的方法,如assign_add
,可以将上面的代码缩短为 self.layer.kernel.assign_add(tf.ones_like(self.layer.kernel))