简体   繁体   English

Python多维数组索引说明

[英]Python multidimensional array indexing explanation

Could someone please explain to me what is happening here? 有人可以告诉我这里发生了什么吗? I understand what is happening here: https://docs.scipy.org/doc/numpy-1.15.0/user/basics.indexing.html#index-arrays , but do not understand this piece of code. 我了解这里发生的事情: https : //docs.scipy.org/doc/numpy-1.15.0/user/basics.indexing.html#index-arrays ,但不了解这段代码。

import numpy as np
y = np.zeros((3,3))
y = y.astype(np.int16)
y[1,1] = 1
x = np.ones((3,3))
t = (1-y).astype(np.int16)
print(t)
print(x[t])
x[(1-y).astype(np.int16)] = 0
print(x)

output: 输出:

[[1 1 1]
 [1 0 1]
 [1 1 1]]

[[[1. 1. 1.]
  [1. 1. 1.]
  [1. 1. 1.]]

 [[1. 1. 1.]
  [1. 1. 1.]
  [1. 1. 1.]]

 [[1. 1. 1.]
  [1. 1. 1.]
  [1. 1. 1.]]]

[[0. 0. 0.]
 [0. 0. 0.]
 [1. 1. 1.]]
import numpy as np              # Line 01
y = np.zeros((3,3))             # Line 02
y = y.astype(np.int16)          # Line 03
y[1,1] = 1                      # Line 04
x = np.ones((3,3))              # Line 05
t = (1-y).astype(np.int16)      # Line 06
print(t)                        # Line 07
print(x[t])                     # Line 08
x[(1-y).astype(np.int16)] = 0   # Line 09
print(x)                        # Line 10

Line 02: 第02行:

Creates a two-dimensional 3 x 3 ndarray of zeros. 创建零的二维3 x 3 ndarray。 y is a name that is made to point to this ndarray. y是指向此ndarray的名称。

Line 03: 03行:

Sets the data-type of each element of y , to 16-bit integer. y的每个元素的数据类型设置为16位整数。

Line 04: 04行:

Sets the element of y at the intersection of the middle row and middle column, to 1 . 将中间行和中间列的交点处的y元素设置为1

Line 05: 05行:

Creates a two-dimensional 3 x 3 ndarray of ones. 创建一个二维的3 x 3 ndarray。 x is a name that is made to point to this ndarray. x是指向该ndarray的名称。

Line 06: 第06行:

The subtraction ( 1-t ) results in several scalar subtractions ( 1- elem ), where elem is each element of t . 减法( 1-t )导致多个标量减法( 1- elem ),其中elemt每个元素。 The result will be another ndarray, having the same shape as t , and having the result of the subtraction ( 1- elem ), as its values. 结果将是另一个ndarray,其形状与t相同,并且将减法的结果( 1- elem )作为其值。 That is, the values of the ndarray (1-t) will be: 也就是说,ndarray (1-t)将为:

[[1-t[0,0], 1-t[0,1], 1-t[0,2]],
 [1-t[1,0], 1-t[1,1], 1-t[1,2]],
 [1-t[2,0], 1-t[2,1], 1-t[2,2]]]

Since t is full of zeros, and a lone 1 at the intersection of the middle row and middle column, (1-t) will be a two-dimensional ndarray full of ones, with a lone 0 at the intersection of the middle row and middle column. 由于t充满零,并且在中间行和中间列的交点处有一个孤岛1 ,因此(1-t)将是一个由(1-t)的二维ndarray,在中间行和中间列的交点处有一个孤岛0 。中间列。

Line 07: 第07行:

Prints t 打印t

Line 08: 第08行:

