Проверьте, существует ли данный ключ в словаре

Я хотел проверить, существует ли ключ в словаре, прежде чем обновлять значение ключа. Я написал следующий код:

if 'key1' in dict.keys():
  print "blah"
else:
  print "boo"

Я думаю, что это не лучший способ выполнить эту задачу. Есть ли лучший способ проверить ключ в словаре?

21 ответ

Решение

in это намеченный способ проверить наличие ключа в dict,

d = dict()

for i in xrange(100):
    key = i % 10
    if key in d:
        d[key] += 1
    else:
        d[key] = 1

Если вы хотели по умолчанию, вы всегда можете использовать dict.get():

d = dict()

for i in xrange(100):
    key = i % 10
    d[key] = d.get(key, 0) + 1

... и если вы хотите всегда гарантировать значение по умолчанию для любого ключа, который вы можете использовать defaultdict от collections модуль, вот так:

from collections import defaultdict

d = defaultdict(lambda: 0)

for i in xrange(100):
    d[i % 10] += 1

... но в целом in ключевое слово - лучший способ сделать это.

Вам не нужно называть ключи:

if 'key1' in dict:
  print "blah"
else:
  print "boo"

Это будет намного быстрее, так как он использует хеширование словаря, а не линейный поиск, как это делают вызывающие ключи.

Вы можете проверить наличие ключа в словаре, используя ключевое слово in:

d = {'a': 1, 'b': 2}
'a' in d # <== evaluates to True
'c' in d # <== evaluates to False

Обычное использование для проверки наличия ключа в словаре перед его изменением - инициализация значения по умолчанию (например, если ваши значения являются списками, и вы хотите убедиться, что существует пустой список, к которому вы можете добавить при вставке первого значения для ключа). В таких случаях вы можете найти collections.defaultdict() типа, чтобы представлять интерес.

В старом коде вы также можете найти некоторые варианты использования has_key() устаревший метод для проверки наличия ключей в словарях (просто используйте key_name in dict_name вместо).

Вы можете сократить это:

if 'key1' in dict:
    ...

Однако это в лучшем случае косметическое улучшение. Почему вы считаете, что это не лучший способ?

Для получения дополнительной информации о быстром выполнении предложенного метода предложенного ответа (10-метровые петли):

  • 'key' in mydict прошедшее время 1,07 сек
  • mydict.get('key') прошедшее время 1,84 сек
  • mydefaultdict['key'] прошедшее время 1,07 сек

Поэтому с помощью in или же defaultdict рекомендуются против get,

Я бы порекомендовал использовать setdefault метод вместо. Похоже, он будет делать все, что вы хотите.

>>> d = {'foo':'bar'}
>>> q = d.setdefault('foo','baz') #Do not override the existing key
>>> print q #The value takes what was originally in the dictionary
bar
>>> print d
{'foo': 'bar'}
>>> r = d.setdefault('baz',18) #baz was never in the dictionary
>>> print r #Now r has the value supplied above
18
>>> print d #The dictionary's been updated
{'foo': 'bar', 'baz': 18}

Словарь в python имеет метод get('key', default). Таким образом, вы можете просто установить значение по умолчанию, если нет ключа.

values = {...}
myValue = values.get('Key', None)

Использование троичного оператора:

message = "blah" if 'key1' in dict else "booh"
print(message)

Как насчет использования EAFP (проще просить прощения, чем разрешения):

try:
   blah = dict["mykey"]
   # key exists in dict
except KeyError:
   # key doesn't exist in dict

Смотрите другие SO сообщения:

Используя try vs if в python или

Проверка существования члена в Python

Проверьте, существует ли данный ключ в словаре

Чтобы понять, как это сделать, мы сначала проверим, какие методы мы можем вызвать в словаре. Вот методы:

d={'clear':0, 'copy':1, 'fromkeys':2, 'get':3, 'items':4, 'keys':5, 'pop':6, 'popitem':7, 'setdefault':8, 'update':9, 'values':10}

Python Dictionary clear()       Removes all Items
Python Dictionary copy()        Returns Shallow Copy of a Dictionary
Python Dictionary fromkeys()    Creates dictionary from given sequence
Python Dictionary get()         Returns Value of The Key
Python Dictionary items()       Returns view of dictionary (key, value) pair
Python Dictionary keys()        Returns View Object of All Keys
Python Dictionary pop()         Removes and returns element having given key
Python Dictionary popitem()     Returns & Removes Element From Dictionary
Python Dictionary setdefault()  Inserts Key With a Value if Key is not Present
Python Dictionary update()      Updates the Dictionary 
Python Dictionary values()      Returns view of all values in dictionary

