我有dict
种不同的类型,我想根据实际参数的名称添加一个简单的getter。
例如,对于三个存储参数,我们说:
self.storage = {'total':100,'used':88,'free':1}
我现在正在寻找一种方法(如果可能的话)来动态生成一个带有一些元编程魔法的函数。
而不是
class spaceObj(object):
def getSize(what='total'):
return storage[what]
或硬编码
@property
def getSizeTotal():
return storage['total']
但
class spaceObj(object):
# manipulting the object's index and magic
@property
def getSize:
return ???
这样就可以派生出调用mySpaceObj.getSizeFree
- getSize只在对象中定义一次,并通过操作对象函数列表从它派生的相关函数。
这样的事情可能吗?
答案 0 :(得分:5)
虽然当然可以从类中获取未知属性作为属性,但这不是pythonic方法(__getattr__
魔术方法相当rubyist)
class spaceObj(object):
storage = None
def __init__(self): # this is for testing only
self.storage = {'total':100,'used':88,'free':1}
def __getattr__(self, item):
if item[:7] == 'getSize': # check if an undefined attribute starts with this
return self.getSize(item[7:])
def getSize(self, what='total'):
return self.storage[what.lower()]
print (spaceObj().getSizeTotal) # 100
答案 1 :(得分:2)
您可以将值作为属性放入对象:
class SpaceObj(object):
def __init__(self, **kwargs):
self.__dict__.update(kwargs)
storage = {'total':100,'used':88,'free':1}
o = SpaceObj(**storage)
print o.total
或
o = SpaceObj(total=100, used=88, free=1)
print o.total
或使用__getattr__
:
class SpaceObj(object):
def __init__(self, **kwargs):
self.storage = kwargs
def __getattr__(self,name):
return self.storage[name]
o = SpaceObj(total=100, used=88, free=1)
print o.total
后一种方法需要更多的代码,但它更安全;如果您有一个方法foo
并且某人使用SpaceObj(foo=1)
创建了该实例,那么该方法将被第一种方法覆盖。
答案 2 :(得分:-2)
>>> import new
>>> funcstr = "def wat(): print \"wat\";return;"
>>> funcbin = compile(funcstr,'','exec')
>>> ns = {}
>>> exec funcbin in ns
>>> watfunction = new.function(ns["wat"].func_code,globals(),"wat")
>>> globals()["wat"]=watfunction
>>> wat()
wat