python装饰对象_Python装饰一个类以更改父对象类型

Suppose you have two classes X & Y. You want to decorate those classes by adding attributes to the class to produce new classes X1 and Y1.

For example:

class X1(X):

new_attribute = 'something'

class Y1(Y):

new_attribute = 'something'

new_attribute will always be the same for both X1 and Y1. X & Y are not related in any meaningful way, except that multiple inheritance is not possible. There are a set of other attributes as well, but this is degenerate to illustrate.

I feel like I'm overcomplicating this, but I had thought to use a decorator, somewhat likeso:

def _xywrap(cls):

class _xy(cls):

new_attribute = 'something'

return _xy

@_xywrap(X)

class X1():

pass

@_xywrap(Y)

class Y1():

pass

It feels like I'm missing a fairly common pattern, and I'd be much obliged for thoughts, input and feedback.

Thank you for reading.

Brian

EDIT: Example:

Here is a relevant extract that may illuminate. The common classes are as follows:

from google.appengine.ext import db

# I'm including PermittedUserProperty because it may have pertinent side-effects

# (albeit unlikely), which is documented here: [How can you limit access to a

# GAE instance to the current user][1].

class _AccessBase:

users_permitted = PermittedUserProperty()

owner = db.ReferenceProperty(User)

class AccessModel(db.Model, _AccessBase):

pass

class AccessExpando(db.Expando, _AccessBase):

pass

# the order of _AccessBase/db.* doesn't seem to resolve the issue

class AccessPolyModel(_AccessBase, polymodel.PolyModel):

pass

Here's a sub-document:

class Thing(AccessExpando):

it = db.StringProperty()

Sometimes Thing will have the following properties:

Thing { it: ... }

And other times:

Thing { it: ..., users_permitted:..., owner:... }

I've been unable to figure out why Thing would sometimes have its _AccessParent properties, and other times not.

解决方案

Use 3-arguments type:

def makeSomeNicelyDecoratedSubclass(someclass):

return type('MyNiceName', (someclass,), {'new_attribute':'something'})

This is indeed, as you surmised, a reasonably popular idiom.

Edit: in the general case if someclass has a custom metaclass you may need to extract and use it (with a 1-argument type) in lieu of type itself, to preserve it (this may be the case for your Django and App Engine models):

def makeSomeNicelyDecoratedSubclass(someclass):

mcl = type(someclass)

return mcl('MyNiceName', (someclass,), {'new_attribute':'something'})

This also works where the simpler version above does (since in simple cases w/no custom metaclasses type(someclass) is type).

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值