Can someone explain exactly what the axis
parameter in NumPy does?
I am terribly confused.
I'm trying to use the function myArray.sum(axis=num)
At first I thought if the array is itself 3 dimensions, axis=0
will return three elements, consisting of the sum of all nested items in that same position. If each dimension contained five dimensions, I expected axis=1
to return a result of five items, and so on.
However this is not the case, and the documentation does not do a good job helping me out (they use a 3x3x3 array so it's hard to tell what's happening)
Here's what I did:
>>> e
array([[[1, 0],
[0, 0]],
[[1, 1],
[1, 0]],
[[1, 0],
[0, 1]]])
>>> e.sum(axis = 0)
array([[3, 1],
[1, 1]])
>>> e.sum(axis=1)
array([[1, 0],
[2, 1],
[1, 1]])
>>> e.sum(axis=2)
array([[1, 0],
[2, 1],
[1, 1]])
>>>
Clearly the result is not intuitive.
Clearly,
e.shape == (3, 2, 2)
Sum over an axis is a reduction operation so the specified axis disappears. Hence,
e.sum(axis=0).shape == (2, 2)
e.sum(axis=1).shape == (3, 2)
e.sum(axis=2).shape == (3, 2)
Understanding what axis means in numpy:
Consider the 3 dimensional x,y,z coordinate plane:
The axis parameter is a number that communicates to numpy arrays along which dimension you want your aggregate function to operate.
Python numpy/pandas axis mnemonic:
axis=0 means 'along the row', (x in the above image)
axis=1 means 'along the column', (y in the above image)
axis=2 means 'along the depth', (z in the above image)
Image source: https://github.com/sentientmachine/Cheatsheets#python_numpy
Understanding the axis parameter is a necessity if you are to understand numpy vectorization specifically the order of dimensional operations for broadcasting.
Imagine we want to sum across a matrix with three dimensions. A sum could operate along the x, y or z axis, or along all three. By default axis is 0 meaning the outermost dimension, the outermost dimension is the one returned by your_3d_matrix[0]
So if you sum along axis=0, axis=1, or axis=2 you will receive one dimensional sum slices across that dimension.
Example:
a = np.array([[1,2],[3,4]]) #define a simple 2d ndarray
>>> a[0,0]
1
>>> a[0,1]
2
>>> a[1,0]
3
>>> a[1,1]
4
>>> a.sum() #axis not specified means first along the col then
10 #along the row: (1+3) = 4 and
#2+4 = 6 then along the column 4+6 = 10
>>> a.sum(axis=0) #forcing axis=0 says collapse along the row so:
array([4, 6]) #1+3 = 4, 2+4 = 6
>>> a.sum(axis=1) #forcing axis=1 says collapse along the col so:
array([3, 7]) #1+2 = 3, 3+4 = 7
You can even have axis=2 which is the 2nd dimension down:
>>> b = np.array([[[1,2],[3,4]], [[5,6],[7,8]]])
>>> b
array([[[1, 2],
[3, 4]],
[[5, 6],
[7, 8]]])
>>> b.sum() #sum along depth, col, then row:
36
>>> b.sum(axis=0) #sum across the topmost dimension 0, the two groups of 4
array([[ 6, 8],
[10, 12]])
>>> b.sum(axis=1) #sum across dimension 1 the lists of two, added.
array([[ 4, 6],
[12, 14]])
>>> b.sum(axis=2) #sum across the dimension 2, each individual list, row wise.
array([[ 3, 7],
[11, 15]])
The axis orientation depends on the structure it applies to.
The orders of operation of axis collapse starts at outermost, the dimension of yourarray[0]
to innermost: yourarray[0][0][0]
.
Even the developers who coded up this numpy software have trouble creating intuition for the linear algebra governing matrix operations, Youtube videos attempt to explain the axis parameter in depth:
Alexandre Chabot LeClerc NumPy Tutorial that covers the axis parameter: https://youtu.be/gtejJ3RCddE?t=1h55m17s
Data School channel on youtube has an excellent explanation of the axis parameter: https://youtu.be/PtO3t6ynH-8?t=5m1s
To understand the axis
intuitively, refer the picture below (source: Physics Dept, Cornell Uni)
The shape of the (boolean) array in the above figure is shape=(8, 3)
. ndarray.shape will return a tuple where the entries correspond to the length of the particular dimension. In our example, 8
corresponds to length of axis 0 whereas 3
corresponds to length of axis 1.
There are good answers for visualization however it might help to think purely from analytical perspective.
You can create array of arbitrary dimension with numpy. For example, here's a 5-dimension array:
>>> a = np.random.rand(2, 3, 4, 5, 6)
>>> a.shape
(2, 3, 4, 5, 6)
You can access any element of this array by specifying indices. For example, here's the first element of this array:
>>> a[0, 0, 0, 0, 0]
0.0038908603263844155
Now if you take out one of the dimensions, you get number of elements in that dimension:
>>> a[0, 0, :, 0, 0]
array([0.00389086, 0.27394775, 0.26565889, 0.62125279])
When you apply a function like sum
with axis
parameter, that dimension gets eliminated and array of dimension less than original gets created. For each cell in new array, the operator will get list of elements and apply the reduction function to get a scaler.
>>> np.sum(a, axis=2).shape
(2, 3, 5, 6)
Now you can check that the first element of this array is sum of above elements:
>>> np.sum(a, axis=2)[0, 0, 0, 0]
1.1647502999560164
>>> a[0, 0, :, 0, 0].sum()
1.1647502999560164
The axis=None
has special meaning to flatten out the array and apply function on all numbers.
Now you can think about more complex cases where axis is not just number but a tuple:
>>> np.sum(a, axis=(2,3)).shape
(2, 3, 6)
Note that we use same technique to figure out how this reduction was done:
>>> np.sum(a, axis=(2,3))[0,0,0]
7.889432081931909
>>> a[0, 0, :, :, 0].sum()
7.88943208193191
You can also use same reasoning for adding dimension in array instead of reducing dimension:
>>> x = np.random.rand(3, 4)
>>> y = np.random.rand(3, 4)
# New dimension is created on specified axis
>>> np.stack([x, y], axis=2).shape
(3, 4, 2)
>>> np.stack([x, y], axis=0).shape
(2, 3, 4)
# To retrieve item i in stack set i in that axis
Hope this gives you generic and full understanding of this important parameter.
来源:https://stackoverflow.com/questions/22320534/how-does-the-axis-parameter-from-numpy-work