2017-03-01 6 views
2

나는 이것이 중복되는 것 같지 않습니다. is==특정 사례의 유형을 비교하고 있지만 알려 주시면 질문을 삭제하겠습니다.타입/클래스를 비교할 때 '=='연산자 대신 'is'연산자를 사용하는 것이 안전할까요?

저는 파이썬에서 is 연산자가 실제로 id(type(a))==id(<type>)으로 변환된다는 것을 알고 있습니다. 그러나 지금까지 나는 type(a) is <type>이 예측 가능한 결과를주는 것으로 나타났습니다. 제 질문은 입니다. is 연산자를 사용하면 예기치 않은 결과 인 (예 : 'foo' is strFalse 인 결과)이 생성됩니까? 또는 파이썬은 type 클래스를 예측 가능한 위치에 저장하므로 is은 항상 ==과 동일한 결과를 제공합니까? 나는이 문맥에서 다소 더 읽을 수있는 is을 발견한다.

이 경우는 내가 인데 상속 된 클래스/서브 클래스 (이 경우 isinstance이 적합 할 것임)을 다루지 않은 경우입니다.

+0

'is'를 'id'비교로 생각하지 마십시오. 'a is b'는 'a'와 'b'가 같은 객체 인 경우 'True'로 평가됩니다. 그것이 당신이 찾고있는 것이라면, 그것을 계속 사용하십시오. – user2357112

+1

특히, 메모리 위치는 전적으로 관련이 없습니다. CPython 이외의 다른 Python 구현에서는 식의 중간에서 변경 될 수도 있습니다 ('id'값은 그렇지 않지만). – user2357112

+0

@ user2357112 죄송합니다. 여러 개의 stackoverflow 스레드에서이 설명을 들었습니다. 나는 제한된 상황에서만 그 작업이 동등하다고 생각합니다. –

답변

1

아니요, is을 사용하면 항상 (C) Python에서 제공 한 객체의 주소를 비교합니다. is을 다시 정의 할 필요가 없으므로 항상 동일한 동작을 얻습니다.

이 만약 객체 abtype(a) is type(b) 것이다 항상 반환 True을 사용하여, 자신의 유형으로 동일한 개체가 있습니다. 반대로, type(a) is type(b)이면 형식이 일치한다는 것을 보장합니다. 이제

class MetaFoo(type): 
    def __eq__(self, other): 
     return False 

class Foo(metaclass=MetaFoo): 
    pass 

f1, f2 = Foo(), Foo() 

:

type(f1) == type(f2) 
False 

하지만 :

type(f1) is type(f2) 
True 
사람이 주위에 와서 어리석은 일을한다는 __eq__을 정의하는 경우, 다른 한편으로

==

예기치 않은 결과가 발생할 수 있습니다

사람들은 그런 일을하지 않을 것입니다. 어. 따라서 type(f1) == type(f2)은 아무것도 보증하지 않습니다 (비 내장형 인 경우).

일반적으로 동일한 내용 (설명에 명시된 바와 같음)을 사용하는 경우 is을 사용하는 것이 좋습니다. 동일한 방식으로 동작하도록 설계된 경우 (해당하는 경우 __eq__ 구현하려면 ==을 사용하십시오.

+0

@StefanPochmann 주소 유형? 'is'는 ('id'로 이어집니다) 당신이주는 것을 신경 쓰지 않습니다. 똑같은 방식으로 행동합니다. '=='로 이어지는'__eq__'는 이것이 인스턴스인지, 클래스인지, 메타 클래스인지는 신경 쓰지 않지만 예기치 않은 결과를 가져 오는 이상한 구현을 여전히 가질 수 있습니다. 어쩌면 나는 그 질문을 오해 했는가? 나는 잘 모르겠다. –

+3

음 * 질문에 대한 유형입니다. 그리고 그들을 확인하는 방법. 나는 그가 객체'a'가 타입't'을 가지고 있지만 타입 (a)는't'가'False'를 리턴 할 수 있는지 궁금합니다. –

+1

이 질문에 더 잘 대답하고 있지만 실제로는 그렇지 않습니다. 당신은 * "두 객체 a와 b가 그 객체의 유형과 동일한 객체를 가지고 있다면"* 이야기해야합니다. "두 객체 a와 b가 같은 유형을 가지고 있다면"*에 대해서 이야기해야합니다. –