2012-03-18 3 views

ответ

17

Как и в любом вызове функции, аргументы оцениваются до выполнения вызова.
В этом случае dict.get() не исключение ...

+2

+1 - Дзен python: «Особые случаи не являются достаточно сложными, чтобы нарушать правила». – Sake

+0

+1 zen of python – Doboy

+0

Это должен быть принятый ответ. –

3

Поскольку вы оцениваете его, а затем передать его в качестве аргумента get. Это происходит независимо от того, заканчивается ли get с использованием аргумента.

0
  1. a[key] является a['foo'] и у вас нет этого ключа в a.
  2. это вычисляется перед вызовом b.get поэтому ошибка
  3. «даже если ключ находится в словаре» - это anot правда, b пусто (но как 2. точек показывает, что это не имеет отношения)
6

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

b.get(key, a.get(key)) 

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

try: 
    x = b[key] 
except KeyError: 
    x = a[key] # or whatever the default value is supposed to be 
5

использовать это вместо

x = b.get(key) or a.get(key) 

or и and короткие операторы цепи, так что если b имеет ключ это не будет смотреть на a. Но проблемы возникнут, если у вас есть falsy значений в b. Если это так, вы можете сделать ..

x = b[key] if key in b else b.get(a) 
1

Чтобы избежать поиск вы можете:

value = b.get(key) 
if value is None: 
    value = a[key] 

Или, если None разрешено, то:

not_set = object() 
# ... 
value = b.get(key, not_set) 
if value is not_set: 
    value = a[key] 
+0

Что делать, если в '# ...' пользователь делает 'b [not_set] = 1'. {trollface} – Doboy

+0

@Doboy: ничего не происходит. 'not_set' - специальное значение, а не ключ. – jfs

+0

Я имею в виду .. 'b [1] = not_set' – Doboy

Смежные вопросы