Python Tensorflow:tf.argmax和切片

Python Tensorflow:tf.argmax和切片,python,tensorflow,slice,argmax,Python,Tensorflow,Slice,Argmax,我想设计这个损失函数: sum((y[argmax(y_)] - y_[argmax(y_)])²) 我找不到一种方法来做y[argmax(y)]。我试过y[k],y[:,k]和y[None,k]这些都不管用。这是我的代码: Na = 3 x = tf.placeholder(tf.float32, [None, 2]) W = tf.Variable(tf.zeros([2, Na])) b = tf.Variable(tf.zeros([Na]))

我想设计这个损失函数:

sum((y[argmax(y_)] - y_[argmax(y_)])²)
我找不到一种方法来做
y[argmax(y)]
。我试过
y[k]
y[:,k]
y[None,k]
这些都不管用。这是我的代码:

    Na = 3
    x = tf.placeholder(tf.float32, [None, 2])
    W = tf.Variable(tf.zeros([2, Na]))
    b = tf.Variable(tf.zeros([Na]))
    y = tf.nn.relu(tf.matmul(x, W) + b)
    y_ = tf.placeholder(tf.float32, [None, 3])
    k = tf.argmax(y_, 1)
    diff = y[k] - y_[k]
    loss = tf.reduce_sum(tf.square(diff))
错误是:

  File "/home/ncarrara/phd/code/cython/robotnavigation/ftq/cftq19.py", line 156, in <module>
    diff = y[k] - y_[k]
  File "/home/ncarrara/miniconda3/lib/python2.7/site-packages/tensorflow/python/ops/array_ops.py", line 499, in _SliceHelper
    name=name)
  File "/home/ncarrara/miniconda3/lib/python2.7/site-packages/tensorflow/python/ops/array_ops.py", line 663, in strided_slice
    shrink_axis_mask=shrink_axis_mask)
  File "/home/ncarrara/miniconda3/lib/python2.7/site-packages/tensorflow/python/ops/gen_array_ops.py", line 3515, in strided_slice
    shrink_axis_mask=shrink_axis_mask, name=name)
  File "/home/ncarrara/miniconda3/lib/python2.7/site-packages/tensorflow/python/framework/op_def_library.py", line 767, in apply_op
    op_def=op_def)
  File "/home/ncarrara/miniconda3/lib/python2.7/site-packages/tensorflow/python/framework/ops.py", line 2508, in create_op
    set_shapes_for_outputs(ret)
  File "/home/ncarrara/miniconda3/lib/python2.7/site-packages/tensorflow/python/framework/ops.py", line 1873, in set_shapes_for_outputs
    shapes = shape_func(op)
  File "/home/ncarrara/miniconda3/lib/python2.7/site-packages/tensorflow/python/framework/ops.py", line 1823, in call_with_requiring
    return call_cpp_shape_fn(op, require_shape_fn=True)
  File "/home/ncarrara/miniconda3/lib/python2.7/site-packages/tensorflow/python/framework/common_shapes.py", line 610, in call_cpp_shape_fn
    debug_python_shape_fn, require_shape_fn)
  File "/home/ncarrara/miniconda3/lib/python2.7/site-packages/tensorflow/python/framework/common_shapes.py", line 676, in _call_cpp_shape_fn_impl
    raise ValueError(err.message)
ValueError: Shape must be rank 1 but is rank 2 for 'strided_slice' (op: 'StridedSlice') with input shapes: [?,3], [1,?], [1,?], [1].
文件“/home/ncarrara/phd/code/cython/robotnavigation/ftq/cftq19.py”,第156行,在
diff=y[k]-y_k[k]
文件“/home/ncarrara/miniconda3/lib/python2.7/site packages/tensorflow/python/ops/array_ops.py”,第499行,在
名称=名称)
文件“/home/ncarrara/miniconda3/lib/python2.7/site packages/tensorflow/python/ops/array_ops.py”,第663行,跨步切片
收缩轴遮罩=收缩轴遮罩)
文件“/home/ncarrara/miniconda3/lib/python2.7/site packages/tensorflow/python/ops/gen_array_ops.py”,第3515行,跨步切片
收缩轴遮罩=收缩轴遮罩,名称=名称)
文件“/home/ncarrara/miniconda3/lib/python2.7/site packages/tensorflow/python/framework/op_def_library.py”,第767行,在apply_op
op_def=op_def)
文件“/home/ncarrara/miniconda3/lib/python2.7/site packages/tensorflow/python/framework/ops.py”,第2508行,在create_op中
为输出设置形状(ret)
文件“/home/ncarrara/miniconda3/lib/python2.7/site packages/tensorflow/python/framework/ops.py”,第1873行,在集合形状中,用于输出
形状=形状函数(op)
文件“/home/ncarrara/miniconda3/lib/python2.7/site packages/tensorflow/python/framework/ops.py”,第1823行,与
回传呼叫\u cpp\u shape\u fn(op,require\u shape\u fn=True)
文件“/home/ncarrara/miniconda3/lib/python2.7/site packages/tensorflow/python/framework/common_shapes.py”,第610行,在call_cpp_shape_fn中
调试\u python\u形状\u fn,需要\u形状\u fn)
文件“/home/ncarrara/miniconda3/lib/python2.7/site packages/tensorflow/python/framework/common_shapes.py”,第676行,在“调用”cpp_shape_fn_impl中
提升值错误(错误消息)
ValueError:形状必须为秩1,但对于输入形状为[?,3],[1],[1],[1],[1],[1]的“跨步切片”(op:“跨步切片”),形状必须为秩2。
可通过以下方式完成:

