keras 레이어에 자연스러운 그라디언트를 구현하고 싶습니다. 이것은 이미 제자리에있는 사용자 정의 된 그라디언트 내에서 발생해야합니다. 옵티 마이저를 호출 할 때 계산해야 할 구현 (일반 또는 자연 그라디언트)을 선택할 수 있기를 원합니다.
내가 직면 한 문제는 내가 nat_grad=True
(그래프 빌드 시간이 아닌) 훈련 시간에 부울 을 Op에 전달할 때 AutoGraph가 행복하지 않다는 것입니다.
현재 무슨 일이 일어나고 있는지 의사 코드는 다음과 같습니다.
@tf.custom_gradient
def MyOp(inputs, w, nat_grad=False):
output = w*inputs
def grad(dy):
if nat_grad:
return dy, 1.0
else:
return -dy, -1.0
return output, grad
class MyKerasLayer(tf.keras.layers.Layer):
def __init__(self):
super().__init__()
self.nat_grad = False
def build(self, input_shape):
self.w = self.add_weight("w", dtype=tf.float32, trainable=True, initializer=tf.random_normal_initializer)
super().build(input_shape)
def call(self, inputs):
return MyOp(inputs, self.w, self.nat_grad)
class MyModel(tf.keras.Sequential):
def __init__(self, num_layers):
super().__init__([tf.keras.Input(shape=[1], batch_size=None, dtype=tf.float32)]+[MyKerasLayer() for _ in range(num_layers)])
def optimize(model, X, Y, nat_grad:bool):
for layer in model.layers:
layer.nat_grad = nat_grad
model.fit(x=X, y=Y)
model = MyModel(5)
model.compile(optimizer='SGD', loss=lambda x,y:x-y, metrics=[])
X = np.array([1.0, 2.0, 3.0])
Y = np.array([1.0, 2.0, 3.0])
optimize(model, X, Y, nat_grad=True)
>>> OperatorNotAllowedInGraphError: using a `tf.Tensor` as a Python `bool` is not allowed: AutoGraph did convert this function. This might indicate you are trying to use an unsupported feature.
이를 수행하는 올바른 방법은 무엇입니까?
Tensorflow 2.x를 사용하면 함수를 tf.graphs [1]로 실행할 수 있습니다. 장식 그래서 grad(dy)
함께하는 @tf.function
작동해야하지만 이후 새로운 오류로 실행하겠습니다 MyOp
소요 nat_grad
입력으로이 변수 [2]에 대한 기울기를 기대합니다.
@tf.custom_gradient
def MyOp(inputs, w, nat_grad=False):
output = w*inputs
@tf.function
def grad(dy):
if nat_grad:
return dy, 1.0, 0.
else:
return -dy, -1.0, 0.
return output, grad
이것은 이것을 수행하는 방법이 아니며 오히려 그라디언트 op를 2 부분으로 나누고 call
.
@tf.custom_gradient
def NatOp(inputs, w):
output = w*inputs
def grad(dy):
return dy, 1.0
return output, grad
@tf.custom_gradient
def RegOp(inputs, w):
output = w*inputs
def grad(dy):
return -dy, -1.0
return output, grad
class MyKerasLayer(tf.keras.layers.Layer):
def __init__(self):
super().__init__()
self.nat_grad = False
def build(self, input_shape):
self.w = self.add_weight("w", dtype=tf.float32, trainable=True, initializer=tf.random_normal_initializer)
super().build(input_shape)
def call(self, inputs):
return NatOp(inputs, self.w) if self.nat_grad else RegOp(inputs, self.w)
[1] https://www.tensorflow.org/api_docs/python/tf/function
[2] https://www.tensorflow.org/api_docs/python/tf/custom_gradient
이 기사는 인터넷에서 수집됩니다. 재 인쇄 할 때 출처를 알려주십시오.
침해가 발생한 경우 연락 주시기 바랍니다[email protected] 삭제
몇 마디 만하겠습니다