python 有没有更好的方法用kwargs更新对象的__dict__?

92dk7w1h  于 2023-03-07  发布在  Python
关注(0)|答案(3)|浏览(141)

这是我目前使用的方法,通过传入的关键字args来更新对象dict,它工作得很好。这是一个可接受的方法吗?有更好的方法吗?

class MyClass():
    def __init__(self, **kwargs):
        default_settings = {
            'style': None, 'mods': None, 'filt': True,
            'gsize': 600, 'scale': False
        }
        default_settings.update(kwargs)
        self.__dict__.update(default_settings)
        # ...

if __name__ == '__main__':
    test = MyClass(style='some_style', filt=False, scale=True)
knpiaxh1

knpiaxh11#

建议:
你失去了检查构造函数中键的拼写错误的能力。至少,如果kwargs中的键不是default_settings中的键,你可能想抛出一个异常。

bad_keys = [k for k in kwargs.keys() if k not in default_settings]
if bad_keys:
  raise TypeError(
    "Invalid arguments for MyClass.__init__: %r" % bad_keys)

您可能希望default_settings是MyClass的静态成员,但这样您就必须修改代码以:

self.__dict__.update(default_settings)
self.__dict__.update(kwargs)

...而不是修改本地default_settings示例。

x8diyxa7

x8diyxa72#

现在我已经在这个块周围多呆了几次,我已经了解到一个更好的答案可能是只使用attrs package并允许装饰器为您创建一个构造函数。
例如:

from attrs import define, field
from typing import Optional

@define
class MyClass:
    style: Optional[str] = field(default=None)
    mods: Optional[int] = field(default=None)
    filt: bool = field(default=True)
    gsize: int = field(default=600)
    scale: bool = field(default=False)

完成! attrs类将为您创建一个构造函数,它将接受args和kwargs样式的初始化。

atmip9wb

atmip9wb3#

不要仅仅为了减少输入量而使用kwargs,如果您需要特定的参数,请列出它们。

class MyClass:
    def __init__(self, *, style=None, mods=None, filt=True, gsize=600, scale=False):
       self.style = style
       self.mods = mods
       self.filt = filt
       self.gsize = gsize
       self.scale = scale

if __name__ == '__main__':
    test = MyClass(style='some_style', filt=False, scale=True)

https://stackoverflow.com/a/75644958/1126841类似,您可以使用标准库中的dataclasses模块来减少这里涉及的样板文件的数量。

from dataclasses import dataclass
from typing import Optional

@dataclass
class MyClass:
    style: Optional[str] = None
    mods: Optional[str] = None
    filt: bool = True
    gsize: int = 600
    scale: bool = False

相关问题