Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Fastest way to find Indexes of item in list?

If one was to attempt to find the indexes of an item in a list you could do it a couple different ways here is what I know to be the fastest:

aList = [123, 'xyz', 'zara','xyz', 'abc']; 
indices = [i for i, x in enumerate(aList) if x == "xyz"]
print(indices)

Another way not pythonic and slower:

count = 0
indices = []
aList = [123, 'xyz', 'zara','xyz', 'abc'];
for i in range(0,len(aList):
    if 'xyz' == aList[i]:
        indices.append(i)
print(indices)

The first method is undoubtedly faster however what if you wanted to go faster, is there a way? For the first index using method:

aList = [123, 'xyz', 'zara','xyz', 'abc'];             
print "Index for xyz : ", aList.index( 'xyz' ) 

is very fast but can't handle multiple indexes.
How might one go about speeding things up?

like image 978
Tyler Cowan Avatar asked Feb 25 '16 23:02

Tyler Cowan


People also ask

What is the fastest way to find an element in a list Python?

To facilitate this, Python has an inbuilt function called index(). This function takes in the element as an argument and returns the index. By using this function we are able to find the index of an element in a list in Python.

How do you get the multiple index of an element in a list in Python?

One of the most basic ways to get the index positions of all occurrences of an element in a Python list is by using a for loop and the Python enumerate function. The enumerate function is used to iterate over an object and returns both the index and element.

How do you find the index of a string in a list?

By using type() operator we can get the string elements indexes from the list, string elements will come under str() type, so we iterate through the entire list with for loop and return the index which is of type string.


2 Answers

Use list.index(elem, start)! That uses a for loop in C (see its implementation list_index_impl function in the source of CPython's listobject.c). Avoid looping through all the elements in Python, it is slower than in C.

def index_finder(lst, item):
    """A generator function, if you might not need all the indices"""
    start = 0
    while True:
        try:
            start = lst.index(item, start)
            yield start
            start += 1
        except ValueError:
            break

import array
def index_find_all(lst, item, results=None):
    """ If you want all the indices.
    Pass results=[] if you explicitly need a list,
    or anything that can .append(..)
    """
    if results is None:
        length = len(lst)
        results = (array.array('B') if length <= 2**8 else
                   array.array('H') if length <= 2**16 else
                   array.array('L') if length <= 2**32 else
                   array.array('Q'))
    start = 0
    while True:
        try:
            start = lst.index(item, start)
            results.append(start)
            start += 1
        except ValueError:
            return results

# Usage example
l = [1, 2, 3, 4, 5, 6, 7, 8] * 32

print(*index_finder(l, 1))
print(*index_find_all(l, 1))
like image 135
poke53280 Avatar answered Nov 02 '22 17:11

poke53280


def find(target, myList):
    for i in range(len(myList)):
        if myList[i] == target:
            yield i

def find_with_list(myList, target):
     inds = []
     for i in range(len(myList)):
         if myList[i] == target:
             inds += i,
     return inds


In [8]: x = range(50)*200
In [9]: %timeit [i for i,j in enumerate(x) if j == 3]
1000 loops, best of 3: 598 us per loop

In [10]: %timeit list(find(3,x))
1000 loops, best of 3: 607 us per loop
In [11]: %timeit find(3,x)
1000000 loops, best of 3: 375 ns per loop

In [55]: %timeit find_with_list(x,3)
1000 loops, best of 3: 618 us per loop

Assuming you want a list as your output:

  • All options seemed exhibit similar time performance for my test with the list comprehension being the fastest (barely).

If using a generator is acceptable, it's way faster than the other approaches. Though it doesn't account for actually iterating over the indices, nor does it store them, so the indices cannot be iterated over a second time.

like image 44
Garrett R Avatar answered Nov 02 '22 18:11

Garrett R