Словарь Iterating - для dict vs for dict.items()
Когда мы перебираем словарь ниже, каждая итерация возвращает (правильно) ключ, пара значений
for key, value in dict.items():
print "%s key has the value %s" % (key, value)
'some key'
имеет значение 'some value'
(повторяется, однако много раз имеется пара k, v)
Приведенное выше имеет смысл для меня, однако, если мы это сделаем:
for key in dict.items():
print "%s key has the value %s" % (key, value)
("some key", "some value")
имеет значение "some value"
(левый кортеж будет перебирать каждую пару значений ключа, а правое значение останется только при первом значении в dict и повторить)
В результате получаем каждую пару k, v, возвращенную в первом %s
(ключ), а второй %s
(значение) не выполняет итерацию, он просто возвращает первое значение в dict для каждой итерации for цикл.
Я понимаю, что если вы повторяете только for key in dict
, вы выполняете итерацию только по клавишам. Здесь, поскольку мы повторяем набор кортежей (используя dict.items()
) только с ключом в цикле for, цикл должен выполняться в течение того же числа раз, что и первый пример, так как имеется столько ключей, сколько ключ, значение пар.
У меня возникли проблемы с пониманием того, почему python дает вам весь кортеж во втором примере для key
.
Спасибо за помощь всем - я хотел бы добавить еще один вопрос в микс.
for a,a in dict.items():
print a
Почему вышеприведенное значение выдает, а если я print a,a
- очевидно, что оба значения печатаются дважды. Если бы я набрал for a,b
, я бы повторял пары (key,value)
, поэтому я бы логично подумал, что теперь я повторяю пары (key,key)
и поэтому печатаю ключ, а не значение. Извините за основные вопросы, которые просто играют в интерпретаторе и пытаются отобразить материал.
Ответы
Ответ 1
В первом примере используется что-то, известное как "распаковка кортежа", чтобы разбить то, что ДЕЙСТВИТЕЛЬНО такое же кортеж, что и в вашем отдельном примере, на две разные переменные.
Другими словами:
for key, value in dict.items():
Это только:
for keyvalue in dict.items():
key, value = keyvalue[0], keyvalue[1]
Помните, что цикл for
всегда выполняет итерацию по отдельным элементам итератора, которые вы ему даете. dict.items()
возвращает подобный списку объект кортежей, поэтому каждый пробег в цикле for
представляет собой новый кортеж, автоматически распаковываемый в key, value
, если вы определяете его как таковой в цикле for
.
Это может помочь подумать об этом так:
d = {'a':1, 'b':2, 'c':3}
list(d) # ['a', 'b', 'c'] the keys
list(d.keys()) # ['a', 'b', 'c'] the keys
list(d.values()) # [1, 2, 3] the values
list(d.items()) # [('a',1), ('b',2), ('c',3)] a tuple of (key, value)
N.B. что единственная причина, по которой ваш код
for key in dict.items():
print "%s key has value: %s" % (key, value)
Не выбрасывает NameError
, потому что value
уже определен из другого места вашего кода. Поскольку вы не определяете value
где-либо в этом цикле for
, в противном случае это создало бы исключение.
Ответ 2
Во втором примере, который вы указали, вы не присваиваете значение "значение":
Обратите внимание на небольшое изменение здесь:
for key in dict: ##Removed call to items() because we just want the key,
##Not the key, value pair
value = dict[key] # Added this line
print "%s key has the value %s (key, value)
Примечание:
Во втором примере вы можете теперь вызвать dict.keys() или просто dict (ссылка на словарь в цикле for вернет ему ключи). Вызов dict.items() будет конфессионально назначать
key = (,)
вероятно, не то, что вы хотите.