Жестокий метод проверки, если ключ уже существует, может быть get() метод:

d.get("key")

Два других интересных метода items() а также keys() звучит как слишком много работы. Итак, давайте посмотрим, если get() это правильный метод для нас. У нас есть наш дикт d:

d= {'clear':0, 'copy':1, 'fromkeys':2, 'get':3, 'items':4, 'keys':5, 'pop':6, 'popitem':7, 'setdefault':8, 'update':9, 'values':10}

Печать показывает, что ключ, которого у нас нет, вернется None:

print(d.get('key')) #None
print(d.get('clear')) #0
print(d.get('copy')) #1

Мы можем использовать это, чтобы получить информацию, если ключ присутствует или нет. Но учтите это, если мы создадим диктат с одним key:None:

d= {'key':None}
print(d.get('key')) #None
print(d.get('key2')) #None

Ведущий get() метод не является надежным в случае, если некоторые значения могут быть None, У этой истории должен быть более счастливый конец. Если мы используем in компаратор:

print('key' in d) #True
print('key2' in d) #False

Мы получаем правильные результаты. Мы можем изучить байт-код Python:

import dis
dis.dis("'key' in d")
#   1           0 LOAD_CONST               0 ('key')
#               2 LOAD_NAME                0 (d)
#               4 COMPARE_OP               6 (in)
#               6 RETURN_VALUE

dis.dis("d.get('key2')")
#   1           0 LOAD_NAME                0 (d)
#               2 LOAD_METHOD              1 (get)
#               4 LOAD_CONST               0 ('key2')
#               6 CALL_METHOD              1
#               8 RETURN_VALUE

Это показывает, что in Оператор сравнения не просто надежнее, но даже быстрее get(),

Способы, которыми вы можете получить результаты:

  • если your_dict.has_key(key) удален в Python 3
  • если введите your_dict
  • попробуй / кроме блока

Что лучше, зависит от 3 вещей:

  1. Есть ли в словаре "обычно есть ключ" или "обычно нет ключа".
  2. Намереваетесь ли вы использовать такие условия, как если... еще... еще, если... еще?
  3. Насколько большой словарь?

Подробнее: http://paltman.com/try-except-performance-in-python-a-simple-test/

Использование try/block вместо "in" или "if":

try:
    my_dict_of_items[key_i_want_to_check]
except KeyError:
    # Do the operation you wanted to do for "key not present in dict".
else:
    # Do the operation you wanted to do with "key present in dict."

Вы можете использовать метод has_key():

if dict.has_key('xyz')==1:
    #update the value for the key
else:
    pass

Или dict.get метод для установки значения по умолчанию, если не найден:

mydict = {"a": 5}

print mydict["a"]            #prints 5
print mydict["b"]            #Throws KeyError: 'b'

print mydict.get("a", 0)     #prints 5
print mydict.get("b", 0)     #prints 0

Просто добавление к Крису. B (лучший ответ):

d = defaultdict(int)

Работает так же; причина в том, что призыв int() возвращается 0 который является то, что defaultdict делает за кулисами (при создании словаря), отсюда и название "Factory Function" в документации.

Для проверки вы можете использовать has_key() метод

if dict.has_key('key1'):
   print "it is there"

Если вы хотите значение, то вы можете использовать get() метод

a = dict.get('key1', expeced_type)

Если вы хотите, чтобы в качестве значения по умолчанию в качестве значения по умолчанию использовался кортеж, список, словарь или любая строка, используйте get() метод

a = dict.get('key1', {}).get('key2', [])

В словаре Python есть метод __contains__, Этот метод возвращает True, если в словаре есть ключ, иначе возвращается False.

 >>> temp = {}

 >>> help(temp.__contains__)

Help on built-in function __contains__:

__contains__(key, /) method of builtins.dict instance
    True if D has a key k, else False.

Совместное использование еще одного способа проверки наличия ключа с использованием логических операторов.

d = {'a': 1, 'b':2}
keys = 'abcd'

for k in keys:
    x = (k in d and 'blah') or 'boo'
    print(x) 

