如何以自定义定义的指标获取会话?

时间:2018-09-07 08:08:35

标签: python tensorflow keras metrics

我正在尝试在Keras中运行自定义定义的指标。我成功做到了这一点,但是我不相信它的结果,所以我想检查一些价值。麻烦的是,一切都在张量中,我想将它们转换为ndarray以便对其进行检查。要转换它们,我必须召开会议来评估它们。当我尝试使用Keras后端进行会话时,出现错误:

  

InvalidArgumentError(请参阅上面的回溯):您必须使用dtype float和shape [?,?]为占位符张量'Dense_1_target_1'提供一个值。        [[[Node:Dense_1_target_1 = Placeholderdtype = DT_FLOAT,shape = [?,?],_device =“ / job:localhost / replica:0 / task:0 / device:GPU:0”]]

我唯一想要的就是能够打印一些关于张量的信息:值,形状等。

from keras import backend as K

def t_zeros(Y_true, y_pred):
""" Just count # zero's in Y_true and try to print some info """
    threshold = 0.5
    true_zeros = K.less(Y_true, threshold) # element-wise True where Y_true < theshold
    true_zeros = K.cast(true_zeros, K.floatx())  # cast to 0.0 / 1.0
    n_zeros = K.sum(true_zeros)

    sess = K.get_session()
    y_t = Y_true.eval(session=sess) # <== error happens here
    print(y_t.shape)

    return n_zeros

2 个答案:

答案 0 :(得分:1)

请记住,tensorflow使用延迟评估。

因此,您无法print使用函数中的值。您需要创建一个打印节点并将其连接到整个图形中。

类似这样的东西

def t_zeros(Y_true, y_pred):
""" Just count # zero's in Y_true and try to print some info """
    threshold = 0.5
    true_zeros = K.less(Y_true, threshold) # element-wise True where Y_true < theshold
    true_zeros = K.cast(true_zeros, K.floatx())  # cast to 0.0 / 1.0
    n_zeros = K.sum(true_zeros)

    return tf.Print(n_zeros, [n_zeros]) 

... 
my_metric = t_zeros(Y_true, y_pred)  # Returns the tensor, but we need to make sure it's evaluated
...
train_op = tf.group(train_op, my_metric) 

如果需要,您可以将其连接到其他操作,只需确保对其进行评估即可。

答案 1 :(得分:0)

如果您不介意使用Tensorflow,则可以使用tf.py_func或更现代的版本tf.py_function通过传递您拥有的任何张量来调用python函数,而无需会话。 (Tensorflow Documentation)。

您传递给函数的张量应该转换为numpy数据/数组。 py_funcpy_function之间的唯一区别在于,使用py_func时,张量会自动变成numpy数组,而使用py_function时,它仍然是张量,而您必须手动调用.numpy()

Tensorflow将为您添加此调用到图形执行中。

from keras import backend as K
import tensorflow as tf

def t_zeros(Y_true, y_pred):
""" Just count # zero's in Y_true and try to print some info """
    threshold = 0.5
    true_zeros = K.less(Y_true, threshold) # element-wise True where Y_true < theshold
    true_zeros = K.cast(true_zeros, K.floatx())  # cast to 0.0 / 1.0
    n_zeros = K.sum(true_zeros)

    result = tf.py_function(some_function, [Y_true], [tf.float64, tf.int32]) # where the last argument
    # is an array representing the return type(s) of `some_function()`.
    # If `some_function` returns nothing, then you can do
    # tf.py_function(some_function, [Y_true], [])

    return n_zeros

def some_function(input):
    '''
    If you called this through py_func, the inputs are already numpy arrays,
    if you called through py_function, they're Tensors and you have to call
    input.numpy().
    '''
    input = input.numpy()
    print(input)