В комментарии к этому вопросу я видел оператор, который рекомендовал использовать
result is not None
по сравнению с
result != None
Я задавался вопросом, что различие, и почему можно было бы быть рекомендован по другому?
==
является тестом на равенство. Он проверяет, являются ли правая и левая стороны равными объектами (в соответствии с их методами __eq__
или __cmp__
)
is
является тестом на идентичность. Он проверяет, являются ли правая и левая стороны одним и тем же объектом. Методы не выполняются, объекты не могут влиять на работу is
.
Вы используете is
(и is not
) для синглетов, как None
, где вас не волнуют объекты, которые могут притворяться None
, или где вы хотите защитить от взлома при сравнении с None
.
Для решения вопроса 2 Java может быть немного болевым в обработке чисел с плавающей запятой, но он стал намного лучше, чем версии 1.5 и 1.6. При переходе по пути Java убедитесь в наличии последней доступной версии.
Соответствующие вопросы достаточно хорошо объясняются в этой статье: http://www.ibm.com/developerworks/java/library/j-math2.html .
-121--3049980-Я не думаю, что это может быть сделано без неконтролируемого кастинга где-то. Вам понадобится нечто подобное экзистенциальным типам Хаскелла , которых нет в Java.
Вместо этого клиент может выполнить бесконтрольный кастинг...
synchronized public static <V> FieldBinder<V>
getInstance(Class<V> klass, Class<FieldBinder<V>> binderKlass) {
if(!instanceMap.containsKey(klass)) {
instanceMap.put(klass, new FieldBinder<V>());
}
return binderKlass.cast(instanceMap.get(klass));
}
Если клиент передает метод Class < StartBinder < V > >
методу getInstance ()
, можно избежать отсутствия флажка в getInstance ()
.
К сожалению, создавая Класс
сам требует незарегистрированного броска.
Class<FieldBinder<Integer>> binderKlass =
(Class<FieldBinder<Integer>>) (Class<?>) FieldBinder.class;
BinderAssociator.getInstance(Integer.class, binderKlass);
-121--2611318- Нет
является одиночным, поэтому сравнение идентичности всегда будет работать, тогда как объект может подделать сравнение равенства через . _ _ eq _ _ ()
.
>>> () is () True >>> 1 is 1 True >>> (1,) == (1,) True >>> (1,) is (1,) False >>> a = (1,) >>> b = a >>> a is b True
Некоторые объекты являются одиночными, поэтому равно
с ними, что эквивалентно ==
. Большинство нет.
Примите во внимание следующее:
class Bad(object):
def __eq__(self, other):
return True
c = Bad()
c is None # False, equivalent to id(c) == id(None)
c == None # True, equivalent to c.__eq__(None)
Во-первых, позвольте мне остановиться на нескольких терминах. Если вы просто хотите получить ответ на свой вопрос, прокрутите вниз до «Ответить на ваш вопрос».
Идентификатор объекта : Когда вы создаете объект, вы можете назначить его переменной. Затем вы также можете присвоить его другой переменной. И другой.
>>> button = Button()
>>> cancel = button
>>> close = button
>>> dismiss = button
>>> print(cancel is close)
True
В этом случае cancel
, close
и dismiss
все относятся к одному и тому же объекту в памяти. Вы создали только один объект Button
, и все три переменные относятся к этому одному объекту. Мы говорим, что cancel
, close
и dismiss
все относятся к идентичным объектам; то есть они относятся к одному единственному объекту.
Равенство объектов : Когда вы сравниваете два объекта, вас обычно не волнует, что они ссылаются на точный тот же объект в памяти. С помощью равенства объектов вы можете определить свои собственные правила сравнения двух объектов. Когда вы пишете if a == b:
, вы, по сути, говорите if a .__ eq __ (b):
. Это позволяет вам определить метод __ eq __
на a
, чтобы вы могли использовать свою собственную логику сравнения.
Обоснование: Два объекта имеют одинаковые данные, но не идентичны. (Это не один и тот же объект в памяти.) Пример: Строки
>>> greeting = "It's a beautiful day in the neighbourhood."
>>> a = unicode(greeting)
>>> b = unicode(greeting)
>>> a is b
False
>>> a == b
True
Примечание: я использую здесь строки Unicode, потому что Python достаточно умен, чтобы повторно использовать обычные строки без создания новых в памяти .
Здесь у меня есть две строки Unicode, a
и b
. У них одинаковое содержимое, но они не являются одним и тем же объектом в памяти. Однако, когда мы сравниваем их, мы хотим, чтобы они сравнивались как равные. Здесь происходит то, что объект unicode реализовал метод __ eq __
.
class unicode(object):
# ...
def __eq__(self, other):
if len(self) != len(other):
return False
for i, j in zip(self, other):
if i != j:
return False
return True
Примечание: __ eq __
в unicode
определенно реализован более эффективно, чем это.
Обоснование: Два объекта имеют разные данные, но считаются одним и тем же объектом, если некоторые ключевые данные совпадают. Пример: Большинство типов данных модели
>>> import datetime
>>> a = Monitor()
>>> a.make = "Dell"
>>> a.model = "E770s"
>>> a.owner = "Bob Jones"
>>> a.warranty_expiration = datetime.date(2030, 12, 31)
>>> b = Monitor()
>>> b.make = "Dell"
>>> b.model = "E770s"
>>> b.owner = "Sam Johnson"
>>> b.warranty_expiration = datetime.date(2005, 8, 22)
>>> a is b
False
>>> a == b
True
Здесь , У меня есть два монитора Dell, a
и b
. У них одна и та же марка и модель. Однако они не имеют одинаковых данных и не являются одним и тем же объектом в памяти. Однако, когда мы сравниваем их, мы хотим, чтобы они сравнивались как равные. Здесь происходит то, что объект Monitor реализовал метод __ eq __
.
class Monitor(object):
# ...
def __eq__(self, other):
return self.make == other.make and self.model == other.model
При сравнении с Нет
, всегда использовать не
. В Python нет синглтона - в памяти всегда есть только один его экземпляр.
Сравнивая идентичность , это может быть выполнено очень быстро.Python проверяет, имеет ли объект, на который вы ссылаетесь, тот же адрес памяти, что и глобальный объект None - очень и очень быстрое сравнение двух чисел.
Сравнивая равенство ,Python должен проверить, есть ли у вашего объекта метод __ eq __
. В противном случае он проверяет каждый суперкласс в поисках метода __ eq __
. Если он его находит, Python вызывает его. Это особенно плохо, если метод __ eq __
работает медленно и не возвращается сразу же, когда замечает, что другой объект - None
.
Разве вы не реализовали __ eq __
? Тогда Python, вероятно, найдет метод __ eq __
на объекте
и воспользуется им вместо него, который в любом случае просто проверяет идентичность объекта.
При сравнении большинства других вещей в Python вы будете использовать ! =
.