I have a 1D NumPy array, and I want to find the index of the last non-zero element. The vector consists only of 1s and 0s, not sure if this is relevant information.
For example:
import numpy as np
vec = np.array([0, 1, 1, 0, 0, 1, 0, 0])
In this case, the result should be 5 because vec[5] == 1 is the last non-zero value.
What is the most efficient way to do this using NumPy?
I am forced to use Python, but this will run a few million times with arrays that are quite a bit larger than the example and I need this to be as performant as possible. Any little edge helps.
Here are two approaches I currently have. One using standard python loops, the other one trying to leverage what NumPy gives me. I feel like there might be some elegant way of making this even more performant, but I am constrained by only having an Economics degree.
def last_nonzero_index(vec):
for i in range(len(vec) - 1, -1, -1):
if vec[i] != 0:
return i
return None
def last_nonzero_index(vec):
rev_idx = np.flatnonzero(vec[::-1])
return len(vec) - 1 - rev_idx[0] if rev_idx.size else None
Right now the native python loop does beat everything else.
Use Numba JIT compilation. It's significantly faster than any NumPy-based approach.
from numba import njit
import numpy as np
@njit
def find_last_nonzero(vec):
"""Finds the last non-zero element's index in a vector"""
for i in range(len(vec) - 1, -1, -1):
if vec[i] != 0:
return i
return -1
Usage
vec = np.array([0, 1, 1, 0, 0, 1, 0, 0])
result = find_last_nonzero(vec)
print(result)