说明:

在这种情况下,
tf.gather nd
的思想是生成一个矩阵(一个二维张量),其中每一行包含输出中要包含的行和列的索引。例如,如果我有一个矩阵
a
包含:

| 1 2 3 |
| 4 5 6 |
| 7 8 9 |
| 1 2 |
| 0 1 |
| 2 2 |
| 1 0 |
| 6 |
| 2 |
| 9 |
| 4 |
以及矩阵
i
,包含:

| 1 2 3 |
| 4 5 6 |
| 7 8 9 |
| 1 2 |
| 0 1 |
| 2 2 |
| 1 0 |
| 6 |
| 2 |
| 9 |
| 4 |
然后,
tf.gather\n nd(a,i)
的结果将是包含以下内容的向量(一维张量):

| 1 2 3 |
| 4 5 6 |
| 7 8 9 |
| 1 2 |
| 0 1 |
| 2 2 |
| 1 0 |
| 6 |
| 2 |
| 9 |
| 4 |
在这种情况下,列索引由
k
中的
tf.argmax
给出;它告诉您,对于每一行,哪一列的值最高。现在,您只需要将行索引与其中的每一个放在一起。
k
中的第一个元素是第0行最大值列的索引,下一个元素是第1行的索引,依此类推
num\u examples
只是
x
tf中的行数。range(num\u examples)
为您提供一个从0到
x
中的行数减去1(即所有行索引序列)的向量。现在您只需要将其与
k
结合起来,这就是
tf.stack
所做的,结果
idx
tf.gather\n的参数,可以使用以下方法完成:

说明:

在这种情况下,
tf.gather nd
的思想是生成一个矩阵(一个二维张量),其中每一行包含输出中要包含的行和列的索引。例如,如果我有一个矩阵
a
包含:

| 1 2 3 |
| 4 5 6 |
| 7 8 9 |
| 1 2 |
| 0 1 |
| 2 2 |
| 1 0 |
| 6 |
| 2 |
| 9 |
| 4 |
以及矩阵
i
,包含:

| 1 2 3 |
| 4 5 6 |
| 7 8 9 |
| 1 2 |
| 0 1 |
| 2 2 |
| 1 0 |
| 6 |
| 2 |
| 9 |
| 4 |
然后,
tf.gather\n nd(a,i)
的结果将是包含以下内容的向量(一维张量):

| 1 2 3 |
| 4 5 6 |
| 7 8 9 |
| 1 2 |
| 0 1 |
| 2 2 |
| 1 0 |
| 6 |
| 2 |
| 9 |
| 4 |

在这种情况下,列索引由
k
中的
tf.argmax
给出;它告诉您,对于每一行,哪一列的值最高。现在,您只需要将行索引与其中的每一个放在一起。
k
中的第一个元素是第0行最大值列的索引,下一个元素是第1行的索引,依此类推
num\u examples
只是
x
tf中的行数。range(num\u examples)
为您提供一个从0到
x
中的行数减去1(即所有行索引序列)的向量。现在你只需要把它和
k
放在一起,这就是
tf.stack
所做的,结果
idx
tf.gather\u nd

看起来不错,但现在我还不能确定你的答案是否正确,谢谢你@Nicolascararra我添加了一些解释。看起来不错,但现在我不确定是否能验证你的答案,谢谢你@尼古拉斯·卡拉拉:我补充了一些解释。