在numpy中,我们可以这样做:
x = np.random.random((10,10))
a = np.random.randint(0,10,5)
b = np.random.randint(0,10,5)
x[a,b] # gives 5 entries from x, indexed according to the corresponding entries in a and b
当我在TensorFlow中尝试相同的东西时:
xt = tf.constant(x)
at = tf.constant(a)
bt = tf.constant(b)
xt[at,bt]
最后一行给出“Bad slice index tensor”异常。似乎TensorFlow不支持像numpy或Theano那样的索引。
是否有人知道是否有TensorFlow方法(按任意值索引张量)。我已经看过tf.nn.embedding部分了,但我不确定它们是否可以用于此,即使它们可以,也是一个很简单的解决方法。
(现在,我正在将来自x
的数据作为输入并在numpy中进行索引,但我希望将x
置于TensorFlow中以获得更高的效率)
答案 0 :(得分:10)
LDGN的评论是正确的。目前这是不可能的,并且是请求的功能。如果您关注issue#206 on github,则会在/当有可用时更新。很多人都喜欢这个功能。
答案 1 :(得分:10)
您现在可以使用tf.gather_nd
实现这一目的。我们假设您有一个矩阵m
,如下所示:
| 1 2 3 4 |
| 5 6 7 8 |
你想构建一个大小为r
的矩阵,比如3x2,由m
的元素构建,如下所示:
| 3 6 |
| 2 7 |
| 5 3 |
| 1 1 |
r
的每个元素都对应m
的行和列,您可以使用这些索引的矩阵rows
和cols
(从零开始,因为我们是编程,而不是数学!):
| 0 1 | | 2 1 |
rows = | 0 1 | cols = | 1 2 |
| 1 0 | | 0 2 |
| 0 0 | | 0 0 |
你可以像这样堆叠成三维张量:
| | 0 2 | | 1 1 | |
| | 0 1 | | 1 2 | |
| | 1 0 | | 2 0 | |
| | 0 0 | | 0 0 | |
这样,您可以从m
到r
到rows
和cols
,如下所示:
import numpy as np
import tensorflow as tf
m = np.array([[1, 2, 3, 4], [5, 6, 7, 8]])
rows = np.array([[0, 1], [0, 1], [1, 0], [0, 0]])
cols = np.array([[2, 1], [1, 2], [0, 2], [0, 0]])
x = tf.placeholder('float32', (None, None))
idx1 = tf.placeholder('int32', (None, None))
idx2 = tf.placeholder('int32', (None, None))
result = tf.gather_nd(x, tf.stack((idx1, idx2), -1))
with tf.Session() as sess:
r = sess.run(result, feed_dict={
x: m,
idx1: rows,
idx2: cols,
})
print(r)
输出:
[[ 3. 6.]
[ 2. 7.]
[ 5. 3.]
[ 1. 1.]]
答案 2 :(得分:2)
对于Tensorflow 0.11
,已实施基本索引。更高级的索引(如布尔索引)仍然缺失,但显然计划用于未来的版本。