在不带exec/eval的字符串中调用代码,python
我有一段代码,当玩家试图吃东西时执行:在不带exec/eval的字符串中调用代码,python,python,reference,eval,exec,Python,Reference,Eval,Exec,我有一段代码,当玩家试图吃东西时执行: def eat(target='object'): global current_room global locations global inventory if target in inventory: items[target]['on_eat'] #This is showing no results. else: print 'You have no ' + target +
def eat(target='object'):
global current_room
global locations
global inventory
if target in inventory:
items[target]['on_eat'] #This is showing no results.
else:
print 'You have no ' + target + ' to eat.'
此代码用于项目(已修剪)
有没有一种有效的方法可以调用items[whatever]['on_eat'],而不用执行exec()或eval()之类的愚蠢操作?如果不是,也可以使用其他格式作为示例
在此之前,items[everyitems]['on_eat']值不是字符串,而是在代码运行后立即对每个项执行on_eat
我已经看到了许多类似问题的答案,但它们并没有处理函数唯一的参数——更确切地说,它们更像是您可以将函数和函数参数存储为
部分
:
from functools import partial
items = {
'strawberry': {
'weight': 1,
'text': 'The strawberry is red',
'on_eat': partial(normal_eat, 'strawberry', 'pretty good, but not as sweet as you expected')
},
'trees': {
'weight': 50,
'text': 'The trees are tall with large, leaf filled branches blocking out a majority of sunlight.',
'on_eat': partial(forcesay, 'Eating trees? What the hell is your problem?')
}
def eat(target='object'):
# those globals are probably not necessary
if target in inventory:
items[target]['on_eat']() #Add ()'s to call the partial
else:
print 'You have no ' + target + ' to eat.'
您可以使用代码模块
def eat(target='object'):
import code
console = code.InteractiveConsole(locals()) # make a python interpreter with local vars
if target in inventory:
console.push("items[target]['on_eat']")
else:
print 'You have no ' + target + ' to eat.'
部分函数的另一种替代方法是编写如下项
items = {
'strawberry': {
'weight': 1,
'text': 'The strawberry is red',
'on_eat': (normal_eat,('strawberry', 'pretty good, but not as sweet as you expected'))
},
'trees': {
'weight': 50,
'text': 'The trees are tall with large, leaf filled branches blocking out a majority of sunlight.',
'on_eat': (forcesay,('Eating trees? What the hell is your problem?',))
}
}
def eat(target='object'):
if target in inventory:
func, args = items[target]['on_eat']
func(*args)
else:
print 'You have no ' + target + ' to eat.'
这样称呼它
items = {
'strawberry': {
'weight': 1,
'text': 'The strawberry is red',
'on_eat': (normal_eat,('strawberry', 'pretty good, but not as sweet as you expected'))
},
'trees': {
'weight': 50,
'text': 'The trees are tall with large, leaf filled branches blocking out a majority of sunlight.',
'on_eat': (forcesay,('Eating trees? What the hell is your problem?',))
}
}
def eat(target='object'):
if target in inventory:
func, args = items[target]['on_eat']
func(*args)
else:
print 'You have no ' + target + ' to eat.'
你不需要那些
global
语句,除非你重新分配它们,这很奇怪;它起作用了。我想这是有道理的,你/有人能告诉我速度/cpu/步数是如何下降的吗?此外,为什么不在定义项之后随意执行partials,就像定义项[blah]['on_eat']值时那样较少/正常函数调用?因为在items dict的on_eat元素中创建分部时,分部实际上并不调用函数。它所做的只是捕获要调用的函数和要调用它的任何参数。当您访问分部并使用()调用它时,将调用该函数。试试这个:z=partial(min,2,4,6)什么都没有发生。现在调用z:z()返回答案2。创建分部时未调用min;仅当您以z()的形式调用分部函数时才调用它。就速度而言,它应该与调用原始函数非常接近。谢谢。另外,如果我想同时使用打印、更改当前房间、调用正常饮食、再次打印、爆炸用户扬声器等物品[“但丁地狱中的魔法运输食品”][“吃上”]执行多项操作,该怎么办。我假设我必须创建一个单独的函数来完成所有这些工作,或者只是修改数据结构来存储一个分部列表,而不仅仅是一个分部,然后逐个调用它们。这就是我在pyparsing中使用解析操作所做的。很抱歉,我错过了对象后面的结束引号