딕트 값을 일치시켜 목록 내 딕트 인덱스 찾기
받아쓰기 목록이 있습니다.
list = [{'id':'1234','name':'Jason'},
{'id':'2345','name':'Tom'},
{'id':'3456','name':'Art'}]
이름 = 'Tom'과 일치하여 인덱스 위치 [0], [1] 또는 [2]를 효율적으로 찾을 수 있는 방법은 무엇입니까?
만약 이것이 1차원 목록이었다면 저는 list.index()를 할 수 있었을 텐데, 목록 내에서 딕트의 값을 검색하여 어떻게 진행해야 할지 모르겠습니다.
lst = [{'id':'1234','name':'Jason'}, {'id':'2345','name':'Tom'}, {'id':'3456','name':'Art'}]
tom_index = next((index for (index, d) in enumerate(lst) if d["name"] == "Tom"), None)
# 1
이름에서 반복적으로 가져와야 하는 경우 이름별로 인덱스를 작성해야 합니다(사전을 사용하여). 이렇게 하면 get 작업이 O(1) 시간이 됩니다.아이디어:
def build_dict(seq, key):
return dict((d[key], dict(d, index=index)) for (index, d) in enumerate(seq))
people_by_name = build_dict(lst, key="name")
tom_info = people_by_name.get("Tom")
# {'index': 1, 'id': '2345', 'name': 'Tom'}
간단하게 읽을 수 있는 버전은 다음과 같습니다.
def find(lst, key, value):
for i, dic in enumerate(lst):
if dic[key] == value:
return i
return -1
목록에서 모든 항목을 확인해야 하므로 효율적이지 않습니다(O(n)).효율성을 원한다면 딕트를 사용할 수 있습니다.질문에 대해 다음과 같은 한 가지 가능한 방법이 있습니다(그러나 이 데이터 구조를 고수하려면 Brent Newey가 코멘트에 기록한 것처럼 제너레이터를 사용하는 것이 실제로 더 효율적입니다. 토클랜드의 답변도 참조하십시오.).
>>> L = [{'id':'1234','name':'Jason'},
... {'id':'2345','name':'Tom'},
... {'id':'3456','name':'Art'}]
>>> [i for i,_ in enumerate(L) if _['name'] == 'Tom'][0]
1
필터/인덱스 콤보를 사용하는 것이 가장 논리적으로 보입니다.
names=[{}, {'name': 'Tom'},{'name': 'Tony'}]
names.index(next(filter(lambda n: n.get('name') == 'Tom', names)))
1
일치하는 항목이 여러 개 있을 수 있다고 생각하는 경우:
[names.index(item) for item in filter(lambda n: n.get('name') == 'Tom', names)]
[1]
@faham이 제공하는 답변은 한 줄로 묶는 것이 좋지만, 값이 포함된 사전에 색인을 반환하지는 않습니다.대신 사전 자체를 반환합니다.인덱스가 여러 개인 경우 하나 이상의 목록을 가져오거나 인덱스가 없는 경우 빈 목록을 가져오는 간단한 방법은 다음과 같습니다.
list = [{'id':'1234','name':'Jason'},
{'id':'2345','name':'Tom'},
{'id':'3456','name':'Art'}]
[i for i, d in enumerate(list) if 'Tom' in d.values()]
출력:
>>> [1]
이 접근 방식에서 제가 좋아하는 점은 간단한 편집으로 인덱스와 사전 목록을 모두 튜플로 얻을 수 있다는 것입니다.이것이 제가 해결해야 할 문제이고 이 답들을 찾았습니다.다음에서는 작동 방식을 보여주기 위해 다른 사전에 중복 값을 추가했습니다.
list = [{'id':'1234','name':'Jason'},
{'id':'2345','name':'Tom'},
{'id':'3456','name':'Art'},
{'id':'4567','name':'Tom'}]
[(i, d) for i, d in enumerate(list) if 'Tom' in d.values()]
출력:
>>> [(1, {'id': '2345', 'name': 'Tom'}), (3, {'id': '4567', 'name': 'Tom'})]
이 솔루션은 값 중 하나에 'Tom'이 포함된 모든 사전을 찾습니다.
사전의 인덱스 위치가 존재할 경우 이를 찾는 함수가 있습니다.
dicts = [{'id':'1234','name':'Jason'},
{'id':'2345','name':'Tom'},
{'id':'3456','name':'Art'}]
def find_index(dicts, key, value):
class Null: pass
for i, d in enumerate(dicts):
if d.get(key, Null) == value:
return i
else:
raise ValueError('no dict with the key and value combination found')
print find_index(dicts, 'name', 'Tom')
# 1
find_index(dicts, 'name', 'Ensnare')
# ValueError: no dict with the key and value combination found
라이너 하나!?
elm = ([i for i in mylist if i['name'] == 'Tom'] or [None])[0]
목록에 있는 여러 사전이 핵심 가치를 가질 수 있는 가능성을 설명하기 위한 보다 일반적인 솔루션과 목록 이해를 사용한 간단한 구현이 필요했습니다.
dict_indices = [i for i, d in enumerate(dict_list) if d[dict_key] == key_value]
지정된 반복 가능한 경우 술어를 만족하는 항목의 위치를 산출합니다.
import more_itertools as mit
iterable = [
{"id": "1234", "name": "Jason"},
{"id": "2345", "name": "Tom"},
{"id": "3456", "name": "Art"}
]
list(mit.locate(iterable, pred=lambda d: d["name"] == "Tom"))
# [1]
more_itertools
는 다른 유용한 도구 중에서 사이트 도구 레시피를 구현하는 타사 라이브러리입니다.
def search(itemID,list):
return[i for i in list if i.itemID==itemID]
나의 대답은 사용하기에 하나의 사전에 있는 것이 더 좋습니다.
food_time_dict = {"Lina": 312400, "Tom": 360054, "Den": 245800}
print(list(food_time_dict.keys()).index("Lina"))
사전에 키를 요청한 다음 목록을 번역합니다. 추가되지 않으면 오류가 발생하여 목록으로 사용합니다. 하지만 코드에:
lists = [{'id': '1234', 'name': 'Jason'},
{'id': '2345', 'name': 'Tom'},
{'id': '3456', 'name': 'Art'}]
def dict_in_lists_index(lists, search): # function for convenience
j = 0 # [j][i]
for i in lists:
try: # try our varible search if not found in list
return f"[{j}][{list(i.values()).index(search)}]"
# small decor
except ValueError: # error was ValueError
pass # aa... what must was what you want to do
j += 1 # not found? ok j++
return "Not Found"
def dict_cropped_index(lists, search):
for i in lists:
try:
return list(i.values()).index(search)
except ValueError:
pass
return "Not Found"
print(dict_in_lists_index(lists, 'Tom')) # and end
print(dict_cropped_index(lists, 'Tom')) # now for sure end
다음은 첫 번째 일치 항목에 대한 인덱스를 반환합니다.
['Tom' == i['name'] for i in list].index(True)
언급URL : https://stackoverflow.com/questions/4391697/find-the-index-of-a-dict-within-a-list-by-matching-the-dicts-value
'programing' 카테고리의 다른 글
장고-고-고-고-고-고-고-고-고가 나타나지 않음 (0) | 2023.06.06 |
---|---|
S3 버킷의 하위 폴더 이름을 bo에서 3으로 검색하는 중 (0) | 2023.06.06 |
명령행 인수를 레이크 태스크로 전달하는 방법 (0) | 2023.06.06 |
ugettext_lazy는 언제 사용해야 합니까? (0) | 2023.06.06 |
Android 도구 모음 센터 제목 및 사용자 정의 글꼴 (0) | 2023.06.01 |