0

In this loss function, I need to create full metrics depends on the number of images in batch and size of the image. However, I can get the image size from y_pred but no the batch size because it is coming as None while initializing the graph.

def focal_loss(content, label_remap, gamma_=2, w_d=1e-4):
def focal_loss_fixed(y_true, y_pred):
    num_classes = len(content.keys())
    print("y_true_b", y_true.get_shape().as_list())

    cv_eqation = K.constant([0.114, 0.587, 0.299])
    y_true = tf.multiply(y_true, cv_eqation)
    y_true = tf.reduce_sum(y_true, axis=3)
    y_true = tf.cast(y_true, dtype=tf.uint8)

    lbls_resized = y_true
    logits_train = y_pred

    b, c, w, h = K.int_shape(y_pred)
    batch = K.constant(b)
    channel = K.variable(c)
    width = K.variable(w)
    high = K.variable(h)
    with tf.variable_scope("loss"):
        ......
        # make the labels one-hot for the cross-entropy
        onehot_mat = tf.reshape(tf.one_hot(lbls_resized, num_classes), (-1, num_classes))

        # focal loss p and gamma
        gamma = np.full((high * width * batch, channel), fill_value=gamma_)
        print("gamma", gamma.shape)
        .........
    return loss
return focal_loss_fixed

Also, I tried a different way by using onehot_mat shape but it has none value in its shape.

Zaher88abd
  • 448
  • 7
  • 20

1 Answers1

0

Please refere to this answer. It sounds like you want to know the dynamic shape of the tensor but are using the static shape instead. You need to use tf.shape to get the dynamic shape of your batch during runtime instead of get_shape which only returns the static shape that is known while constructing the network.

Update: For your particular tasks it looks to me like you are trying to create a tensor that has a shape dependend on the current batch size. I think you could do something like this:

import tensorflow as tf
import numpy as np

vector = tf.Variable(tf.random_normal([3], stddev=0.1), name="weights")
batch = tf.placeholder(tf.float32, shape=[None,2,2])

vector_times_batchsize = tf.tile(vector, tf.shape(batch)[0:1])

init_all_op = tf.global_variables_initializer()
with tf.Session() as sess:
    sess.run(init_all_op)
    print sess.run(vector_times_batchsize, feed_dict={batch: np.zeros((5,2,2), np.float32)}).shape

This creates a new tensor by repeating the gamma_image tensor depending on the shape of the first dimension of the tensor batch.

Please be aware that you can't use numpy functions since the creation of this tensor needs to be part of the tensorflow graph because the sice is only known during run time but not while the graph is created.

sietschie
  • 7,425
  • 3
  • 33
  • 54
  • Thank you @Sietschie for the answer, tried to use ```tf.shape``` but it didn't work, and I got this exception ```TypeError: Tensor objects are not iterable when eager execution is not enabled. To iterate over this tensor use tf.map_fn.```, Which logically right I am not in eager mode so I can't get the shape of the y_true of y_pred in Keras I will but the value of batch in a fit method. However, I am not sure, but it should be a way to use that value in the equation. – Zaher88abd Oct 26 '18 at 13:12