No exemplo, x is zretorna False. Mas se x e z forem atribuídos aos mesmos valores em vez de listas (por exemplo x, z = 13, 13), então x is zretorna True. Por que é que?
Bill
12
@Bill: Esse é um artefato de como o python lida com ints. Python aloca objetos inteiros para os quais xe zapontam. Uma vez que pequenos inteiros são comuns a falhas (-1 como um valor de erro, 0 sempre que você realmente indexar algo, pequenos números geralmente são valores padrão razoáveis) Python otimiza pré-alocando pequenos números (-5 a 256) e reutiliza o mesmo objeto inteiro. Portanto, seu exemplo só funciona para números neste intervalo. Tente atribuir algo maior, ou seja 270. Para mais informações olhada aqui
ted
1
@AndresR Não, isso está errado. isverifica se dois nomes fazem referência ao mesmo local de memória. Não tem nada a ver com o próprio objeto. É fácil ter objetos imutáveis, como strings iguais, mas não armazenadas no mesmo local, por exemplo, ''a'*10000 is 'a' * 10000é False.
Jochen Ritzel de
1
@JochenRitzel Você está totalmente certo, obrigado por este comentário! Então, eu não entendo o que está acontecendo com "af" is "af"ou () is ()... por que eles compartilham o mesmo local de memória?
AndresR de
2
@AndreasR Para strings / números literais no código, o compilador verifica se eles existem apenas uma vez e os reutiliza. Valores especiais como (), None, True, False etc também são definidos como singletons. Durante a execução, o tempo de execução também tenta reutilizar pequenos números e strings, mas no final é uma troca entre velocidade e memória e o que acontece depende de como o tempo de execução do Python foi implementado.
Enquanto as duas soluções corretas x is ze id(x) == id(z)já foram postadas, quero ressaltar um detalhe de implementação de python. Python armazena inteiros como objetos, como uma otimização, ele gera um monte de pequenos inteiros em seu início (-5 a 256) e aponta CADA variável que contém um inteiro com um pequeno valor para esses objetos pré-inicializados. Mais informações
Isso significa que para objetos inteiros inicializados com os mesmos pequenos números (-5 a 256), verificar se dois objetos são iguais retornará verdadeiro ( ON C-Pyhon , pelo que estou ciente, este é um detalhe de implementação ), enquanto para maiores números, isso só retorna verdadeiro se um objeto for inicializado do outro.
> i =13> j =13> i is j
True> a =280> b =280> a is b
False> a = b
> a
280> a is b
True
A nota de @ ted sobre o uso de id é bastante relevante aqui.
Leo Ufimtsev
2
Eu realmente gosto de ter um feedback visual, é por isso que às vezes apenas abro http://www.pythontutor.com/visualize.html#mode=edit para ver como a memória está alocada e o que está referenciando o quê.
Adicionado este gif incrível, pois esta resposta é sobre visualização.
Isso é de docs.python.org: "Cada objeto tem uma identidade, um tipo e um valor. A identidade de um objeto nunca muda depois de ser criado; você pode considerá-lo como o endereço do objeto na memória. O operador 'é' compara a identidade de dois objetos; a função id () retorna um número inteiro que representa sua identidade. "
Aparentemente, toda vez que você altera o valor, o objeto é recriado conforme indicado pela alteração da identidade. A linha x = 3 seguida pela linha x = 3,14 não dá nenhum erro e dá diferentes identidades, tipos e valores para x.
Respostas:
Isso
is
é para quê :x is y
retornaTrue
sex
ey
forem o mesmo objeto.fonte
x is z
retornaFalse
. Mas se x e z forem atribuídos aos mesmos valores em vez de listas (por exemplox, z = 13, 13
), entãox is z
retornaTrue
. Por que é que?x
ez
apontam. Uma vez que pequenos inteiros são comuns a falhas (-1 como um valor de erro, 0 sempre que você realmente indexar algo, pequenos números geralmente são valores padrão razoáveis) Python otimiza pré-alocando pequenos números (-5 a 256) e reutiliza o mesmo objeto inteiro. Portanto, seu exemplo só funciona para números neste intervalo. Tente atribuir algo maior, ou seja270
. Para mais informações olhada aquiis
verifica se dois nomes fazem referência ao mesmo local de memória. Não tem nada a ver com o próprio objeto. É fácil ter objetos imutáveis, como strings iguais, mas não armazenadas no mesmo local, por exemplo,''a'*10000 is 'a' * 10000
é False."af" is "af"
ou() is ()
... por que eles compartilham o mesmo local de memória?y is x
seráTrue
,y is z
seráFalse
.fonte
Enquanto as duas soluções corretas
x is z
eid(x) == id(z)
já foram postadas, quero ressaltar um detalhe de implementação de python. Python armazena inteiros como objetos, como uma otimização, ele gera um monte de pequenos inteiros em seu início (-5 a 256) e aponta CADA variável que contém um inteiro com um pequeno valor para esses objetos pré-inicializados. Mais informaçõesIsso significa que para objetos inteiros inicializados com os mesmos pequenos números (-5 a 256), verificar se dois objetos são iguais retornará verdadeiro ( ON C-Pyhon , pelo que estou ciente, este é um detalhe de implementação ), enquanto para maiores números, isso só retorna verdadeiro se um objeto for inicializado do outro.
fonte
Você também pode usar id () para verificar a qual objeto único cada nome de variável se refere.
fonte
Eu realmente gosto de ter um feedback visual, é por isso que às vezes apenas abro http://www.pythontutor.com/visualize.html#mode=edit para ver como a memória está alocada e o que está referenciando o quê.
Adicionado este gif incrível, pois esta resposta é sobre visualização.
fonte
Isso é de docs.python.org: "Cada objeto tem uma identidade, um tipo e um valor. A identidade de um objeto nunca muda depois de ser criado; você pode considerá-lo como o endereço do objeto na memória. O operador 'é' compara a identidade de dois objetos; a função id () retorna um número inteiro que representa sua identidade. "
Aparentemente, toda vez que você altera o valor, o objeto é recriado conforme indicado pela alteração da identidade. A linha x = 3 seguida pela linha x = 3,14 não dá nenhum erro e dá diferentes identidades, tipos e valores para x.
fonte