user1902689
user1902689

Reputation: 1775

How to achieve strongly typed integers in Python

I don't think that I like that the following is True. I understand that's the case because NewType is only examined by the static checker, and ignored at runtime. If I want it to be False, what's the best way to do that? Make a @dataclass with a single field like "value", take the performance hit, and write the forwarding functions that you want to have available?

from typing import NewType
A = NewType("A", int)
B = NewType("B", int)
print(A(1) == B(1))

What I'm doing right now is:

from dataclasses import dataclass

@dataclass
class Integer:
   value: int

@dataclass
class A(Integer):
   pass

@dataclass
class B(Integer):
   pass

This prevents the classes from being compared, but certainly has a performance hit. I tried inheriting from int, but that way it does say A(1) == B(1) is True.

Upvotes: 1

Views: 649

Answers (1)

Connor Nicholson
Connor Nicholson

Reputation: 51

Subclass int and override __eq__ (and other methods like __add__, if appropriate).

class A(int):
   def __eq__(self, other):
     return isinstance(other, A) and super().__eq__(other)
 
 class B(int):
   def __eq__(self, other):
     return isinstance(other, B) and super().__eq__(other)
>>> A(2) == B(2)
False
>>> A(2) == A(2)
True
>>> A(2) == A(3)
False

The __eq__ operator does not inherently need to return False if the two objects are different types. If you want that behavior, you'll have to specify that by adding it like above.

Upvotes: 2

Related Questions