This question already has answers here:
How to find maximum value in whole 2D array with indices [duplicate]
(3 answers)
Closed 2 years ago.
I have a large 2-dimensional Numpy array which looks a bit like this, and I want to find the indexes of the highest number in the array.
[[0.09911875 0.087047 0.07395894 ... 0.10334793 0.10507131 0.10572167]
[0.09951172 0.08808007 0.07559184 ... 0.0953996 0.09637988 0.09686002]
[0.09908096 0.08856899 0.07680183 ... 0.08633772 0.08709209 0.08753099]
...
[0.16518855 0.1658697 0.16564748 ... 0.16108064 0.15890269 0.15795946]
[0.16250964 0.1616099 0.16255783 ... 0.15931444 0.15753458 0.15655452]
[0.16211866 0.15905266 0.15936445 ... 0.15891747 0.15701842 0.15521818]]
So far, I've tried to use numpy.where() as that function returns a tuple of coordinates but I've only been able to receive an array of tuples, but I want one tuple, the coordinates of the highest number. I've also tried to use other Numpy methods like np.amax, np.max, and np.where but to no success.
To further explain, if you had a small 2D array like this. The largest number is 9.99 and the indexes of the highest number will be (2,2).
[[2.18, 4.01, 3.49, 1.22]
[2.34, 5.23, 5.11, 4.23]
[1.23, 3.42, 9.99, 6.02]
[2.08, 4.01, 3.49, 1.22]]
You could use the numpy.argmax method combined with numpy.unravel:
Here's a minimal working example:
import numpy as np
# create random array
a = np.random.random((8, 8))
# find indexes of the maximum value in this array
np.unravel_index(a.argmax(), a.shape)
# > [4, 3]
You can use:
(x.argmax() // x.shape[1], x.argmax() % x.shape[1])
(2, 2)
All you need to do is to convert the index found by np.argmax() into your matrix indexes. This answer shows how to do that.
This is how you could do it.
import numpy as np
a = np.array([[1, 2, 3], [3, 4, 7], [4, 5, 1]])
max_index = np.argmax(a)
tuple_result = (max_index // a.shape[0], max_index % a.shape[1])
print(tuple_result)
If x is the array then you can try
np.where(x==np.max(x))
This will give you the i,j positions in the array.
Related
I'd like to generate an array which contains the positions of the highest integers/floating point numbers to the lowest in another array.
For example:
integers = [1,6,8,5]
I want the newly generated array to be:
newArray = [2,1,3,0]
or
floatingPoints = [1.6,0.5,1.1]
would become
newArray = [0,2,1]
You can use the numpy function argsort and then simply reverse the ordering as it gives you ascending rather than descending, by default:
np.argsort(integers)[::-1]
Example:
import numpy as np
integers = np.array([1, 6, 8, 5])
np.argsort(integers)[::-1]
This results in the desired [2, 1, 3, 0].
Given a list of numpy arrays, each of different length, as that obtained by doing lst = np.array_split(arr, indices), how do I get the sum of every array in the list? (I know how to do it using list-comprehension but I was hoping there was a pure-numpy way to do it).
I thought that this would work:
np.apply_along_axis(lambda arr: arr.sum(), axis=0, arr=lst)
But it doesn't, instead it gives me this error which I don't understand:
ValueError: operands could not be broadcast together with shapes (0,) (12,)
NB: It's an array of sympy objects.
There's a faster way which avoids np.split, and utilizes np.reduceat. We create an ascending array of indices where you want to sum elements with np.append([0], np.cumsum(indices)[:-1]). For proper indexing we need to put a zero in front (and discard the last element, if it covers the full range of the original array.. otherwise just delete the [:-1] indexing). Then we use the np.add ufunc with np.reduceat:
import numpy as np
arr = np.arange(1, 11)
indices = np.array([2, 4, 4])
# this should split like this
# [1 2 | 3 4 5 6 | 7 8 9 10]
np.add.reduceat(arr, np.append([0], np.cumsum(indices)[:-1]))
# array([ 3, 18, 34])
I have a numpy array arr of numpy arrays each with varying length. I can get the shape of arr:
arr.shape
>>> (9,)
I can get the shape of one of the elements of arr:
arr[0].shape
>>> (6, 1, 2)
And I know that all such elements have shape (n, 1, 2).
I want to slice arr to get a 1 dimensional result as follows:
arr[:,:,:,0]
But I get the following error:
IndexError: too many indices for array
EDIT: My original question was misleading. I want to do this slice so that I can assign values to the slice. So getting the slice in a new variable is not useful for my case. Essentially I want to do something like this in a simple one liner:
arr[:,:,:,0] = arr[:,:,:,0] - np.min(arr[:,:,:,0])
You can fix your first (in fact all varying ones) dimension, and apply your transformation per static-shaped elements of arr
import numpy as np
from random import randint
arr=np.array([np.random.randint(3,15, size=(randint(3,9),randint(3,7),randint(6,19))) for el in range(9)])
print(arr.shape)
print(arr[0].shape)
for i in range(arr.shape[0]):
arr[i][:,:,0]-=arr[i][:,:,0].min()
print(arr[i][:,:,0])
You could use list comprehension version of your solution.
desired_result = np.array([el[:,:,0] for el in arr])
How do you split an array in python in terms of the number of elements in the array. Im doing knn classification and I need to take into account of the first k elements of the 2D array.
import numpy as np
x = np.array([1, 2, 4, 4, 6, 7])
print(x[range(0, 4)])
You can also split it up by taking the range of elements that you want to work with. You could store x[range(x, x)]) in a variable and work with those particular elements of the array as well. The output as you can see splits the array up:
[1 2 4 4]
In Numpy, there is a method numpy.split.
x = np.arange(9.0)
np.split(x, 3)
Say that I have 4 numpy arrays
[1,2,3]
[2,3,1]
[3,2,1]
[1,3,2]
In this case, I've determined [1,2,3] is the "minimum array" for my purposes, as it is one of two arrays with lowest value at index 0, and of those two arrays it has the the lowest index 1. If there were more arrays with similar values, I would need to compare the next index values, and so on.
How can I extract the array [1,2,3] in that same order from the pile?
How can I extend that to x arrays of size n?
Thanks
Using the python non-numpy .sort() or sorted() on a list of lists (not numpy arrays) automatically does this e.g.
a = [[1,2,3],[2,3,1],[3,2,1],[1,3,2]]
a.sort()
gives
[[1,2,3],[1,3,2],[2,3,1],[3,2,1]]
The numpy sort seems to only sort the subarrays recursively so it seems the best way would be to convert it to a python list first. Assuming you have an array of arrays you want to pick the minimum of you could get the minimum as
sorted(a.tolist())[0]
As someone pointed out you could also do min(a.tolist()) which uses the same type of comparisons as sort, and would be faster for large arrays (linear vs n log n asymptotic run time).
Here's an idea using numpy:
import numpy
a = numpy.array([[1,2,3],[2,3,1],[3,2,1],[1,3,2]])
col = 0
while a.shape[0] > 1:
b = numpy.argmin(a[:,col:], axis=1)
a = a[b == numpy.min(b)]
col += 1
print a
This checks column by column until only one row is left.
numpy's lexsort is close to what you want. It sorts on the last key first, but that's easy to get around:
>>> a = np.array([[1,2,3],[2,3,1],[3,2,1],[1,3,2]])
>>> order = np.lexsort(a[:, ::-1].T)
>>> order
array([0, 3, 1, 2])
>>> a[order]
array([[1, 2, 3],
[1, 3, 2],
[2, 3, 1],
[3, 2, 1]])