2

Is there a way pass arguments conditionally in Python (I use Python 2.7)?

As an example, this code gives 2 or 3 arguments depending if the 3rd argument exists in a dictionary.

if "arg3" in my_dict:
    my_method(
        my_dict[arg1],
        my_dict[arg2],
        my_dict[arg3],
    )
else:
    my_method(
        my_dict[arg1],
        my_dict[arg2],
    )

I think it looks redundant to write it this way. I've seen some info on argparse, which I think would look like this:

import argparse

parser = argparse.ArgumentParser()
parser.add_argument(my_dict[arg1])
parser.add_argument(my_dict[arg2])
if arg3 in my_dict:
    parser.add_argument(my_dict[arg3])
args = parser.parse_args()

my_method(args)

I don't really like this method either, as it needs an import and is hard to read.

Is there a way to do something like:

my_method(
    my_dict[arg1],
    my_dict[arg2],
    my_dict[arg3] if arg3 in my_dict,
)

Or any other way I am missing, that would be simple and clean?

0

4 Answers 4

6

Assuming that your method signature is

def my_method(arg1=None, arg2=None, arg3=None):
    print ('arg1',arg1,'arg2',arg2,'arg3',arg3)

Then simply replace all those if/else blocks with

my_method(**dictionary)

For example

 d = {'arg3':11, 'arg2':22, 'arg1':3}

the above will produce

arg1 3 arg2 22 arg3 11

This behaviour is brought to by **kwargs there are quite a few good tutorials on it on the web. Here's one from digial ocean (I am not affiliated)

Sign up to request clarification or add additional context in comments.

5 Comments

how does this work given that dictionaries are not ordered?
That is the nature of kwargs
@Ev.Kounis It depends on the keyword arguments having the same names as the dict keys, in which case the order in which you provide the keyword arguments is irrelevant. This answer greatly depends on how my_method is defined, though.
Oh I see.. So the function variables have to be the same as the dictionary keys. nice!
I like your answer a lot, and it fits my question, but actually I also have arguments that are from outside of my_dict as well in the call, so this solution would not work for me, while the .get(arg3, None) will always work.
2

You can call it like that:

my_method(my_dict[arg1], my_dict[arg2], my_dict.get(arg3, None))

You might want to change the my_method to adapt for this; maybe something like def my_method(*args):.

For more info on the .get() dictionary method take a look at this.

This solution is definitely uglier (acc to the Pythonic standards of beauty) than the one provided by @e4c5 but does not require the function variables to have the same name as the dictionary keys.

Comments

0

Both @Ev.Kounis and @e4c5 provide good answers. As far the attempt you made in the question, you are only missing a valid conditional expression.

my_method(
    my_dict[arg1],
    my_dict[arg2],
    my_dict[arg3] if arg3 in my_dict else None,
)

which is, practically speaking, the same as @Ev.Kounis proposed.

Comments

0

As an alternative, I would consider changing my_method to take in a dict if you know that you will be passing in a dict each time.

def my_method(d):
    a1 = d[arg1]
    a2 = d[arg2]
    a3 = d[arg3] if 'arg3' in d else None
    ...

Otherwise, the other answers are also valid.

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.