## Problem:

I have a list of functions with different signatures. There is some set of possible parameters, and I want to call all these functions with the “appropriate” argument for each parameter.

This is a little hand-wavy, let’s look at an example:

```def half(a):
return a / 2

def twice(a):
return 2 * a

return a + b

def subtraction(a, b):
return a - b

functions = [half, twice, addition, subtraction]
a = get_a()
b = get_b()

```

Desired outcome:

```[half(a), twice(a), addition(a,b), subtraction(a, b)]
```

And we want to do this without making our function definitions too ugly.

## Solution 1:

One option is to `get_b()` within the functions that need them. This is not ideal, suppose `get_b` is not a pure function (e.g. a network call), we would want to pass `b` into scope instead of getting it from elsewhere every time it’s needed.

## Solution 2:

We could change the signature to accept arbitrary kwargs and then pass a dict of args, for example:

```def half(**kwargs):
return kwargs['a'] / 2

def twice(**kwargs):
return 2 * kwargs['a']

return kwargs['a'] + kwargs['b']

def subtraction(**kwargs):
return kwargs['a'] - kwargs['b']

functions = [half, twice, addition, subtraction]
payload = {'a': get_a(), 'b': get_b()}
results = [f(**payload) for f in functions]
```

This works, but makes each of our function definitions uglier.

## Solution 3:

Allow each function to have a different signature, inspect the signature at runtime and pass what is needed.

```import inspect

def half(a):
return a / 2

def twice(a):
return 2 * a

return a + b

def subtraction(a, b):
return a - b

# Wrapper which:
# * accepts a dict of all possible kwargs and their names
# * inspects the signature of the function
# * calls that function with the correct args
def call_func_with_correct_args(f, possible_args):
func_args = inspect.getargspec(f).args
args_to_pass = {k: possible_args[k] for k in func_args}
return f(**args_to_pass)

functions = [half, twice, addition, subtraction]
a = get_a()
b = get_b()
full_payload = {'a': a, 'b': b}

results = [call_func_with_correct_args(f, full_payload) for f in functions]

```

So this is nice and clever, but we need to be careful that our function parameters are named correctly and consistently. Essentially we are passing the burden to the function definitions.

## Conclusion

I don’t know what a great solution to this might look like. Is there a better way to do this? If all the parameters are different types, Python3’s type hinting might provide another option. What does this look like in other languages?