Question

... le mot-clé is qui peut être utilisé pour l'égalité dans les chaînes.

>>> s = 'str'
>>> s is 'str'
True
>>> s is 'st'
False

J'ai essayé à la fois __is__() et __eq__() mais ils ne travaillaient pas.

>>> class MyString:
...   def __init__(self):
...     self.s = 'string'
...   def __is__(self, s):
...     return self.s == s
...
>>>
>>>
>>> m = MyString()
>>> m is 'ss'
False
>>> m is 'string' # <--- Expected to work
False
>>>
>>> class MyString:
...   def __init__(self):
...     self.s = 'string'
...   def __eq__(self, s):
...     return self.s == s
...
>>>
>>> m = MyString()
>>> m is 'ss'
False
>>> m is 'string' # <--- Expected to work, but again failed
False
>>>
Était-ce utile?

La solution

chaînes d'essai avec is ne fonctionne que lorsque les cordes sont internées. Sauf si vous savez vraiment ce que vous faites et explicitement interné les chaînes que vous devriez jamais utilisation is sur les chaînes.

tests is pour identité , pas l'égalité . Cela signifie que Python compare simplement l'adresse mémoire d'un objet réside dans. is répond essentiellement à la question « Dois-je deux noms pour le même objet? » -. Surcharge qui n'a pas de sens

Par exemple, ("a" * 100) is ("a" * 100) est false . En général, Python écrit chaque chaîne dans un autre emplacement de mémoire, interner se produit surtout pour les chaînes littérales.

Autres conseils

L'opérateur is équivaut à comparer des valeurs de id(x). id est actuellement mis en œuvre pour utiliser des pointeurs comme la comparaison. Donc, vous ne pouvez pas la surcharge se is et AFAIK vous ne pouvez pas surcharger id soit.

Alors, vous ne pouvez pas. Inhabituel en python, mais il est.

Le Python is des tests de mots-clés identité objet. Vous ne devriez pas l'utiliser pour tester l'égalité des cordes. Il peut sembler travailler souvent parce que les implémentations Python, comme ceux de plusieurs langues de très haut niveau, effectue « interner » des cordes. C'est-à-dire que les chaînes littérales et valeurs sont conservées en interne dans une liste et celles qui hachée sont identiques sont rendus comme des références au même objet. (Ceci est possible parce que les chaînes Python sont immuables).

Cependant, comme tous les détails de mise en œuvre, vous ne devriez pas compter sur ce point. Si vous voulez tester pour l'égalité l'opérateur ==. Si vous voulez vraiment tester l'identité de l'objet puis utilisez is --- et je serais mal à trouver un cas où vous devriez se soucier de l'identité de l'objet chaîne. Malheureusement, vous ne pouvez pas compter sur si deux chaînes sont en quelque sorte « intentionnellement » références d'objets identiques en raison de l'interner mentionné ci-dessus.

Le mot-clé de is compare des objets (ou plutôt, compare si deux références au même objet).

Ce qui est, je pense, pourquoi il n'y a pas de mécanisme pour fournir votre propre implémentation.

Il arrive parfois à travailler sur les chaînes parce que les chaînes Python magasins « intelligemment », de sorte que lorsque vous créez deux chaînes identiques, ils sont stockés dans un objet.

>>> a = "string"
>>> b = "string"
>>> a is b
True
>>> c = "str"+"ing"
>>> a is c
True

Vous pouvez voir la référence, espérons-vs comparaison des données dans un simple « copie » par exemple:

>>> a = {"a":1}
>>> b = a
>>> c = a.copy()
>>> a is b
True
>>> a is c
False

Si vous n'êtes pas peur de vous embêter avec bytecode, vous pouvez intercepter et COMPARE_OP patch avec l'argument de 8 ("is") d'appeler votre fonction crochet objets comparés. Regardez la documentation du module dis pour le démarrage dans.

Et ne pas oublier d'intercepter __builtin__.id() aussi si quelqu'un va faire id(a) == id(b) au lieu de a is b.

est ne compare pas une variable de chaîne à valeur de chaîne et deux variables de chaîne lorsque la chaîne commence par « - ». Ma version Python est 2.6.6

>>> s = '-hi'
>>> s is '-hi'
False 
>>> s = '-hi'
>>> k = '-hi'
>>> s is k 
False
>>> '-hi' is '-hi'
True

'est' compare l'identité de l'objet alors que == compare les valeurs.

Exemple:

a=[1,2]
b=[1,2]
#a==b returns True
#a is b returns False

p=q=[1,2]
#p==q returns True
#p is q returns True

Vous ne pouvez pas surcharger l'opérateur is. Ce que vous voulez surcharge est l'opérateur ==. Cela peut être fait en définissant une méthode __eq__ dans la classe.

Vous utilisez la comparaison d'identité. == est probablement ce que vous voulez. L'exception à cette règle est lorsque vous voulez être vérifier si un élément et un autre sont le même, l'objet et dans la même position de mémoire. Dans vos exemples, les années d'article ne sont pas les mêmes, puisque l'on est d'un type différent (de my_string) que l'autre (string). En outre, il n'y a pas une telle chose comme someclass.__is__ en python (à moins, bien sûr, vous le mettez-vous là-bas). S'il y avait, en comparant les objets avec ne serait pas fiable pour comparer simplement les emplacements de mémoire.

Quand je rencontrais le mot-clé, il me confond aussi bien. J'aurais pensé que et == sont pas différents. Ils ont produit la même sortie de l'interprète sur de nombreux objets. Ce type d'hypothèse est en fait exactement ce que ... est pour. Il est le python équivalent « Hé, ne confondez pas ces deux objets. Ils sont différents. », Ce qui est essentiellement ce [qui que ce soit qui me redressé] dit. LIBELLEES bien différemment, mais un point == l'autre point.

quelques exemples utiles et un texte à l'aide des différences parfois source de confusion visitez un document à partir de l'hôte de messagerie de python.org écrit par « Danny Yoo "

ou, si c'est hors ligne, utilisez le non cotées pastebin J'ai fait du corps est tout.

au cas où ils, dans certains 20 ou si des lunes bleues (lunes bleues sont un événement réel), sont à la fois vers le bas, je vais citer les exemples de code

###
>>> my_name = "danny"
>>> your_name = "ian"
>>> my_name == your_name
0                #or False
###

###
>>> my_name[1:3] == your_name[1:3]
1    #or True
###

###
>>> my_name[1:3] is your_name[1:3]
0
###

Erreurs Assertion peut facilement se produire avec mot-clé en comparant les objets. Par exemple, les objets a et b peut contenir même valeur et partager la même adresse mémoire. Par conséquent, faire un

>>> a == b

va évaluer à

True

Mais si

>>> a is b

à evalue

False

vous devriez probablement vérifier

>>> type(a)

et

>>> type(b)

Ceux-ci peuvent être différentes et une raison de l'échec.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top