我在使用 TensorFlow 中的自动微分计算梯度时遇到问题。基本上我想创建一个只有一个输出值 f 并获得两个值 (x,t) 的输入的神经网络。网络应该像一个数学函数一样工作,所以在这种情况下 f(x,t) 其中 x 和 t 是输入变量,我想计算偏导数,例如df_dx, d2f/dx2
or df_dt
。我稍后需要这些偏导数来获得特定的损失函数。这是我的简化代码:
import numpy as np
import tensorflow as tf
from tensorflow.keras.layers import Dense, Flatten
from tensorflow.keras import Model
class MyModel(Model):
def __init__(self):
super(MyModel, self).__init__()
self.flatten = Flatten(input_shape=(2, 1))
self.d1 = Dense(28)
self.f = Dense(1)
def call(self, y):
y = self.flatten(y)
y = self.d1(y)
y = self.f(y)
return y
if __name__ == "__main__":
#inp contains the input-variables (x,t)
inp = np.random.rand(1,2,1)
inp_tf = tf.convert_to_tensor(inp, np.float32)
#Create a Model
model = MyModel()
#Here comes the important part:
x = inp_tf[0][0]
t = inp_tf[0][1]
with tf.GradientTape(persistent=True) as tape:
tape.watch(inp_tf[0][0])
tape.watch(inp_tf)
f = model(inp_tf)
df_dx = tape.gradient(f, inp_tf[0][0]) #Derivative df_dx
grad_f = tape.gradient(f, inp_tf)
tf.print(f) #--> [[-0.0968768075]]
tf.print(df_dx) #--> None
tf.print(grad_f) #--> [[[0.284864038]
# [-0.243642956]]]
我期望的是我得到df_dx = [0.284864038]
(grad_f 的第一个组件),但它导致None
. 我的问题是:
- 是否可以将 f 的偏导数仅计算为一个输入变量?
- 如果是:我必须在我的代码中更改计算 df_dx 不会产生的内容
None
?
我认为可以做的是修改class MyModel
我使用两个不同 Inputlayer(一个用于 x,一个用于 t)的架构,以便我可以调用模型,f = model(x,t)
但这对我来说似乎不自然,我认为应该有一个更简单的方法.
另一点是,例如,当我将 Flattenlayer 的 input_shape 更改为self.flatten = Flatten(input_shape=(5,1)
但我的 inputvector 具有 shape(1,2,1) 时,我没有得到错误,所以我希望得到一个错误,但事实并非如此,为什么?我很感谢你的帮助:)
我使用以下配置:
- 使用 Python 扩展作为 IDE 的 Visual Studio Code
- Python 版本:3.7.6
- TensorFlow 版本:2.1.0
- Keras 版本:2.2.4-tf