如何使用keras.backend.gradients()获得梯度值 [英] How to get gradient values using keras.backend.gradients()

查看:2694
本文介绍了如何使用keras.backend.gradients()获得梯度值的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试获取Keras模型的输出相对于模型的输入(x)(而不是权重)的导数.似乎最简单的方法是使用来自keras.backend的梯度",该梯度返回张量的张量( https://keras.io/backend/).我是tensorflow的新手,现在还不满意.我得到了梯度张量,并尝试为输入(x)的不同值获取其数值.但是,似乎渐变值与输入x(预期不是这样)无关,或者我做错了什么.任何帮助或评论将不胜感激.

I am trying to get derivative of output of a Keras model with respect to the input (x) of the model (not the weights). It seems like the easiest way is to use "gradients" from keras.backend which returns a tensor of gradients (https://keras.io/backend/). I am new with tensorflow and not comfortable with it yet. I have got the gradient tensor, and trying to get numerical values for it for different values of input (x). But it seems like the gradient value is independent of the input x (which is not expected to be) or I am doing something wrong. Any help or comment will be appreciated.

import keras
import numpy as np
import matplotlib.pyplot as plt
from keras.layers import Dense, Dropout, Activation
from keras.models import Sequential
import keras.backend as K
import tensorflow as tf
%matplotlib inline

n = 100         # sample size
x = np.linspace(0,1,n)    #input
y = 4*(x-0.5)**2          #output
dy = 8*(x-0.5)       #derivative of output wrt the input
model = Sequential()
model.add(Dense(32, input_dim=1, activation='relu'))            # 1d input
model.add(Dense(32, activation='relu'))
model.add(Dense(1))                                             # 1d output

# Minimize mse
model.compile(loss='mse', optimizer='adam', metrics=["accuracy"])
model.fit(x, y, batch_size=10, epochs=1000, verbose=0)

gradients = K.gradients(model.output, model.input)              #Gradient of output wrt the input of the model (Tensor)
print(gradients)

#value of gradient for the first x_test
x_test_1 = np.array([[0.2]])
sess = tf.Session()
sess.run(tf.global_variables_initializer())
evaluated_gradients_1 = sess.run(gradients[0], feed_dict={model.input: 
x_test_1})
print(evaluated_gradients_1)

#value of gradient for the second x_test
x_test_2 = np.array([[0.6]])
evaluated_gradients_2 = sess.run(gradients[0], feed_dict={model.input: x_test_2})
print(evaluated_gradients_2)

我的代码的输出:

[<tf.Tensor 'gradients_1/dense_7/MatMul_grad/MatMul:0' shape=(?, 1) dtype=float32>]
[[-0.21614937]]
[[-0.21614937]]

evaluated_gradients_1和rated_gradients_2对于不同的运行是不同的,但始终相等!我希望它们在同一运行中会有所不同,因为它们用于输入(x)的不同值. 网络的输出似乎是正确的.这是网络输出的图:网络输出与真实值

evaluated_gradients_1 and evaluated_gradients_2 are different for different runs, but always equal! I expected them to be different for the same run, because they are for different values of input (x). Output of the network seems to be correct. Here's a plot of the network output: Output of the network vs. true value

推荐答案

答案是:

sess = tf.Session()
sess.run(tf.global_variables_initializer())

应替换为:

sess = K.get_session()

前者创建一个新的Tensorflow会话并初始化所有值,这就是为什么它提供随机值作为梯度函数的输出的原因.后者退出了在Keras内部使用的会话,该会话具有训练后的价值.

The former creates a new tensorflow session and initializes all the values, that's why it gives random values as the output of gradient function. The latter pulls out the session which was used inside the Keras, which has after training values.

这篇关于如何使用keras.backend.gradients()获得梯度值的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