itsource

'_eq__'을(를) 정의하는 유형은 해시할 수 없습니까?

mycopycode 2023. 5. 17. 22:58
반응형

'_eq__'을(를) 정의하는 유형은 해시할 수 없습니까?

프로그램의 파이썬 3.1 포크에 기능을 이식할 때 이상한 버그가 발생했습니다.저는 그것을 다음과 같은 가설로 좁혔습니다.

Python 2.x와 달리 Python 3.x에서는 객체에__eq__method 자동으로 해시할 수 없습니다.

이것이 사실입니까?

다음은 Python 3.1에서 수행되는 작업입니다.

>>> class O(object):
...     def __eq__(self, other):
...         return 'whatever'
...
>>> o = O()
>>> d = {o: 0}
Traceback (most recent call last):
  File "<pyshell#16>", line 1, in <module>
    d = {o: 0}
TypeError: unhashable type: 'O'

후속 질문은 제 개인적인 문제를 어떻게 해결해야 할까요?나는 목표가 있습니다.ChangeTracker저장하는 위치WeakKeyDictionary이는 여러 개체를 가리키며 각 개체에 대해 과거 특정 시점의 피클 덤프 값을 제공합니다.기존 개체가 체크인될 때마다 변경 추적기는 새 피클이 이전 피클과 동일한지 여부를 알려주며, 그 사이에 개체가 변경되었는지 여부를 알려줍니다.문제는 이제 지정된 개체가 라이브러리에 있는지 확인할 수도 없습니다. 이 개체는 해시할 수 없는 개체에 대한 예외를 발생시키기 때문입니다. (왜냐하면 이 개체는__eq__방법).어떻게 하면 해결할 수 있을까요?

예, 정의할 경우__eq__채무 불이행__hash__(즉, 메모리에 있는 개체의 주소를 해시하는 것)이 사라집니다.해싱은 동일성과 일치해야 하기 때문에 중요합니다. 동일한 개체는 동일하게 해싱해야 합니다.

솔루션은 간단합니다. 정의만 하면 됩니다.__hash__정의와 함께__eq__.

http://docs.python.org/3.1/언급/datamodel.html#object.hash 의 이 단락.

재정의하는 클래스인 경우__eq__()의 구현을 유지할 필요가 있습니다.__hash__()부모 클래스에서, 통역사는 이것을 설정에 의해 명시적으로 말해야 합니다.__hash__ = <ParentClass>.__hash__그렇지 않으면 다음의 상속.__hash__()차단될 것입니다, 마치.__hash__없음으로 명시적으로 설정되었습니다.

다음에서 Python 3 설명서를 확인하십시오.

클래스가 정의하지 않는 경우__eq__()방법을 정의해서는 안 됩니다.__hash__()작업을 정의하지만 정의하지 않으면 인스턴스를 해시 가능한 컬렉션의 항목으로 사용할 수 없습니다.

제가 강조합니다.

게으르고 싶다면, 그냥 정의할 수 있는 것처럼 들립니다.__hash__(self)돌아오다id(self):

사용자 정의 클래스는 다음과 같습니다.__eq__()그리고.__hash__()기본적으로 메소드, 메소드를 사용하면 모든 개체가 동일하지 않게 비교됩니다(자신 제외).x.__hash__()돌아온다id(x).

저는 파이썬 전문가는 아니지만, eq-method를 정의할 때 해시-method도 정의해야 한다는 것이 말이 되지 않을까요? (개체의 해시 값을 계산하는)그렇지 않으면 해시 메커니즘은 동일한 개체에 도달했는지 아니면 동일한 해시 값을 가진 다른 개체에 도달했는지 알 수 없습니다.사실, 그 반대입니다. 아마도 당신이 동일하다고 생각하는 객체에 대해 다른 해시 값을 계산하게 될 것입니다.__eq__방법.

그 모르겠습니다만, 그해함불모는만르지겠지는리뭐시수가고라.__hash__아마도?:)

언급URL : https://stackoverflow.com/questions/1608842/types-that-define-eq-are-unhashable

반응형