4

I have python functions in string format and I want to get the python objects of these functions in the scope of the program. I have tried exec(), eval() and ast.literal_eval() but none of these return a function object.

For example:

s = "def add(args):\n    try:\n        return sum([int(x) for x in args])\n    except Exception as e:\n        return 'error'\n

this is a simple function in string to add elements of a list. I am looking for a module of utility which can return the object of the function add

function_obj = some_function(s)
print 'type:', type(function_obj)
type: <type 'function'>
1
  • 1
    Why do you have function definitions in string format? Commented Sep 5, 2019 at 11:28

4 Answers 4

6

First compile the function(as string) into code object ie,

code_obj = compile(s, '<string>', 'exec')

and then use types.FunctionType to create new function type from code object.

>>> import types
>>> new_func_type = types.FunctionType(code_obj.co_consts[0], globals())
>>> print(type(new_func_type))
<class 'function'>
>>> new_func_type([*range(10)])
45
Sign up to request clarification or add additional context in comments.

Comments

3

One way (there might be better ones - e.g. [Python.Docs]: Built-in functions - compile(source, filename, mode, flags=0, dont_inherit=False, optimize=-1) as pointed out by @Abdul-Niyas-P-M's answer) would be to:

>>> s = "def add(args):\n    try:\n        return sum([int(x) for x in args])\n    except Exception as e:\n        return 'error'"
>>>
>>> def create_func_obj(func_code_str):
...     g = dict()
...     l = dict()
...     exec(func_code_str, g, l)
...     if l:
...         return list(l.values())[0]
...
>>>
>>> func = create_func_obj(s)
>>>
>>> func
<function add at 0x000002952F0DEC80>
>>> func([1, 2, 3])
6
>>>
>>> add  # The function wasn't added in the global namespace (as an exec sideeffect)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
NameError: name 'add' is not defined

If the code string contains other things besides the definition of one function, the results will not be the expected ones.

Comments

1

In Python 2, you can give a globals dictionary to exec:

globalsdict = {}
exec s in globalsdict

And then globalsdict['add'] will be your function object. Globalsdict will also contain all the builtins.

Comments

0
a = \
'''def fun():\n
    print 'result'
'''
exec(a)

fun()

1 Comment

You should add some explanation and a link to the exec docs - otherwise people will recommend to delete your answer.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.