-1

Help would be greatly appreciated with this as Im struggling with the final product.

I need to write a function that opens and reads the file, returns a dictionary where each key is the name of a function, and the value is a list of the parameters of the function. And should return something like this.

{"h":[x], "f":[a, b], "g":[c]}

The file I am transferring looks like this

def h(x):

   f(x + 4, 9)

def f(a, b):

    e = a * b
    g(e)

def g(c):

   b = 3

print(c)

print(b)

So far my code looks like this but I have no clue how to make it look like the final product in dictionary.

filename=""

ddd=dict()

new=list()

def take_name():

global filename

filename= input("Please, type the name of the file:")

print(take_name())

def open_read():

   global handle

   handle= open(filename, 'r')

   for line in handle:

       line=line.rstrip()

       if line.startswith('def'):

            line=line.replace('def', " ")

            line=line.replace(':', " ")


             new.append(line)



print(new)

print(ddd)

print(open_read())

Thanks again for the help

  • Please fix the formatting. Also, note that the "(Python)" shouldn't be in the title, that is what the tags are for. [edit] you question to fix those two. – Ulrich Eckhardt Dec 06 '18 at 06:24

2 Answers2

1

Best to use Python's parser for the job, not regexps.

Assuming you mean {'h': ['x'], 'f': ['a', 'b'], 'g': ['c']} (since {"h":[x], "f":[a, b], "g":[c]} does not look particularly usable):

import ast

with open(filename) as f:
    code = f.read()
module = ast.parse(code, filename)
functions = { statement.name: [arg.arg for arg in statement.args.args]
    for statement in module.body if isinstance(statement, ast.FunctionDef)
}
print(functions)

However, this is just a base snippet, much more complexity is possible. For one, it will only give you top-level functions (you'd need some recursion to catch sub-functions, or methods). For another, it ignores the variety of possible arguments besides positional (e.g. kwargs). If you need them, you can add them yourself now that you see the basics of AST.

EDIT: A notable difference between inspect and ast is that you have to have imported (i.e. executed) the source file for it to be available to inspect; ast works on source file itself, without executing it. Both approaches are valid; but if you have security concerns about a file, or you cannot execute it (due to dependencies, for example), or if you want to fetch things you can't from executed code (such as locally defined functions I mentioned above), you should prefer ast.

Amadan
  • 191,408
  • 23
  • 240
  • 301
1

You can use the builtin python module inspect to accomplish what you want. Here is some code to help you get started, in this example I am processing a file named dummy.py but you could use the import using something like this.

import dummy
import inspect


members = inspect.getmembers(dummy)
for each in members:
    k,v = each
    if callable(v):
        args = inspect.getargspec(v)
        print(v, args)
Luv
  • 386
  • 4
  • 15