Около list
Сначала очень важный момент, из которого все будет следовать (надеюсь).
В обычном Python listон не является чем-то особенным (за исключением симпатичного синтаксиса для построения, что в большинстве случаев является исторической случайностью). После того, как список [3,2,6]составлен, он для всех целей и задач является просто обычным объектом Python, например числом 3, набором {3,7}или функцией lambda x: x+5.
(Да, он поддерживает изменение своих элементов, поддерживает итерацию и многое другое, но это именно то, что представляет собой тип: он поддерживает одни операции, но не поддерживает некоторые другие. Int поддерживает возведение в степень, но это не сделайте его особенным - это то, что такое int. лямбда поддерживает вызов, но это не делает его особенным - в конце концов, лямбда для этого нужна :).
Около and
andне является оператором (вы можете называть его оператором, но вы также можете позвонить «за» оператору :). Операторы в Python - это (реализованные посредством) методы, вызываемые для объектов определенного типа, обычно записываемые как часть этого типа. У метода нет способа провести оценку некоторых из своих операндов, но он andможет (и должен) это делать.
Следствием этого является andневозможность перегрузки, как и forневозможность перегрузки. Он является полностью общим и обменивается данными по указанному протоколу. Вы можете настроить свою часть протокола, но это не значит, что вы можете полностью изменить его поведение and. Протокол:
Представьте, что Python интерпретирует «a и b» (это не происходит буквально таким образом, но помогает понять). Когда дело доходит до «и», он смотрит на объект, который только что оценил (а), и спрашивает его: вы правы? ( НЕ : а True?) Если вы являетесь автором класса, вы можете настроить этот ответ. Если aответ «нет» and(полностью пропускает b, он вообще не оценивается, и) говорит: aэто мой результат ( НЕ : Ложь - мой результат).
Если aне отвечает, andспрашивает: какой у тебя длина? (Опять же, вы можете настроить это как автор aкласса). Если aотвечает 0, andделает то же, что и выше - считает ложным ( НЕ Ложным), пропускает b и дает aрезультат.
Если aна второй вопрос («какова ваша длина») ответит что-то иное, чем 0, или он не отвечает вообще, или он отвечает «да» на первый («правда ли вы?»), andОценивает b и говорит: bэто мой результат. Обратите внимание, что он НЕ задает bникаких вопросов.
Другой способ сказать, что все это a and bпочти то же самое b if a else a, за исключением того, что a оценивается только один раз.
Теперь посидите несколько минут с ручкой и бумагой и убедитесь, что когда {a, b} является подмножеством {True, False}, это работает точно так, как вы ожидаете от логических операторов. Но я надеюсь, что убедил вас, что это гораздо более общий и, как вы увидите, гораздо более полезный способ.
Собираем эти двое вместе
Теперь я надеюсь, что вы понимаете ваш пример 1. andМне все равно, является ли mylist1 числом, списком, лямбда-выражением или объектом класса Argmhbl. Его просто волнует ответ mylist1 на вопросы протокола. И, конечно же, mylist1 отвечает 5 на вопрос о длине, поэтому и возвращает mylist2. Вот и все. Это не имеет ничего общего с элементами mylist1 и mylist2 - они никуда не входят в картинку.
Второй пример: &наlist
С другой стороны, &это такой же оператор, как и любой другой, например, как +. Его можно определить для типа, определив специальный метод для этого класса. intопределяет его как побитовое «and», а bool определяет его как логическое «and», но это только один вариант: например, наборы и некоторые другие объекты, такие как представления ключей dict, определяют его как пересечение наборов. listпросто не дает ему определения, вероятно, потому, что Гвидо не придумал никакого очевидного способа его определения.
тупой
На другой ноге: -D, Numpy массивы являются специальными, или , по крайней мере , они пытаются быть. Конечно, numpy.array - это просто класс, он не может переопределить andкаким-либо образом, поэтому он делает следующее лучшее: когда его спрашивают «правда ли?», Numpy.array вызывает ValueError, эффективно говоря: «Пожалуйста, перефразируйте вопрос, мой взгляд на истину не вписывается в вашу модель ». (Обратите внимание, что сообщение ValueError не говорит о and- потому что numpy.array не знает, кто задает ему вопрос; он просто говорит об истине.)
Ведь &это совсем другая история. numpy.array может определять его по своему усмотрению, и он определяется &согласованно с другими операторами: точечно. Итак, вы наконец получили то, что хотите.
HTH,
np.bitwise_and()иnp.logical_and()и друзей , чтобы избежать путаницы.