Это возвращает

>>> blah
>>> blah
>>> boo
>>> boo

объяснение

Сначала вы должны знать, что в Python, 0, Noneили объекты с нулевой длиной оцениваются как False, Все остальное оценивается как True, Булевы операции оцениваются слева направо и возвращают операнд не True или False.

Давайте посмотрим на пример:

>>> 'Some string' or 1/0 
'Some string'
>>>

поскольку 'Some string' оценивает True, остаток от or не оценивается и нет деления на нулевую ошибку.

Но если мы изменим порядок 1/0 оценивается первым и вызывает исключение:

>>> 1/0 or 'Some string'
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ZeroDivisionError: division by zero
>>> 

Мы можем использовать это для шаблона для проверки, существует ли ключ.

(k in d and 'blah')

делает так же, как

if k in d:
    'blah'
else:
    False

Это уже возвращает правильный результат, если ключ существует, но мы хотим, чтобы он печатал 'boo', когда его нет. Итак, мы берем результат и or это с 'boo'

>>> False or 'boo'
'boo'
>>> 'blah' or 'boo'
'blah'
>>> 

print dict.get('key1', 'blah')

Не будет печатать boo для значений в dict, но достигнет цели, напечатав значение key1, чтобы подтвердить его существование.

Чтобы проверить, существует ли данный ключ в словаре, вы должны использовать любой из следующих подходов:

Первый подход (работает в Python 3):

def checkKey(dict, key):    
    if key in dict.keys(): 
        print("Key is here, ", end =" ") 
        print("value =", dict[key]) 
    else: 
        print("Key isn't present.") 

Давайте проверим это:

dict = {'r': 30, 'g':59, 'b':11} 

key = 'b'
checkKey(dict, key) 

key = 'a'
checkKey(dict, key) 

Результат Approach One:

# Key is here, value = 11
# Key isn't present.

Подход второй (работа в Python 3):

def checkKey(dict, key):   
    if key in dict: 
        print("Key is here, ", end =" ") 
        print("value =", dict[key]) 
    else: 
        print("Key isn't present.") 

Давайте проверим это тоже:

dict = {'x': 10, 'y':20, 'z':30} 

key = 'y'
checkKey(dict, key) 

key = 'u'
checkKey(dict, key) 

Результат Approach Two:

# Key is here, value = 20
# Key isn't present.

Подход третий (работа в Python 3):

def checkKey(dict, key):      
    if dict.has_key(key): 
        print "Key is here, value =", dict[key] 
    else: 
        print "Key isn't present."

Давайте проверим это также:

dict = {'u': 0, 'v':1, 'w':2} 

key = 'u'
checkKey(dict, key) 

key = 'm'
checkKey(dict, key)

Результат Approach Three:

# Key is here, value = 0
# Key isn't present.

Надеюсь это поможет.

Вы можете использовать цикл for для ввода каждого элемента в словарь и получения имени, которое вы хотите найти в словаре, после этого проверьте, существует ли он или нет:

dic={‘first’ : 12, ‘second’ : 123}
For each in dic :
If each == ‘second’: 
    Print (‘it is exist’)
else :
     print (‘not exist’)

Хорошо... Вам будет знакомо, что поиск существования элемента в списке или данных означает прохождение всего (по крайней мере, для неупорядоченного списка, например dict.keys). Так что вместо использования исключений и ошибок, которые возникают обычно, мы можем избежать этой сложности...

d={1:'a',2:'b'}
try:
    needed=d[3]
    print(needed)
except:
    print("Key doesnt exist")

Проще всего, если вы знаете, какой ключ (имя ключа) искать:

# suppose your dictionary is
my_dict = {'foo': 1, 'bar': 2}
# check if a key is there
if 'key' in my_dict.keys():   # it will evaluates to true if that key is present otherwise false.
    # do something

или вы также можете сделать просто как:

if 'key' in my_dict:   # it will evaluates to true if that key is present otherwise false.
    # do something

Я использую попробовать / кроме; если выброшено исключение, то ключа нет в словаре. пример:

st = 'sdhfjaks'
d = {}
try:
    print d['st']
except Exception, e:
    print 'Key not in the dictionary'

Почему бы просто не использовать метод has_key().

a = {}
a.has_key('b') => #False

a['b'] = 8
a.has_key('b') => #True
Другие вопросы по тегам