TensorFlow 重复功能因 ValueError 失败:不支持无值

Alb*_*rto 3 repeat keras tensorflow

我已经实现了以下自定义Layerseed_vectors根据x使用函数的输入大小,在调用时修改可学习参数的大小repeat

import tensorflow as tf
from tensorflow.keras.layers import Dense
from tensorflow import repeat
from tensorflow.keras.layers import LayerNormalization


class PoolingMultiHeadAttention(tf.keras.layers.Layer):

    def __init__(self, d, k, h):
        """
        Arguments:
            d: an integer, input dimension.
            k: an integer, number of seed vectors.
            h: an integer, number of heads.
        """
        super(PoolingMultiHeadAttention, self).__init__()
        self.seed_vectors = self.add_weight(initializer='uniform',
                                            shape=(1, k, d),
                                            trainable=True)

    def call(self, z):
        """
        Arguments:
            z: a float tensor with shape [b, n, d].
        Returns:
            a float tensor with shape [b, k, d]
        """
        b = z.shape[0]
        s = self.seed_vectors
        s = repeat(s, (b), axis=0, name='rep')  # shape [b, k, d]
        return s*z


# Dimensionality test    
z = tf.random.normal(shape=(10, 2, 9))
pma = PoolingMultiHeadAttention(d=9, k=2, h=3)
pma(z)
Run Code Online (Sandbox Code Playgroud)

我已经在单元测试中测试了维度输入/输出,它工作正常,但不幸的是,如果我在模型中使用这个层,它会失败并出现错误:


    <ipython-input-4-89023d123369>:110 call  *
        s = repeat(s, (b), axis=0, name='rep')  # shape [b, k, d]
    /usr/local/lib/python3.6/dist-packages/tensorflow/python/ops/array_ops.py:5616 repeat  **
        return repeat_with_axis(input, repeats, axis, name)
    /usr/local/lib/python3.6/dist-packages/tensorflow/python/ops/array_ops.py:5478 repeat_with_axis
        repeats = convert_to_int_tensor(repeats, name="repeats")
    /usr/local/lib/python3.6/dist-packages/tensorflow/python/ops/array_ops.py:5388 convert_to_int_tensor
        tensor = ops.convert_to_tensor(tensor, name=name, preferred_dtype=dtype)
    /usr/local/lib/python3.6/dist-packages/tensorflow/python/framework/ops.py:1341 convert_to_tensor
        ret = conversion_func(value, dtype=dtype, name=name, as_ref=as_ref)
    /usr/local/lib/python3.6/dist-packages/tensorflow/python/framework/constant_op.py:317 _constant_tensor_conversion_function
        return constant(v, dtype=dtype, name=name)
    /usr/local/lib/python3.6/dist-packages/tensorflow/python/framework/constant_op.py:258 constant
        allow_broadcast=True)
    /usr/local/lib/python3.6/dist-packages/tensorflow/python/framework/constant_op.py:296 _constant_impl
        allow_broadcast=allow_broadcast))
    /usr/local/lib/python3.6/dist-packages/tensorflow/python/framework/tensor_util.py:439 make_tensor_proto
        raise ValueError("None values not supported.")

    ValueError: None values not supported.
Run Code Online (Sandbox Code Playgroud)

此错误似乎与缺少输出(或输出为无)有关 [我知道情况并非如此,因为我已经在热切模式下测试了该功能并且它有效] 或由于某种原因反向传播不适用于此操作 ( repeat). 我不知道在运行时修改该参数大小的任何替代方法+(几乎)相同的代码使用 Pytorch 可以正常工作(https://github.com/TropComplique/set-transformer/blob/master/blocks.py) 谢谢

xdu*_*ch0 5

修复应该很简单:b = tf.shape(z)[0]改为使用。解释:

问题是您正在尝试重复b时间,这(我想)是可变的批量大小。当不以 Eager 模式运行时,这由None形状中的值表示。因此,您试图重复“无次”,这导致崩溃。

重要的是Tensor.shape返回张量的静态形状,即在编译时已知的任何形状。这包括None如上所述的未知尺寸。
tf.shape(tensor)而是返回动态形状,即只有在模型运行时才会对其进行评估。此时,批量大小当然是已知的(因为您将某些内容放入模型中),因此这将成为可以放入 的具体值,repeat而不是None我们上面得到的值。