在Python中我想将用户输入用作函数调用。特别是,我有以下代码测试:
def forward(forwardValue):
print("in forward, with value " + forwardValue)
return
command = 'forward' # this would come in as user input
value = '255'
command(value)
我希望看到的是一个打印输出,上面写着:向前,值为255
我看到的是一个错误:
'str' object is not callable
该错误信息是有道理的,我可以看到为什么我测试的不起作用,但有什么方法可以做我想做的事情?换句话说,用户输入可以用作函数调用吗?
我目前所做的是使用" if"用于检查用户输入是否为'转发'声明,如果是,则调用函数' forward'。但如果可能的话,我想更多的是Pythonesque。
我有一个用户可以使用的大约30种不同命令的列表,每个命令都有一个定义的函数来处理它。我的系列30" if"和" elif"陈述似乎很笨拙。
答案 0 :(得分:2)
使用globals()
:
globals()[command](value)
但是,如果担心安全性,您可能希望限制可以从用户输入调用的内容。例如,定义可调用函数的字典:
functions = {'forward': forward, 'othercommand': othercommand}
或与先前的解决方案结合以避免重复:
functions = {k: globals()[k] for k in ('forward', 'othercommand')}
然后你可以用:
来调用你的函数functions[command](value)
您可以将类用作用户可调用函数的命名空间:
class Functions:
@staticmethod
def forward(arg):
print("in forward, with value " + forwardValue)
@staticmethod
def othercommand():
pass
(如果您使用的是Python 3.x,@staticmethod
在此上下文中是可选的)
然后使用getattr()
:
getattr(Functions, command)(value)
答案 1 :(得分:1)
Daanii,似乎抓住了你的是名为command的变量包含字符串'forward'。这个字符串对象不是你的功能。正如你所说的那样,使用if语句是最简单的方法。
如果您有许多功能和/或您不一定希望函数名称和用户传递的字符串匹配,那么我建议使用字典。
d = {'foward':forward, 'backward':backward, 'flurb':durf}
def forward(forwardValue):
print("in forward, with value " + forwardValue)
return
def backward(backwardValue):
print("in backward, with value " + backwardValue)
return
def durf(value):
print("in durf, with value " + value)
return
try:
command = raw_input('Enter your thing:\n')
value = '255'
d[command](value)
except KeyError:
print 'The user did not enter a valid string'