0

我对 Python 很陌生,并且一直在寻找一种方法来调用一个函数,该函数的名称由一个字符串和一个在用户选择其中一个选项时动态填充的变量组成。

例子:

我使用一个菜单启动程序,该菜单为用户提供某些选项(选择 1、2、3 或 4)

如果用户选择 1,变量 xyz 将填充一个元组或列表内部的字符串。

将此字符串分配给变量后,我调用另一个函数,它给了我另一个选项。

如果我得到选项 1,我的代码会将 xyz 变量附加到一个预定义的字符串,该字符串将形成一个函数名(接下来将调用的那个。)。

if int(option) == 1:
#prefixfunc will be that predefined string that will be the prefix for every function  #to be called
    exec('prefixfunc'+xyz'()')
    #or
    #eval('prefixfunc_'+xyz'()')
    #for example, we have xyz as abc, then it calls function prefixfunc_abc()

它在代码中运行良好。而且我不认为这可能是用户添加不同输入的情况的责任。由于变量是通过使用列表或元组中已定义的字符串来分配的。

我希望我已经说清楚了。

只是为了更清楚:

def maint_car():
print('It Works!!! But did you come until here in a safe way?' )

def veh_func():
func=( "Maintenance", "Prices", "Back", "Quit" )
ord = 0

for i in func:
    ord += 1
    print(ord,'\b)', i)

picked = input('\nOption: ')

if int(picked) == 1:
    exec('maint_'+xyz+'()')




def startprog():

abcd =( "car", "bike", "airplane", "Quit" )
global xyz
ord = 0
for i in abcd:
    ord += 1
    print(ord,'\b)', i)

picked = input('\nVehicle:')

if int(picked) == 1:
    xyz = abcd[0]
    veh_func()

elif int(picked) == 2:
    xyz = abcd[1]
    veh_func()

elif int(picked) == 3:
    xyz = abcd[3]
    veh_func()

elif int(picked) == 4:
    print('\nBye.\n')

startprog()
4

3 回答 3

8

为此,我将使用dict将字符串名称映射到函数的 a。

def test():
 print "yay"

funcs = { "test": test }
funcs["test"]()

这提供了一种更好的方法来执行此操作,您可以测试是否要使用in运算符非常轻松地执行该功能。

回答:您的示例是否有用,eval否则exec我会拒绝。如果您认为这exec是正确的答案,请查看您的解决方案,看看是否有更可维护、更简单或更明确的方法来实现您的目标。在这种情况下,将用户输入映射到要根据某些用户输入调用的函数。

于 2012-12-28T18:03:47.540 回答
3

好吧,你可以那样做,但是当有很多更好的方法时,为什么要那样做呢?如:

funcs = {1: func1, 2: func2, 3: func3, 4: func4}
option = int(raw_input("Enter selection: "))
option in funcs and funcs[option]()

这里的优点是您不必为函数遵循任何特定的命名约定。如果选项 1 是“添加名称”,那么您可以调用该函数addname()而不是func1(). 这将使您的代码更容易遵循。

于 2012-12-28T18:06:43.513 回答
1

如果您直接知道方法的名称,请按照@kindall 的建议进行操作。如果不这样做,您可以使用 getattr() 获取调用方法,而不必使用 eval() 进行编译/评估。

class ZZ(object):
  def fooBar(self):
    print(42)
  def barFoo(self):
    print(-42)

#now make a z
anInstance = ZZ()

#build up a dynamic string
string = 'foo' + 'Bar'

#fetch the attribute bound to string for the instance
method = getattr(anInstance, string)

#now execute the bound method/function (that's what the empty parens do)
method()

# out comes the following! Tada!
>>> 42

# we can inline a lot of this and just do things like
getattr(anInstance, 'bar' + 'Foo')()

# out comes the following! Again with the Tada...
>>> -42
于 2012-12-28T18:17:15.183 回答