OfLettersAndNumbers
OfLettersAndNumbers

Reputation: 832

How to pass a list of tuples as an argument parameter?

I'm writing a python script where I want to pass in a list of tuples/list. I tried using the argparse module, but couldn't find a way to pass in a list of tuples as an argument (i.e. [(1,2),(3,4),(5,6)]).

What I've tried so far:

 $ python test.py --pairs (1,2) (2,4)
-bash: syntax error near unexpected token `('

Does anyone have any examples that uses the argparse module (or any other module for that matter)?

Here's the script. Nothing special, just wanted to pass in the list of tuples and make sure I can print and access the elements properly:

import argparse

def test(args):
    print("----")
    print(args.pairs)

if __name__ == '__main__':

    parser = argparse.ArgumentParser()
    parser.add_argument('--pairs', type=tuple, nargs='+')

    args = parser.parse_args()
    print("===args===")
    for arg in vars(args):
        print(arg, getattr(args, arg))

    test(args)

Upvotes: 3

Views: 2093

Answers (2)

Pedro Maia
Pedro Maia

Reputation: 2712

You cannot put parenthesis on your arguments since they're special token characters in the syntax of bash/zsh, you can either wrap it into quotes "(1,2)" "(2,4)" or remove them 1,2 2,4 on both ways you can create your own type

First case:

import ast

parser.add_argument('--pairs', type=lambda a: ast.literal_eval(a), nargs='+')

Second case:

parser.add_argument('--pairs', type=lambda a: tuple(map(int, a.split(','))), nargs='+')

Upvotes: 1

OfLettersAndNumbers
OfLettersAndNumbers

Reputation: 832

I figured a way, but please let me know if there's a better one.

I used the ast module and passed the argument as a string and used the ast module (shoutout the answer I found here)

Here's my updated code:

import argparse
import ast

def test(args):
    pairs = ast.literal_eval(args.pairs)
    print(args.pairs, type(args.pairs))
    print(type(pairs))
    print(pairs[0])
    print(pairs[0][1])

if __name__ == '__main__':
    parser = argparse.ArgumentParser()
    parser.add_argument('--pairs')

    args = parser.parse_args()

    test(args)

Testing this out yields:

$ python test.py --pairs '[(1,2),(3,4)]'
[(1,2),(3,4)] <class 'str'>
<class 'list'>
(1, 2)
2

Upvotes: 0

Related Questions