0

How do I use a variable as a function name so that I can have a list of functions and initialize them in a loop. I'm getting the error I expected which is str object is not callable. But I don't know how to fix it. Thanks.

#Open protocol configuration file
config = configparser.ConfigParser()
config.read("protocol.config")

# Create new threads for each protocol that is configured
protocols = ["ISO", "CMT", "ASCII"]
threads = []
threadID = 0

for protocol in protocols:
        if (config.getboolean(protocol, "configured") == True):
                threadID = threadID + 1
                function_name = config.get(protocol, "protocol_func")
                threads.append(function_name(threadID, config.get(protocol, "port")))

# Start new threads
for thread in threads:
        thread.start()

print ("Exiting Main Protocol Manager Thread")
dpetican
  • 771
  • 1
  • 5
  • 12
  • **Where** are these functions? In a specific module? The current module? Often, it's cleanest to have the functions be dictionary keys and do a lookup -- for instance, using a decorator for exposed functions that should be placed in that dictionary; much less metaprogramming hackery that way. – Charles Duffy May 17 '16 at 16:06

3 Answers3

1

If you put your set of valid protocol_funcs in a specific module, you can use getattr() to retrieve from that module:

import protocol_funcs

protocol_func = getattr(protocol_funcs, function_name)
threads.append(protocol_func(threadID, config.get(protocol, "port")))

Another approach is a decorator to register options:

protocol_funcs = {}

def protocol_func(f):
  protocol_funcs[f.__name__] = f
  return f

...thereafter:

@protocol_func
def some_protocol_func(id, port):
  pass # TODO: provide a protocol function here

That way only functions decorated with @protocol_func can be used in the config file, and the contents of that dictionary can be trivially iterated over.

Charles Duffy
  • 280,126
  • 43
  • 390
  • 441
1

Functions are first class citizens in python, so you can treat them as normal variables, simply build a list with the functions an iterate over them:

>>> for f in [int, str, float]:
...     for e in [10, "10", 10.0]:
...         print(f(e))
...         
10
10
10
10
10
10.0
10.0
10.0
10.0
Netwave
  • 40,134
  • 6
  • 50
  • 93
0

Functions can be put in a list to be called later:

def a():
    print("a")
def b():
    print("b")
def c():
    print("c")
func = [a, b, c]
for function in func:
    function()

The output you'll get is from all the functions:

a
b
c

Use the same logic to get your code working as expected

illright
  • 3,991
  • 2
  • 29
  • 54