Given a list ["foo", "bar", "baz"] and an item in the list "bar", how do I get its index 1?
Given a list ["foo", "bar", "baz"] and an item in the list "bar", how do I get its index 1?
>>> ["foo", "bar", "baz"].index("bar")
1
Reference: Data Structures > More on Lists
Note that while this is perhaps the cleanest way to answer the question as asked, index is a rather weak component of the list API, and I can't remember the last time I used it in anger. It's been pointed out to me in the comments that because this answer is heavily referenced, it should be made more complete. Some caveats about list.index follow. It is probably worth initially taking a look at the documentation for it:
list.index(x[, start[, end]])Return zero-based index in the list of the first item whose value is equal to x. Raises a
ValueErrorif there is no such item.The optional arguments start and end are interpreted as in the slice notation and are used to limit the search to a particular subsequence of the list. The returned index is computed relative to the beginning of the full sequence rather than the start argument.
An index call checks every element of the list in order, until it finds a match. If your list is long, and you don't know roughly where in the list it occurs, this search could become a bottleneck. In that case, you should consider a different data structure. Note that if you know roughly where to find the match, you can give index a hint. For instance, in this snippet, l.index(999_999, 999_990, 1_000_000) is roughly five orders of magnitude faster than straight l.index(999_999), because the former only has to search 10 entries, while the latter searches a million:
>>> import timeit
>>> timeit.timeit('l.index(999_999)', setup='l = list(range(0, 1_000_000))', number=1000)
9.356267921015387
>>> timeit.timeit('l.index(999_999, 999_990, 1_000_000)', setup='l = list(range(0, 1_000_000))', number=1000)
0.0004404920036904514
A call to index searches through the list in order until it finds a match, and stops there. If you expect to need indices of more matches, you should use a list comprehension, or generator expression.
>>> [1, 1].index(1)
0
>>> [i for i, e in enumerate([1, 2, 1]) if e == 1]
[0, 2]
>>> g = (i for i, e in enumerate([1, 2, 1]) if e == 1)
>>> next(g)
0
>>> next(g)
2
Most places where I once would have used index, I now use a list comprehension or generator expression because they're more generalizable. So if you're considering reaching for index, take a look at these excellent Python features.
A call to index results in a ValueError if the item's not present.
>>> [1, 1].index(2)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
ValueError: 2 is not in list
If the item might not be present in the list, you should either
item in my_list (clean, readable approach), orindex call in a try/except block which catches ValueError (probably faster, at least when the list to search is long, and the item is usually present.)One thing that is really helpful in learning Python is to use the interactive help function:
>>> help(["foo", "bar", "baz"])
Help on list object:
class list(object)
...
|
| index(...)
| L.index(value, [start, [stop]]) -> integer -- return first index of value
|
which will often lead you to the method you are looking for.
me = ["foo", "bar", "baz"]
me.index("bar")
You can apply this for any member of the list to get their index
My friend, I have made the easiest code to solve your question. While you were receiving gigantic lines of codes, I am here to cater you a two line code which is all due to the help of index() function in python.
LIST = ['foo' ,'boo', 'shoo']
print(LIST.index('boo'))
Output:
1
I Hope I have given you the best and the simplest answer which might help you greatly.
There is a chance that that value may not be present so to avoid this ValueError, we can check if that actually exists in the list .
list = ["foo", "bar", "baz"]
item_to_find = "foo"
if item_to_find in list:
index = list.index(item_to_find)
print("Index of the item is " + str(index))
else:
print("That word does not exist")
It just uses the python function array.index() and with a simple Try / Except it returns the position of the record if it is found in the list and return -1 if it is not found in the list (like on JavaScript with the function indexOf()).
fruits = ['apple', 'banana', 'cherry']
try:
pos = fruits.index("mango")
except:
pos = -1
In this case "mango" is not present in the list fruits so the pos variable is -1, if I had searched for "cherry" the pos variable would be 2.
List comprehension would be the best option to acquire a compact implementation in finding the index of an item in a list.
a_list = ["a", "b", "a"]
print([index for (index , item) in enumerate(a_list) if item == "a"])
# Throws ValueError if nothing is found
some_list = ['foo', 'bar', 'baz'].index('baz')
# some_list == 2
some_list = [item1, item2, item3]
# Throws StopIteration if nothing is found
# *unless* you provide a second parameter to `next`
index_of_value_you_like = next(
i for i, item in enumerate(some_list)
if item.matches_your_criteria())
index_of_staff_members = [
i for i, user in enumerate(users)
if user.is_staff()]
It is mentioned in numerous answers that the built-in method of list.index(item) method is an O(n) algorithm. It is fine if you need to perform this once. But if you need to access the indices of elements a number of times, it makes more sense to first create a dictionary (O(n)) of item-index pairs, and then access the index at O(1) every time you need it.
If you are sure that the items in your list are never repeated, you can easily:
myList = ["foo", "bar", "baz"]
# Create the dictionary
myDict = dict((e,i) for i,e in enumerate(myList))
# Lookup
myDict["bar"] # Returns 1
# myDict.get("blah") if you don't want an error to be raised if element not found.
If you may have duplicate elements, and need to return all of their indices:
from collections import defaultdict as dd
myList = ["foo", "bar", "bar", "baz", "foo"]
# Create the dictionary
myDict = dd(list)
for i,e in enumerate(myList):
myDict[e].append(i)
# Lookup
myDict["foo"] # Returns [0, 4]
If you are going to find an index once then using "index" method is fine. However, if you are going to search your data more than once then I recommend using bisect module. Keep in mind that using bisect module data must be sorted. So you sort data once and then you can use bisect. Using bisect module on my machine is about 20 times faster than using index method.
Here is an example of code using Python 3.8 and above syntax:
import bisect
from timeit import timeit
def bisect_search(container, value):
return (
index
if (index := bisect.bisect_left(container, value)) < len(container)
and container[index] == value else -1
)
data = list(range(1000))
# value to search
value = 666
# times to test
ttt = 1000
t1 = timeit(lambda: data.index(value), number=ttt)
t2 = timeit(lambda: bisect_search(data, value), number=ttt)
print(f"{t1=:.4f}, {t2=:.4f}, diffs {t1/t2=:.2f}")
Output:
t1=0.0400, t2=0.0020, diffs t1/t2=19.60
I find this two solution is better and I tried it by myself
>>> expences = [2200, 2350, 2600, 2130, 2190]
>>> 2000 in expences
False
>>> expences.index(2200)
0
>>> expences.index(2350)
1
>>> index = expences.index(2350)
>>> expences[index]
2350
>>> try:
... print(expences.index(2100))
... except ValueError as e:
... print(e)
...
2100 is not in list
>>>
text = ["foo", "bar", "baz"]
target = "bar"
[index for index, value in enumerate(text) if value == target]
For a small list of elements, this would work fine. However, if the list contains a large number of elements, better to apply binary search with O(log n) runtime complexity .
For those coming from another language like me, maybe with a simple loop it's easier to understand and use it:
mylist = ["foo", "bar", "baz", "bar"]
newlist = enumerate(mylist)
for index, item in newlist:
if item == "bar":
print(index, item)
I am thankful for So what exactly does enumerate do?. That helped me to understand.
As indicated by @TerryA, many answers discuss how to find one index.
more_itertools is a third-party library with tools to locate multiple indices within an iterable.
Given
import more_itertools as mit
iterable = ["foo", "bar", "baz", "ham", "foo", "bar", "baz"]
Code
Find indices of multiple observations:
list(mit.locate(iterable, lambda x: x == "bar"))
# [1, 5]
Test multiple items:
list(mit.locate(iterable, lambda x: x in {"bar", "ham"}))
# [1, 3, 5]
See also more options with more_itertools.locate. Install via > pip install more_itertools.
Let’s give the name lst to the list that you have. One can convert the list lst to a numpy array. And, then use numpy.where to get the index of the chosen item in the list. Following is the way in which you will implement it.
import numpy as np
lst = ["foo", "bar", "baz"] #lst: : 'list' data type
print np.where( np.array(lst) == 'bar')[0][0]
>>> 1
Certain structures in python contains a index method that works beautifully to solve this question.
'oi tchau'.index('oi') # 0
['oi','tchau'].index('oi') # 0
('oi','tchau').index('oi') # 0
References:
using dictionary , where process the list first and then add the index to it
from collections import defaultdict
index_dict = defaultdict(list)
word_list = ['foo','bar','baz','bar','any', 'foo', 'much']
for word_index in range(len(word_list)) :
index_dict[word_list[word_index]].append(word_index)
word_index_to_find = 'foo'
print(index_dict[word_index_to_find])
# output : [0, 5]
Pythonic way would to use enumerate but you can also use indexOf from operator module. Please note that this will raise ValueError if b not in a.
>>> from operator import indexOf
>>>
>>>
>>> help(indexOf)
Help on built-in function indexOf in module _operator:
indexOf(a, b, /)
Return the first index of b in a.
>>>
>>>
>>> indexOf(("foo", "bar", "baz"), "bar") # with tuple
1
>>> indexOf(["foo", "bar", "baz"], "bar") # with list
1
One can use zip() function to get the index of the value in the list. The code could be;
list1 = ["foo","bar","baz"]
for index,value in zip(range(0,len(list1)),list1):
if value == "bar":
print(index)
Simple option:
a = ["foo", "bar", "baz"]
[i for i in range(len(a)) if a[i].find("bar") != -1]