gpt4 book ai didi

python - 为类动态添加类方法

转载 作者:太空狗 更新时间:2023-10-30 00:56:43 26 4
gpt4 key购买 nike

我有以下片段:

FEED_TYPES = [
('fan_mail', 'Fan Mail'),
('review', 'Review'),
('tip', 'Tip'),
('fan_user', 'Fan User'),
('fan_song', 'Fan Song'),
('fan_album', 'Fan Album'),
('played_song', 'Played Song'),
('played_album', 'Played Album'),
('played_radio', 'Played Radio'),
('new_event', 'New Event'),
]

class Feed:
@classmethod
def do_create(cls, **kwargs):
print kwargs

@classmethod
def create(cls, type, **kwargs):
kwargs['feed_type'] = type
cls.do_create(**kwargs)

for type_tuple in FEED_TYPES:
type, name = type_tuple

def notify(self, **kwargs):
print "notifying %s" % type
self.create(type, **kwargs)

notify.__name__ = "notify_%s" % type
setattr(Feed, notify.__name__, classmethod(notify))

Feed.create("FanMail", to_profile="Gerson", from_profile="Felipe")
Feed.notify_fan_mail(to_profile="Gerson2", from_profile="Felipe2")

想法是为每种提要类型动态创建一个类方法(如 notify_fan_mail)。它工作得很好,唯一的问题是 print 语句总是打印“notifying new_event”,不管我调用什么方法(notify_new_mailnotify_review 等)。

我意识到这是因为它使用了分配给类型的最后一个值。我的问题是:如何动态创建方法来为 type 使用正确的值?

此外,如果我在 Python 文件中有这个确切的代码,那么这是向 Feed 类添加方法的正确方法,还是有更优雅的方法?

最佳答案

使用闭包来保存 kind 的值:

for type_tuple in FEED_TYPES:
kind, name = type_tuple
def make_notify(kind):
def notify(self, **kwargs):
print "notifying %s" % kind
self.create(kind, **kwargs)
return notify
notify = make_notify(kind)
notify.__name__ = "notify_%s" % kind
setattr(cls, notify.__name__, classmethod(notify))

顺便说一下,不要使用 type 作为变量名,因为它会隐藏同名的内置函数。


修改 Feed 的一种更优雅的方法是创建类装饰器。这更清楚地表明您有代码修改了 Feed 的原始定义。

FEED_TYPES = [
('fan_mail', 'Fan Mail'),
('review', 'Review'),
('tip', 'Tip'),
('fan_user', 'Fan User'),
('fan_song', 'Fan Song'),
('fan_album', 'Fan Album'),
('played_song', 'Played Song'),
('played_album', 'Played Album'),
('played_radio', 'Played Radio'),
('new_event', 'New Event'),
]

def add_feed_types(cls):
for type_tuple in FEED_TYPES:
kind, name = type_tuple
def make_notify(kind):
def notify(self, **kwargs):
print "notifying %s" % kind
self.create(kind, **kwargs)
return notify
notify = make_notify(kind)
notify.__name__ = "notify_%s" % kind
setattr(cls, notify.__name__, classmethod(notify))
return cls

@add_feed_types
class Feed:
@classmethod
def do_create(cls, **kwargs):
print kwargs

@classmethod
def create(cls, kind, **kwargs):
kwargs['feed_type'] = kind
cls.do_create(**kwargs)


Feed.create("FanMail", to_profile="Gerson", from_profile="Felipe")
Feed.notify_fan_mail(to_profile="Gerson2", from_profile="Felipe2")

关于python - 为类动态添加类方法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15420989/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com