Things get a little tricky from here. 从这里开始,事情变得有些棘手。 What is happening here is called "Combined Advanced and Basic Indexing" ( https://docs.scipy.org/doc/numpy-1.13.0/reference/arrays.indexing.html#combining-advanced-and-basic-indexing ). 这里发生的事情称为“高级和基本索引组合”( https://docs.scipy.org/doc/numpy-1.13.0/reference/arrays.indexing.html#combining-advanced-and-basic-indexing ) 。 Let's go through the specifics, step-by-step. 让我们逐步详细介绍。 First, notice that x , is a two-dimensional ndarray, taking another integer ndarray t as an index. 首先,请注意x是二维ndarray,以另一个整数ndarray t作为索引。 Since x needs two indices to be supplied, t will be taken to be the first of those two indices, and the second index will be implicitly assumed to be : . 由于x需要提供两个索引,因此t将被视为这两个索引中的第一个,而第二个索引将被隐式假定为: So, x[t] is first interpreted as x[t,:] . 因此, x[t]首先被解释为x[t,:] The presence of these two indices, where one index is an array of integers t , and the other index is a slice : , results in the situation that is called "Combined Advanced and Basic Indexing". 这两个指数,其中一个指数是整数数组的存在t ,和其他指数是一个切片: ,导致局面被称为“复合高级和基本的索引”。

Now, what exactly happens in this "Combined" scenario? 现在,在这种“组合”方案中究竟发生了什么? Here goes: First, the shape of the result will get contributions from the first index t , as well as from the second index : . 结果如下:首先,结果的形状将来自第一个索引t和第二个索引:贡献。 Now t has the shape (3,3) , and hence the contribution of t to the shape of the result of x[t,:] , is to supply the outermost (leftmost) dimensions of the result shape. 现在t具有形状(3,3) ,因此tx[t,:]结果的形状的贡献是提供结果形状的最外部(最左侧)的尺寸。 Hence the result shape will begin with (3,3,) . 因此,结果形状将以(3,3,)开头。 Now, the contribution of : to the shape of x[t,:] is based on the answer to the question: On which dimension of x is the : being applied ? 现在, :x[t,:]形状的贡献是基于以下问题的答案::在x哪个维度上应用了: The answer is -- the second dimension (since : is the second index within x[t,:] ). 答案是-第二维(因为:x[t,:]的第二个索引)。 Hence the contribution of : to the result shape of x[t,:] is 3 (since 3 is the length of the second dimension of x ). 因此, :x[t,:]的结果形状的贡献为3 (因为3x的第二维的长度)。 To recap, we have deduced that the result shape of x[t] will be that of x[t,:] , which in turn will be (3,3,3) . 概括地说,我们推论出x[t]的结果形状将是x[t,:]形状,而x[t,:]的结果形状将是(3,3,3) This means x[t] will be a three-dimensional array, even though x itself is only a two-dimensional array. 这意味着x[t]将是三维数组,即使x本身只是二维数组也是如此。

Note that in the shape (3,3,3) of the result, the first two 3 s were contributed by the advanced index t , and the last 3 was contributed by the implicit basic index : . 请注意,在结果的形状(3,3,3)中,前两个3 s由高级索引t贡献,而后3由隐式基本索引:贡献。 These two indexes t and : also use different ways to arrive at their respective contributions. 这两个索引t:也使用不同的方式得出各自的贡献。 The 3,3 , contribution that came from the index t is just the shape of t itself. 来自索引t3,3贡献只是t本身的形状。 It doesn't care about the position of t among the indexes, in the expression x[t,:] (it doesn't care whether t occurs before : or : appears before t ). 它不关心t在索引x[t,:] (它不关心t是否出现在:之前或:出现在t之前)。 The 3 contribution that came from the index : is the length of the second dimension of x , and we consider the second dimension of x because : is the second index in the expression x[t,:] . 来自索引:3贡献是x第二维的长度,我们考虑x第二维,因为:是表达式x[t,:]第二个索引。 If x had the shape (3,5) instead of (3,3) , then the shape of x[t,:] would have been (3,3,5) instead of (3,3,3) . 如果x的形状为(3,5)而不是(3,3) ,则x[t,:]的形状应为(3,3,5)而不是(3,3,3)

