I'm trying to define a custom gradient in TensorFlow for a function that returns a non-scalar.
A simplified toy version of the problem is:
import tensorflow as tf
@tf.custom_gradient
def f(x):
y = tf.Variable([x[1], 2.0*x[0]])
def grad(upstream):
dg = tf.Variable([[0.0, 2.0], [1.0, 0.0]])
return dg * upstream # ? no idea here
return y, grad
x = tf.Variable([1.0, 2.0])
with tf.GradientTape() as tape:
y = f(x)
tape.jacobian(y, x)
# tape.gradient(y,x)
I do not understand what shape the grad function needs to return. In the above example, tape.gradient gives the full jacobian of the problem (which I would expect from tape.jacobian)and tape.jacobian gives nothing (though I had been getting error messages before restarting my kernel).
Is this the expected shape and behaviour? What shape should the custom gradient return for a vector-valued or matrix-valued function's derivative?