Python argparse parse_args into global namespace (or a reason this is a bad idea)

霸气de小男生 提交于 2019-12-22 04:26:07

问题


I've mostly used argparse for making command-line scripts in python, and the idiom I generally use is that I assign the arguments as attributes of an object, then parse them individually to a variable that matches their attribute name. This seems a little repetitive. Is there a way to assign them all into the global namespace and cut out the assignment step; or as is often the case when some python behavior seems counter-intuitive to me, can some wise, python expert point out that there a good reason I should not do this or want to do this?

What I have now is this:

if __name__ == "__main__":
    parser = argparse.ArgumentParser()
    parser.add_argument("--db",type=str, dest='db', nargs='?', default="test")
    parser.add_argument("--collection",type=str, dest='collection', nargs='?', help="Collection, default is test", default="test")
    args = parser.parse_args()
    db = args.db                   # gross! 
    collection = args.collection   # yuck!
    print(db)
    print(collection)

What I'd like this is:

if __name__ == "__main__":
    parser = argparse.ArgumentParser()
    parser.add_argument("--db",type=str, dest='db', nargs='?', default="test")
    parser.add_argument("--collection",type=str, dest='collection', nargs='?', help="Collection, default is test", default="test")
    parser.SUPER_parse_args() # now, db and collection are already in the namespace!
    print(db)
    print(collection)

It doesn't seem like much when I only have 2 arguments, but if I have 10 or so, doubling the assign steps, where I rename into the global namespace the attributes that already exist in the args object, starts to bug me.


回答1:


You can do this using globals:

globals().update(args.__dict__)

however, you really *shouldn't do that. From the zen of python,

Namespaces are one honking great idea -- let's do more of those!

I'll echo what @Martijn said in his comment:

Don't. Just don't. I'd use args directly instead.

Keep things as nicely separated as you can. It makes for more maintainable and easier to understand code.




回答2:


This is what I did. It helps with variable collision but not maintainability.

parser_args = parser.parse_args()
if parser_args.verbose:
    globals().update(argparse.Namespace(verbose=parser_args.verbose).__dict__)



回答3:


To add onto mgilson's answer:

Consider using locals().update(args.__dict__) instead; this will update the current namespace rather than the global namespace.

You can also do this using locals() or vars(). See this Stack Overflow post for a nice explanation on the difference between the two.

I'm a bit late for Mittonchops, but hopefully this helps others.



来源:https://stackoverflow.com/questions/19299635/python-argparse-parse-args-into-global-namespace-or-a-reason-this-is-a-bad-idea

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!