Existe alguma diferença entre:
if foo is None: pass
e
if foo == None: pass
A convenção que eu já vi na maioria dos códigos Python (e no código que eu mesmo escrevo) é a primeira, mas recentemente me deparei com um código que usa a segunda. Nenhuma é uma instância (e a única instância, IIRC) de NoneType; portanto, isso não importa, certo? Existem circunstâncias em que isso possa acontecer?
is
operador não pode ser personalizado (sobrecarregado por uma classe definida pelo usuário).__eq__(self)
é um método interno especial que determina como==
é tratado quando usado em um objeto Python. Aqui nós o substituímos para que, quando==
usado em objetos do tipo,Foo
ele sempre retorne verdadeiro. Não existe um método equivalente para ois
operador e, portanto, o comportamento deis
não pode ser alterado da mesma maneira.Você pode querer ler essa identidade e equivalência do objeto .
A declaração 'is' é usada para a identidade do objeto, verifica se os objetos se referem à mesma instância (mesmo endereço na memória).
E a instrução '==' refere-se à igualdade (mesmo valor).
fonte
a=1;b=1;print(a is b) # True
. Alguma idéia de por quea is b
acaba sendo verdade mesmo que pareçam ser dois objetos diferentes (endereço diferente na memória)?Uma palavra de cautela:
Não é exatamente o mesmo que:
O primeiro é um teste de valor booleano e pode ser avaliado como falso em diferentes contextos. Existem várias coisas que representam false em um teste de valor booleano, por exemplo, contêineres vazios, valores booleanos. Nenhum também é avaliado como falso nessa situação, mas outras coisas também.
fonte
(ob1 is ob2)
igual a(id(ob1) == id(ob2))
fonte
is
versão não precisa de chamada de função e nenhuma pesquisa de atributo do interpretador python; o intérprete pode responder imediatamente se ob1 é, de fato, ob2.{} is {}
é falso eid({}) == id({})
pode ser (e está no CPython) verdadeiro. Veja stackoverflow.com/questions/3877230O motivo
foo is None
é a maneira preferida: você pode estar manipulando um objeto que define o seu próprio__eq__
e que define o objeto como sendo igual a Nenhum. Portanto, sempre usefoo is None
se precisar ver se ele está de fatoNone
.fonte
Não há diferença porque objetos idênticos serão obviamente iguais. No entanto, o PEP 8 afirma claramente que você deve usar
is
:fonte
is
testes de identidade, não de igualdade. Para sua declaraçãofoo is none
, o Python simplesmente compara o endereço de memória dos objetos. Isso significa que você está fazendo a pergunta "Eu tenho dois nomes para o mesmo objeto?"==
por outro lado, testa a igualdade conforme determinado pelo__eq__()
método. Não se importa com identidade.None
é um operador singleton. EntãoNone is None
é sempre verdade.fonte
Para Nenhum, não deve haver diferença entre igualdade (==) e identidade (é). O NoneType provavelmente retorna identidade para igualdade. Como None é a única instância que você pode fazer de NoneType (acho que isso é verdade), as duas operações são iguais. No caso de outros tipos, esse nem sempre é o caso. Por exemplo:
Isso imprimiria "Igual", pois as listas têm uma operação de comparação que não é o retorno padrão da identidade.
fonte
@ Jason :
Não gosto de usar "if foo:", a menos que foo realmente represente um valor booleano (ou seja, 0 ou 1). Se foo for uma string, um objeto ou outra coisa, "if foo:" pode funcionar, mas me parece um atalho preguiçoso. Se você estiver verificando se x é Nenhum, diga "se x é Nenhum:".
fonte
if foo
, retornará falso e o comentário#foo is None
está errado.Mais alguns detalhes:
A
is
cláusula realmente verifica se os doisobject
s estão no mesmo local de memória ou não. ou seja, se ambos apontam para o mesmo local de memória e têm o mesmoid
.Como consequência de 1,
is
garante se os doisobject
s representados lexicamente têm ou não atributos idênticos (atributos-de-atributos ...) ou nãoInstanciação de tipos primitivos, como
bool
,int
,string
(com algumas excepções),NoneType
tendo um mesmo valor será sempre no mesmo local de memória.Por exemplo
E como
NoneType
só pode ter uma instância na tabela de "pesquisa" do python, a primeira e a segunda são mais um estilo de programação do desenvolvedor que escreveu o código (talvez por consistência), em vez de ter qualquer razão lógica sutil para escolha um sobre o outro.fonte
some_string is "bar"
para comparar SEMPRE. Não há uma única razão aceitável para fazê-lo e ele vai quebrar quando você não espera. O fato de que ele funciona com freqüência é simplesmente porque o CPython sabe que seria estúpido criar dois objetos imutáveis com o mesmo conteúdo. Mas isso pode acontecer mesmo assim.int
, certo?A conclusão de John Machin que
None
é um singleton é uma conclusão reforçada por esse código.Uma vez que
None
é um singleton,x == None
ex is None
teria o mesmo resultado. No entanto, na minha opinião estética,x == None
é melhor.fonte
None
objeto. Por comparação, raramente se vê Nenhum usado em qualquer outro contexto, exceto para ser semelhante ao fato deFalse
outros valores serem verdadeiros. Nesses casos, é mais idiomático fazer algo comoif x: pass
fonte