Tensorflow:链接tf.gather()会产生IndexedSlices警告

Art*_*lov 2 python neural-network tensorflow

我遇到了链接tf.gather()索引产生以下警告的问题:

/usr/local/lib/python3.5/dist-packages/tensorflow/python/ops/gradients.py:90: UserWarning: Converting sparse IndexedSlices to a dense Tensor of unknown shape. This may consume a large amount of memory.           
  "Converting sparse IndexedSlices to a dense Tensor of unknown shape. "
Run Code Online (Sandbox Code Playgroud)

当一个层索引到输入层,在相应的切片上执行某些操作,然后下一层索引到结果中时,就会出现这种情况.这是一个代表性的例子:

import tensorflow as tf

## 10-Dimensional data will be fed to the model
X = tf.placeholder( tf.float32, [10, None] )

## W works with the first 3 features of a sample
W = tf.Variable( tf.ones( [5, 3] ) )
Xi = tf.gather( X, [0,1,2] )
mm = tf.matmul( W, Xi )

## Indexing into the result produces a warning during backprop
h = tf.gather( mm, [0,1] )
...
train_step = tf.train.AdamOptimizer(1e-4).minimize( loss )
Run Code Online (Sandbox Code Playgroud)

train_step如果第二次tf.gather()呼叫被取消,则在定义时出现警告并消失.如果X提供明确数量的样本(例如,[10, 1000]),警告也会消失.

思考?

kev*_*man 7

梯度功能的的tf.gather操作返回IndexedSlices类型值.在你的程序中,输入第二个tf.gathertf.matmul(mm)的结果.因此,矩阵乘法的梯度函数被传递一个IndexedSlices值.

现在,想象一下梯度函数tf.matmul需要做什么.要计算梯度wrt W,它必须将输入的梯度与转置相乘Xi.在这种情况下,传入的渐变是一种IndexedSlices类型,并且Xi转置是一种密集张量(Tensor)类型.TensorFlow没有可以在IndexedSlices和上运行的矩阵乘法的实现Tensor.所以它只是在调用之前将其转换IndexedSlices为a .Tensortf.matmul

如果你在这里查看转换函数的代码,你会注意到当这种稀疏到密集的转换可能导致一个非常大的密集张量(_LARGE_SPARSE_NUM_ELEMENTS确定多大)或一个未知大小的密集张量时它打印出一个警告.当您使用形状塑造占位符X[10, None],此转换发生在IndexedSlices具有未知形状的情况下(实际上,只有一个维度未知,但仍无法静态确定结果形状),因此您会看到打印出的警告.一旦你设定的形状X[10, 1000],形状IndexedSlices变得完全指定的,所产生的密集张量的大小在阈值内,这样你就不会看到警告打印出来.

对于你的计算,如果你根本无法避免tf.gathera的结果tf.matmul,那么我会过多地担心这个警告,除非列的数量X非常大.