【问题标题】:Index variable range in numpynumpy中的索引变量范围
【发布时间】:2016-09-09 22:21:41
【问题描述】:

我有一个形状为 (2, 5) 的 numpy 零矩阵 A

A = [[ 0.,  0.,  0.,  0.,  0.],
    [ 0.,  0.,  0.,  0.,  0.]]

我有另一个数组seq,大小为2。这与A 的第一个轴相同。

seq = [2, 3]

我想创建另一个矩阵B,如下所示:

B = [[ 1.,  1.,  0.,  0.,  0.],
    [ 1.,  1.,  1.,  0.,  0.]]

B 是通过将Aith 行中的第一个seq[i] 元素更改为1 来构造的。

这是一个玩具示例。 Aseq 可以很大,因此需要效率。 如果有人知道如何在 tensorflow 中执行此操作,我将不胜感激。

【问题讨论】:

    标签: numpy tensorflow


    【解决方案1】:

    您可以在 TensorFlow 中执行此操作(以及在 NumPy 中使用一些类似的代码),如下所示:

    seq = [2, 3]
    
    b = tf.expand_dims(tf.range(5), 0)   # A 1 x 5 matrix.
    seq_matrix = tf.expand_dims(seq, 1)  # A 2 x 1 matrix.
    b_bool = tf.greater(seq_matrix, b)   # A 2 x 5 bool matrix.
    
    B = tf.to_int32(b_bool)              # A 2 x 5 int matrix.
    

    示例输出:

    In [7]: b = tf.expand_dims(tf.range(5), 0)
            [[0 1 2 3 4]]
    
    In [21]: b_bool = tf.greater(seq_matrix, b)
    In [22]: op = sess.run(b_bool)
    In [23]: print(op)
    [[ True  True False False False]
     [ True  True  True False False]]
    
    In [24]: bint = tf.to_int32(b_bool)
    In [25]: op = sess.run(bint)
    In [26]: print(op)
    [[1 1 0 0 0]
     [1 1 1 0 0]]
    

    【讨论】:

      【解决方案2】:

      这个@mrry's 解决方案,表达方式略有不同

      In [667]: [[2],[3]]>np.arange(5)
      Out[667]: 
      array([[ True,  True, False, False, False],
             [ True,  True,  True, False, False]], dtype=bool)
      In [668]: ([[2],[3]]>np.arange(5)).astype(int)
      Out[668]: 
      array([[1, 1, 0, 0, 0],
             [1, 1, 1, 0, 0]])
      

      这个想法是在“外部”广播意义上将 [2,3] 与 [0,1,2,3,4] 进行比较。结果是布尔值,可以轻松更改为 0/1 整数。

      另一种方法是使用cumsum(或另一个ufunc.accumulate函数):

      In [669]: A=np.zeros((2,5))
      In [670]: A[range(2),[2,3]]=1
      In [671]: A
      Out[671]: 
      array([[ 0.,  0.,  1.,  0.,  0.],
             [ 0.,  0.,  0.,  1.,  0.]])
      In [672]: A.cumsum(axis=1)
      Out[672]: 
      array([[ 0.,  0.,  1.,  1.,  1.],
             [ 0.,  0.,  0.,  1.,  1.]])
      In [673]: 1-A.cumsum(axis=1)
      Out[673]: 
      array([[ 1.,  1.,  0.,  0.,  0.],
             [ 1.,  1.,  1.,  0.,  0.]])
      

      或以1's开头的变体:

      In [681]: A=np.ones((2,5))
      In [682]: A[range(2),[2,3]]=0
      In [683]: A
      Out[683]: 
      array([[ 1.,  1.,  0.,  1.,  1.],
             [ 1.,  1.,  1.,  0.,  1.]])
      In [684]: np.minimum.accumulate(A,axis=1)
      Out[684]: 
      array([[ 1.,  1.,  0.,  0.,  0.],
             [ 1.,  1.,  1.,  0.,  0.]])
      

      【讨论】:

      • 这是使用 numpy 的绝佳解决方案。
      猜你喜欢
      • 2018-05-11
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-09-10
      • 1970-01-01
      • 2012-12-01
      • 2016-04-24
      • 1970-01-01
      相关资源
      最近更新 更多