Python的预初始化方法是__new__
:
无法在冻结的数据类上设置属性,因此我在这里使用了一个命名元组。
from collections import namedtuple
_WithString = namedtuple("WithString", ["stringattr"])
class WithString:
def __new__(cls, input_string):
return _WithString(input_string.lower())
string_1 = WithString("TEST")
string_2 = WithString("test")
print("instances:", string_1, string_2)
print("attributes:", string_1.stringattr, string_2.stringattr)
print("compare instances:", string_1 == string_2)
print("compare attributes:", string_1.stringattr == string_2.stringattr)
输出:
instances: WithString(stringattr='test') WithString(stringattr='test')
compare instances: True
你也可以在 __init__
中这样做:
相同的行为,但这次使用数据类。你需要绕过冻结属性:
from dataclasses import dataclass
@dataclass(frozen=True)
class WithString:
stringattr: str
def __init__(self, input_string):
object.__setattr__(self, "stringattr", input_string.lower())
string_1 = WithString("TEST")
string_2 = WithString("test")
print("instances:", string_1, string_2)
print("compare instances:", string_1 == string_2)
输出:
instances: WithString(stringattr='test') WithString(stringattr='test')
compare instances: True
或者只需覆盖str
生成的对象的行为很像字符串,也可以与字符串进行比较。
class CaseInsensitiveString(str):
def __eq__(self, other):
try:
return self.lower() == other.lower()
except AttributeError:
return NotImplemented
string_1 = CaseInsensitiveString("TEST")
string_2 = CaseInsensitiveString("test")
actual_string = "Test"
print("instances:", string_1, string_2)
print("compare instances:", string_1 == string_2)
print("compare left:", string_1 == actual_string)
print("compare right:", actual_string == string_1)
输出:
instances: TEST test
compare instances: True
compare left: True
compare right: True
pre_init
- 一种在__init__
和__new__
之前被调用的方法。请查看此处以获取更多信息: https://spyhce.com/blog/understanding-new-and-init - baldermanclass Name(NamedTuple): name: str def __init__(self, name: str) -> None: def canonical_representation() -> str: return name.lower() self.name: str = canonical_representation()
会出现以下错误:File "C:\Users\laarpjljvd\AppData\Local\Programs\Python\Python39\lib\typing.py", line 1775, in __new__ raise AttributeError("Cannot overwrite NamedTuple attribute " + key)
- Pierre van de Laar