日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程语言 > python >内容正文

python

Python的元类

發布時間:2025/6/17 python 30 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Python的元类 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

1、用元類驗證子類

每當我們定義新類的時候,元類就會運行雅正代碼,以確保這個新類符合規定的規范。
Python系統把子類的class語句處理完畢,就會調用元類的 __new__ 方法。元類可以通過 __new__ 方法,獲取子類、孫子類的名稱,父親及屬性。
這樣使得我們不需要將驗證代碼放在本類 __init__ 方法中,等到構建對象再驗證。

下例中,定義一個邊數小于3的子類,class語句一結束,元類的驗證代碼就會拒絕這個class。

class ValidatePolygon(type):def __new__(meta, name, bases, class_dict):# Don't validate the abstract Polygon classif bases != (object,):if class_dict['sides'] < 3:raise ValueError('Polygons need 3+ sides')return type.__new__(meta, name, bases, class_dict)class Polygon(object, metaclass=ValidatePolygon):sides = None # Specified by subclasses@classmethoddef interior_angles(cls):return (cls.sides - 2) * 180class Triangle(Polygon):sides = 3print(Triangle.interior_angles())

2、用元類注冊子類

每次從基類中繼承子類時,基類的元類都可以自動運行注冊代碼。
這在需要反向查找 ‘reverse lookup’ 時很有用,使得在簡單標識符和對應的類之間,建立映射關系。
依然利用的是class語句執行完,自動調用元類的 __new__ 方法。

import json registry = {}def register_class(target_class):registry[target_class.__name__] = target_classdef deserialize(data):params = json.loads(data)name = params['class']target_class = registry[name]return target_class(*params['args'])class Meta(type):def __new__(meta, name, bases, class_dict):cls = type.__new__(meta, name, bases, class_dict)register_class(cls)return clsclass Serializable(object):def __init__(self, *args):self.args = argsdef serialize(self):return json.dumps({'class': self.__class__.__name__,'args': self.args,})def __repr__(self):return '%s(%s)' % (self.__class__.__name__,', '.join(str(x) for x in self.args))class RegisteredSerializable(Serializable, metaclass=Meta):passclass Vector3D(RegisteredSerializable):def __init__(self, x, y, z):super().__init__(x, y, z)self.x, self.y, self.z = x, y, zv3 = Vector3D(10, -7, 3) print('Before: ', v3) data = v3.serialize() print('Serialized:', data) print('After: ', deserialize(data))print(registry)

3、用元類注解類的屬性

使用元類像是在 class 語句上放置了掛鉤,class語句處理完畢,掛鉤就會立刻觸發。
下列中借助元類設置了 Filed.name 和 Filed.name。

class Field(object):def __init__(self):# These will be assigned by the metaclass.self.name = Noneself.internal_name = Nonedef __get__(self, instance, instance_type):if instance is None: return selfreturn getattr(instance, self.internal_name, '')def __set__(self, instance, value):setattr(instance, self.internal_name, value)class Meta(type):def __new__(meta, name, bases, class_dict):for key, value in class_dict.items():if isinstance(value, Field):value.name = keyvalue.internal_name = '_' + keycls = type.__new__(meta, name, bases, class_dict)return clsclass DatabaseRow(object, metaclass=Meta):passclass BetterCustomer(DatabaseRow):first_name = Field()last_name = Field()prefix = Field()suffix = Field()foo = BetterCustomer() print('Before:', repr(foo.first_name), foo.__dict__) foo.first_name = 'Euler' print('After: ', repr(foo.first_name), foo.__dict__)

元類總結就到這里,自己也沒有完全理解清楚。
希望對此有深刻理解的pythoner留言。

代碼來自:https://github.com/bslatkin/effectivepython

轉載于:https://www.cnblogs.com/lidyan/p/7157227.html

總結

以上是生活随笔為你收集整理的Python的元类的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。