Now that we've deduced the shape of the result of x[t] to be (3,3,3) , let us move on to understand how the values themselves will get determined, in the result. 现在我们已经推论出x[t]的结果的形状(3,3,3) ,让我们继续了解本身将如何确定。 The values in the result are obviously the values at positions [0,0,0], [0,0,1], [0,1,2], [0,1,0], [0,1,1], [0,1,2], [0,2,0], [0,2,1], [0,2,2], and so on. 结果中的值显然是[0,0,0],[0,0,1],[0,1,2],[0,1,0],[0,1,1]处的值,[0,1,2],[0,2,0],[0,2,1],[0,2,2]等。 Let's walk through one example of these positions, and you will hopefully get the drift. 让我们来看一个这些职位的例子,希望您能有所作为。 For our example, let's look at the position [0,1,2] in the result. 对于我们的示例,让我们看一下结果中的位置[0,1,2]。 To get the value for this position, we will first index into the t array using the 0 and the 1. That is, we find out t[0,1] , which will be 1 (refer to the output of print(t) ). 为了获得该位置的值,我们将首先使用0和1索引到t数组中。即,我们找到t[0,1] ,它将为1 (请参阅print(t)的输出)。 This 1 , which was obtained at t[0,1] , shall be taken to be our first index into x . t[0,1]处获得的1将作为我们对x的第一个索引。 The second index into x will be 2 (remember that we are discussing the position [0,1,2] within the result, and trying to determine the value at that position). x的第二个索引将为2 (请记住,我们正在讨论结果中的位置[0,1,2] ,并试图确定该位置的值)。 Now, given these first and second indices into x , we get from x the value to be populated at position [0,1,2] of x[t] . 现在,给定这些第一个和第二个索引到x ,我们从x得到要在x[t]位置[0,1,2]处填充的值。

Now, x is just full of ones. 现在, x充满了一个。 So, x[t] will only consist of ones, even though the shape of x[t] is (3,3,3) . 因此,即使x[t]的形状为(3,3,3)x[t]也将仅由1组成。 To really test your understanding of what I've said so far, you need to fill x with diverse values: So, temporarily, comment out Line 05, and have the following line in its place: 为了真正测试您对我到目前为止所说的内容的理解,您需要用不同的值来填充x :因此,暂时注释掉05行,并在其中放置以下行:

x = np.arange(9).reshape((3,3))    # New version of Line 05

Now, you will find that print(x[t]) at Line 08 gives you: 现在,您会发现第08行的print(x[t])给您:

[[[3 4 5]
  [3 4 5]
  [3 4 5]]

 [[3 4 5]
  [0 1 2]
  [3 4 5]]

 [[3 4 5]
  [3 4 5]
  [3 4 5]]]

Against this output, test your understanding of what I've described above, about how the values in the result will get determined. 根据此输出,测试您对我上面所描述的内容的了解,以及如何确定结果中的值。 (That is, if you've understood the above explanation of x[t] , you should be able to manually re-construct this same output as above, for print (x[t]) . (也就是说,如果您已经了解了x[t]的上述说明,则应该可以为print (x[t])手动重建与上述相同的输出。

Line 09: 第09行:

Given the definition of t on Line 06, Line 09 is equivalent to x[t] , which, as we saw above, is equivalent to x[t, :] = 0 . 给定第06行的t定义,第09行等效于x[t] ,如我们上面所见,它等效于x[t, :] = 0

And the effect of the assignment x[t, :] = 0 is the same as the effect of x[0:2, :] = 0 . x[t, :] = 0的效果与x[0:2, :] = 0的效果相同。

Why is this so? 为什么会这样呢? Simply because, in x[t, :] : 仅仅因为在x[t, :]

  1. The index values generated by the index t are 0 s and 1 s (since t is an integer index array consisting of only 0 s and 1 s) 索引t生成的索引值为0 s和1 s(因为t是仅包含0 s和1 s的整数索引数组)
  2. The index values generated by the index : are 0 , 1 , and 2 . 由索引产生的索引值:01 ,和2
  3. We are referring only to positions within x that correspond to combinations of these index values. 我们仅指x内与这些索引值的组合相对应的位置。 That is, x[t, :] relates only to the those positions x[i,j] , where i takes values 0 or 1 , and j takes values 0 , 1 , or 2 . 即, x[t, :]仅涉及那些位置x[i,j]其中i取值01 ,和j取值01 ,或2 That is, x[t, :] relates only to the positions x[0,0] , x[0,1] , x[0,2] , x[1,0] , x[1,1] , x[1,2] , within the array x . 也就是说, x[t, :] x[0,0]仅与位置x[0,0]x[0,1]x[0,2]x[1,0]x[1,1]x[1,2] ,在数组x
  4. So, the assignment statement x[t, :] = 0 assigns the value 0 at these positions in x . 因此,赋值语句x[t, :] = 0 ,: x[t, :] = 0x这些位置上赋值0。 Effectively, we are assigning the value 0 into all three columns in the first two rows of x , and we are leaving the third row of x unchanged. 实际上,我们将值0分配给x的前两行中的所有三列,并且使x的第三行保持不变。

Line 10: 第10行:

Prints the value of x after the above assignment. 在上述分配之后打印x的值。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM