0

I've got thousands of small multi-line python3 programs to run, which are generated as strings. They all have a similar structure, and end with a print command. Here's some simple examples

prog_1 = 'h=9\nh=h+6\nprint(h)'
prog_2 = 'h=8\nh-=2\nprint(h)'
prog_3 = 'c=7\nc=c+4\nprint(c)'

They should all be executable if you were to run them from the interpreter. What I mean is, they look like small normal programs when you print them,

>>> print(prog_1)
h=9
h=h+6
print(h)


>>> print(prog_2)
h=8
h-=2
print(h)


>>> print(prog_3)
c=7
c=c+4
print(c)

I want to execute them from inside my program, (which generates them), and capture the output, (i.e. the output of the print) as a variable, but I'm stuck how to do it?

Something like

import os
output = os.popen("python -c " +  prog_1).read()

would be great but I get this error?

/bin/sh: 3: Syntax error: word unexpected (expecting ")")

I think the problem is I don't know how to execute the small programs from the command line? This line executes, but does not print out??

python -c "'h=9\nh=h+6\nprint(h)'"

Thanks a lot for your help :)

Ajay T
  • 73
  • 1
  • 3

3 Answers3

0

If you are not bound to command line you can use:

exec(prog_1)

Warning: exec() can be very dangerous - Why should exec() and eval() be avoided?

Community
  • 1
  • 1
zipa
  • 27,316
  • 6
  • 40
  • 58
  • Cool, thanks a lot, I never new that. I need to somehow capture the output though, so for example, `output = exec(prog_1)`, doesn't seem to work ??? It's empty, not `15`? – Ajay T Apr 18 '17 at 12:35
  • I look forward to evaluating a program involving `shutil.rmtree("/")`. – donkopotamus Apr 18 '17 at 12:42
  • Also be aware that `exec` will pollute the namespace of your program meaning your little mini programs could easily clobber and kill your main one. – donkopotamus Apr 18 '17 at 12:42
0

You can use exec:

>>> prog_1 = 'h=9\nh=h+6\nprint(h)'
>>> exec(prog_1)
15
0

If you wish to execute them in a separate process then you can use subprocess.run:

>>> prog_1 = 'h=9\nh=h+6\nprint(h)'
>>> result = subprocess.run(["python"], input=prog_1, encoding="utf-8", stdout=subprocess.PIPE).stdout
>>> print(result)
15

Note that Python 3.6 is required for encoding support, and Python 3.5 is required for subprocess.run.

In Python 3.5, you need to pass the input as bytes, and the returned output will also be bytes.

>>> result = subprocess.run(["python"], input=bytes(prog_1, "utf-8"), stdout=subprocess.PIPE).stdout
>>> print(str(result, "utf-8"))
15
donkopotamus
  • 22,114
  • 2
  • 48
  • 60
  • Awesome, thanks a lot :))) That's nearly it, I just need to convert to integer, `output=int(result)`. Do I have to somehow shut down/kill the `subprocess`? I've got to run about `100k`, of these little things, on multiple cores? – Ajay T Apr 18 '17 at 12:50