簡體   English   中英

創建在讀取時引發異常的值類型

[英]Creating value type that raises exception on reading

如何創建讀取時引發異常的值類型?

例如:

from dataclasses import dataclass, field

Missing = ...


@dataclass
class A:
    a: int = field(default=None)  # <- value can be None
    b: int = field(default=Missing)  # <- can be Missing until you try to access it

    def print(self):
        for i in [self.a, self.b]:
            print(i)  # <- raises ValueError if i is Missing

在 Python 中,似乎總有辦法解決任何問題 :-)

您可以通過巧妙地將描述符值用作數據類字段來解決此問題,如下圖所示。 我還將閱讀有關驗證器部分的更多信息,以了解更多關於描述符如何工作的信息。

from dataclasses import dataclass


# create `_MissingType` class
_MissingType = type('_MissingType', (), {'__bool__': lambda self: False})

# create a singleton for that class
Missing = _MissingType()


class MissingValidator:
    __slots__ = ('default', 'private_name')

    # You may or may not want a default value
    def __init__(self, default=Missing):
        self.default = default

    def __set_name__(self, owner, name):
        self.private_name = '_' + name

    # override __get__() to return a default value if one is not passed in to __init__()
    def __get__(self, obj, obj_type=None):
        try:
            value = getattr(obj, self.private_name)

            if value is Missing:
                cls_name = obj_type.__qualname__
                public_name = self.private_name.lstrip('_')
                raise ValueError(f'Missing value for field `{public_name}` in class `{cls_name}`')

            return value

        except AttributeError:
            return self.default

    def __set__(self, obj, value):
        setattr(obj, self.private_name, value)


@dataclass
class A:
    a: int = None  # <- value can be None
    b: int = MissingValidator()  # <- can be Missing until you try to access it

    def print(self):
        for i in [self.a, self.b]:
            print(i)  # <- raises ValueError if i is Missing


A(b=3).print()
# None
# 3

A(a=42).print()
# raises:
#   ValueError: Missing value for field `b` in class `A`

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM