Python Forum

Full Version: Multiple variable inputs when only one is called for
You're currently viewing a stripped down version of our content. View the full version with proper formatting.
Hi all, trying to run a python code (not mine) that used a function generate_index(arg). The arg function is actually meant to have 5 parts (host, graft, index, memory, and threads) and these components are called later in the function as arg.host, arg.graft...etc.

Probably a dumb question, but how can i input these five variables into the function? when I separate by commas, i get an error saying only expected one variable. I tried adding a double asterisk to before the variable arg, but this did not help either...

Relevant introduction to the Code as below and is from the xenocell repository:


def generate_index(**args):

  print_header(args)
  print_log('Generate index...')
  create_directory(args.output)
  run_xenome(args)
  print_log('Generation of Xenome index finished!')


#
def print_header(args):
  header = '''##----------------------------------------------------------------------------##
## XenoCell: Generate Xenome index of reference genomes.
##----------------------------------------------------------------------------##
## FASTA of host reference genome:  {host}
## FASTA of graft reference genome: {graft}
## Output directory:                {output}
## Number of threads:               {threads}
## Memory in GB:                    {memory}
##----------------------------------------------------------------------------##'''.format(
    host    = args.host,
    graft   = args.graft,
    output  = args.output,
    threads = args.threads,
    memory  = args.memory
That code is probably part of a class
args.host ,etc.. looks to be from a class object

Simple example
class MyClass:
    def __init__(self):
        self.foo = 'printing foo'
        self.bar = 'printing bar'
        
m = MyClass()

def func(arg):
    print(arg.foo)
    print(arg.bar)

func(m)
output
Output:
printing foo printing bar
I spent too much time trying to think of how the posted code could work and couldn't come up with anything that can be passed in as **args and used as args.attribute. So I took a look at the xenocell code and saw I was right. This is the generate_index code from xenocell.
def generate_index(args):

  print_header(args)
  print_log('Generate index...')
  create_directory(args.output)
  run_xenome(args)
  print_log('Generation of Xenome index finished!')
Then I carefully read your post and saw you added the ** before args, and I felt foolish.

args is expected to be an argsparse.Namespace object, the type of object returned by argparse.ArgumentParser.parse(). xenocell is a command-line tool. You run the program from the command line, including the arguments. argparse parses the arguments and creates a Namespace object that is passed to the functions in the program.

If you want to import xenocell modules and use the functions, you'll need to make a compatible arg object. May as well use argparse.Namespace.
from argparse import Namespace


def generate_index(args):
    print_header(args)


def print_header(args):
    print(args.output)


generate_index(Namespace(output="Hello"))