Здесь вам нужно понять две вещи. Во-первых:
x or y
Если x
правдиво, оно имеет значение x
(даже не оценивая y
, поэтому 23 or launch_nukes()
не запускает ядерное оружие).
В противном случае оно имеет значение y
.
Или, как , docs положил его:
Выражение
x or y
сначала оценивает x ; если x истинно, возвращается его значение; в противном случае y оценивается и возвращается возвращаемое значение.Обратите внимание, что здесь используется слово «true», а не значение
True
. Это немного запутанно (тем более, если вы говорите вслух или печатаете в ASCII без форматирования ...), поэтому каждый говорит «правдивый».Итак, что делать, истина "и" ложь "означают? 1
- « x правдиво »означает не среднее значение
x == True
, это означаетbool(x) == True
.- «x является ложным» означает, что не означает
x == False
, это означаетbool(x) == False
.Для всех типов builtin и stdlib:
False
ложно.None
ложно.- Числовые значения нуля ложны.
- Пустые контейнеры ложны.
- Все остальное правдиво.
Обратите внимание, что
None
и пустые контейнеры ложны, но они не равныFalse
.По соглашению сторонние типы (включая типы, которые вы определяете2) должны следовать тем же правилам. Но иногда есть веские причины не делать этого. (Например, массив NumPy не является ни правдоподобным, ни ложным.3)
Это слабо описано в в той же секции docs :
In контекст булевых операций, а также когда выражения используются операторами управления потоком, следующие значения интерпретируются как ложные: False, None, numeric zero всех типов и пустые строки и контейнеры (включая строки, кортежи, списки, словари, наборы и фризонсет). Все остальные значения интерпретируются как истинные. Пользовательские объекты могут настраивать свое значение истины, предоставляя метод
__bool__()
.Точные детали для всех встроенных типов похоронены в иерархии стандартного типа , в котором вы узнаете, как
bytes
покрывается «строками и контейнерами» (да) или есть ли что-то особенное вNotImplemented
(нет, это правда).Итак, давайте рассмотрим ваши примеры:
[1, 2] or ["hello"]
Поскольку
[1, 2]
является непустым контейнером, он правдивый. Таким образом, это равно[1, 2]
.[] or ["hello"]
Поскольку
[]
является пустым контейнером, он является ложным. Таким образом, это равно["hello"]
.[] == False
[]
может быть ложным, но это неFalse
или даже равноFalse
. Только числа, равные другим номерам, аFalse
- число 0 в числовом типеbool
, 4, но[]
не является числом. Итак, этоFalse
.Просто будь рад, что вы не спросили о
is
. :)1. Технически эти термины не определены, хотя каждый, даже разработчики ядра, использует их все время. Официальная ссылка определяет вещи в терминах оценки true или false как булева, а затем объясняет, что это значит в другом месте.
2. Вы можете контролировать правильность значений ваших типов, определяя метод
__bool__
, или определяя__len__
. Единственное, что вам разрешено делать, это вернутьсяTrue
, вернутьFalse
или вызвать исключение; если вы пытаетесь вернуть что-то другое, оно вызываетTypeError
. Итак, все либо правдиво, либо ложно, либо непроверяется.3. Если вы попытаетесь проверить его правдивость, это вызовет исключение. Это потому, что NumPy широко использует булевы массивы, например,
array([1, 2]) < array([2, 1])
-array([True, False])
, и вы не хотите, чтобы люди писалиif array([1, 2]) < array([2, 1]):
, поскольку все, что они ожидают, вероятно, не имеет смысла.4. Да,
bool
является числовым типом - по сути, подклассомint
. Это немного странно, когда вы впервые изучаете, но оказывается полезным чаще, чем это опасно, поэтому по историческим причинам это не , а только .
Вам нужно создать переменную
var leftCon:NSLayoutConstraint!
, а затем изменить ее, проблема в том, что каждая строка создает новое ограничение
sparkleView.widthAnchor.constraint(equalToConstant: frame.width / 5).isActive = true
sparkleView.leftAnchor.constraint(equalTo: leftAnchor).isActive = true
sparkleView.rightAnchor.constraint(equalTo: self.rightAnchor).isActive = true
примечание: выше 3 ограничений создают конфликт, поскольку представление не может быть закреплено влево и вправо одновременно с ограничением ширины, поэтому вы видите конфликт перерыв => NSLayoutConstraint: 0x6000020b8eb0 UIView: 0x7fc846d551d0.width == 15.35 (активный)
blockquote >независимо от активного назначения, поэтому эти
sparkleView.leftAnchor.constraint(equalTo: leftAnchor).priority = UILayoutPriorityDefaultLow // Doesn't work sparkleView.leftAnchor.constraint(equalTo: leftAnchor).isActive = false // Doesn't work
находятся на лету и не изменяют созданное ограничение, так что это будет
leftCon = sparkleView.leftAnchor.constraint(equalTo: leftAnchor) leftCon.isActive = true
Относительно этого crash
'Изменение приоритета от обязательного к отсутствию установленного ограничения (или наоборот) не поддерживается
blockquote>вам необходимо установить приоритет перед активацией
leftCon.priority = UILayoutPriorityDefaultLow leftCon.isActive = true