我要怎么修改一个被导入的类?
我用python制作了一个指针类,只要将这个类作为第一个类继承,类型类作为第二个类继承,就可以实现有语法提示的指针,但现在有一个问题,我在实例化的时候用type函数重新生成了一个类,导致这个类的实例类型不等于这个类,我要怎么办?
Pointer
def fun_(_fun_): def fun__(self_, *args_, **kwargs_): return _fun_(self_.__value__, *args_, **kwargs_) return fun__ class Pointer: __TypePointer = {} __dir = ['__class__', '__new__', '__init__', '__getattribute__', '__setattr__'] def __new__(cls, *args, **kwargs): bases = cls.__bases__ if bases[0] != Pointer: raise TypeError('Pointer需要作为第一个被继承的父类') if len(bases) == 1: return super().__new__(cls) elif len(bases) == 2: class_ = cls.__bases__[1] else: raise TypeError('只能设置一个类型作为指针类型') if cls.__name__ not in cls.__TypePointer: p = type(cls.__name__, (Pointer,), {'__type__': class_, '__value__': class_()}) for name in dir(class_): if name in cls.__dir: continue if name[:2] == name[-2:] == '__': fun = getattr(class_, name) if callable(fun): setattr(p, name, fun_(fun)) cls.__TypePointer[cls.__name__] = p else: p = cls.__TypePointer[cls.__name__] p = p(*args, **kwargs) return p def __init__(self, value=None): self.__value__ = value def __getattribute__(self, item): if item == '__value__': return super().__getattribute__('__value__') if item == '__type__': return super().__getattribute__('__type__') return getattr(super().__getattribute__('__value__'), item) def __setattr__(self, item, value): if item == '__value__': if type(value) == self.__type__: super().__setattr__('__value__', value) else: raise ValueError('类型不匹配') else: setattr(super().__getattribute__('__value__'), item, value) class StrPointer(Pointer, str): pass
test.py
from Pointer import StrPointer s = StrPointer('a') print(type(s), StrPointer) print(type(s) == StrPointer)
输出
<class 'Pointer.StrPointer'> <class 'Pointer.StrPointer'>False
我知道为什么,但我没法解决。我不希望将__new__函数中的内容移到外面来,因为这样会增加创建有类型指针类的难度,原本只需要多重继承一下即可。
回复
1个回答

test
2024-07-04
已解决,我不应该使用__new__
方法,而应该使用__init_subclass__
方法
class Pointer:
def __init_subclass__(cls, **kwargs):
bases = tuple(set(cls.__bases__) - {Pointer})
assert len(bases) <= 1, '只能再继承一个类'
assert len(bases), '必须再继承一个类'
bases = bases[0]
for fun_name in dir(cls):
if fun_name not in not_transfer_fun and callable(getattr(cls, fun_name)):
setattr(cls, fun_name, fun_transfer(getattr(cls, fun_name)))
cls.__init__ = __init__
cls.__setattr__ = __setattr__
cls.__getattribute__ = __getattribute__
cls.__value__ = None
print(cls.__class__)
cls.__class__ = cls
cls.__type__ = bases
return cls
回复

适合作为回答的
- 经过验证的有效解决办法
- 自己的经验指引,对解决问题有帮助
- 遵循 Markdown 语法排版,代码语义正确
不该作为回答的
- 询问内容细节或回复楼层
- 与题目无关的内容
- “赞”“顶”“同问”“看手册”“解决了没”等毫无意义的内容