Что означает «self.default = по умолчанию, если по умолчанию используется else type()»?

#python

#python

Вопрос:

Я всегда был .NET-парнем с тех пор, как начал работать (~ 6 лет). Недавно я работаю над проектом с использованием Django, который требует от меня параллельного изучения Python. Много раз я натыкался на код Python, который выглядел простым, но я просто не мог понять. И вот один из них.

 class TypedProperty(object):
    def __init__(self, name, type, default=None):
        self.name = "_"   name
        self.type = type
        self.default = default if default else type()
  

Может кто-нибудь любезно объяснить мне, что делает последняя строка кода?

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

Комментарии:

1. Я думаю, что последняя строка должна иметь отступ, чтобы быть частью метода __init__

2. Похоже на ошибку отступа .. Я предполагаю, что последняя строка должна совпадать с предыдущей (т. Е. с отступом в 8 пробелов).

3. не уверен насчет отступа. Я скопировал код непосредственно из книги «Основные ссылки на Python»

Ответ №1:

a if b else c это условное выражение, которое вычисляет значение, равное a if b , True и c в противном случае. В данном контексте это проверяет, является ли default это «trucy», и в этом случае оно хранится в self.default . В противном случае type создается и запускается новый экземпляр self.default .

Обратите внимание, что у этой реализации есть несколько проблем:

  1. Он использует type в качестве имени переменной, затеняя встроенную type() . Это считается плохим стилем.

  2. Он использует условие, if default где на самом деле if default is None должно использоваться. Проверка предназначена для проверки, действительно ли параметр default был передан конструктору. Как бы то ни было, реализация не примет никакого значения по умолчанию, которое равно False .

Комментарии:

1. 1 Другие «ложные» значения включают нули, пустые строки и пустые коллекции. Поэтому обычно лучше использовать if arg is not None: x = default , если вы точно не знаете, что хотите их исключить.

Ответ №2:

В сигнатуре функции, которую вы видите default=None — это означает, что если третий аргумент не передан, он default будет равен None .

Эта последняя строка наивно проверяет, имеет ли default значение true, чтобы определить, было ли передано значение по умолчанию. Если default значение true, то self.default ему будет присвоено значение. В противном случае self.default устанавливается значение экземпляра type , переданного в.

Я говорю наивно, потому что default может быть 0 , или это может быть False , или (что более вероятно) это может быть объект, но этот объект каким-то образом принимает значение False . Я бы предпочел

 self.default = default if default is not None else type()
  

Или, чтобы избежать условного выражения, которое я не нахожу самым понятным в мире

 if default is None:
    self.default = type()
else:
    self.default = default
  

Комментарии:

1. 1 Я бы лично написал это как self.default = default if (default is not None) else type() несмотря на то, что круглые скобки избыточны, это менее подробно, чем 4-строчная версия, но немного более читабельно, чем 1-строчная без скобок в скобках.

Ответ №3:

Это троичный оператор Python (он же условное выражение) в действии! То, что Python лениво вычисляет логические значения, ничего не стоит, поэтому в этом случае:

 self.default = default if default else type()
  

Эквивалентно этому:

 self.default = default or type()
  

Если default вычисляется какое-либо значение, отличное от False, будет использовано его значение, в противном случае оно перейдет к type() .