tags:

views:

372

answers:

5

I've looked at this and it wasn't much help.

I have a Ruby program that puts a question to the cmd line and I would like to write a Python program that can return an answer. Does anyone know of any links or in general how I might go about doing this?

Thanks for your help.

EDIT
Thanks to the guys that mentioned piping. I haven't used it too much and was glad it was brought up since it forced me too look in to it more.

+4  A: 

If you're on unix / linux you can use piping:

question.rb | answer.py

Then the output of question.rb becomes the input of answer.py

I've not tried it recently, but I have a feeling the same syntax might work on Windows as well.

Ben
-1: that does not return the answer to the ruby program.
nosklo
Hmmm... I don't think the OP asked for the second program to return and answer *to the ruby program*. I guess it depends on how you interpret "return".
Ben
+3  A: 

Pexpect

http://www.noah.org/wiki/Pexpect

Pexpect is a pure Python expect-like module. Pexpect makes Python a better tool for controlling other applications.

Pexpect is a pure Python module for spawning child applications; controlling them; and responding to expected patterns in their output. Pexpect works like Don Libes' Expect. Pexpect allows your script to spawn a child application and control it as if a human were typing commands.

GHZ
+1: pexpect can do it.
nosklo
+1  A: 

There are two ways (off the top of my head) to do this. The simplest if you're in a Unix environment is to use piping. Simple example:

cat .profile .shrc | more

This will send the output of the first command (cat .profile .shrc) to the more command using the pipe character |.

The second way is to call one program from the other in your source code. I'm don't know how Ruby handles this, but in Python you can run a program and get it's output by using the popen function. See this example chapter from Learning Python, then Ctrl-F for "popen" for some example code.

Bill the Lizard
-1: using pipe means data goes a single way. He specifically asked to return data
nosklo
That's one reason why I gave two possible solutions.
Bill the Lizard
Okay, removed negative vote.
nosklo
+7  A: 
p = subprocess.Popen(['ruby', 'ruby_program.rb'], stdin=subprocess.PIPE, 
                                          stdout=subprocess.PIPE)
ruby_question = p.stdout.readline()
answer = calculate_answer(ruby_question)
p.stdin.write(answer)
print p.communicate()[0]  # prints further info ruby may show.

The last 2 lines could be made into one:

print p.communicate(answer)[0]
nosklo
This is good if you want the python program to "be in control".
Aaron Maenpaa
@zacherates: which is what you generally want, not? I am sure there is a way to do the same from the ruby side.
nosklo
Or, even better, p.communicate(answer)[0]
Aaron Gallagher
@Aaron: Yes, added info. Thank you.
nosklo
+3  A: 

First of all check this out: [Unix piping][1]

It works on windows or unix but it's slighly dufferent, first the programs:

question.rb:

puts "This is the question"

answer.rb:

question = gets
#calculate answer
puts "This is the answer"

Then the command line:

In unix:

question.rb | answer.rb

In windows:

ruby question.rb | ruby answer.rb

Output:

This is the question
This is the answer
krusty.ar
-1: using pipe means data goes a single way. He specifically asked to return data
nosklo
No it doesn't, what I understand is that he needs to get the question from another process, and this is the way it's done since the 70's, your answer is more controlled but almost equivalent to this one. I improved the examples anyway.
krusty.ar
@krusty.ar: He mentions in question that the python program must somehow *return* the answer to the ruby program. So the -1 stands.
nosklo
@nosklo: If you construct pipes using only the pipe `|` character, then the data flows one way. But you can set up a program to use both input and output pipes -- in fact, that's exactly how your Python answer works under the hood. You don't need Python for this; the Unix shell has been able to do it since the 70s.
Daniel Pryden
@Daniel Pryden: I don't see your point. I mean, yes, but this answer doesn't do that. It uses the pipe `|` character. So it doesn't answer the question.
nosklo
@nosklo: The answer specifically mentions the Unix concept of a *pipe*, which is not the same as the `|` character (which, ambiguously, can be commonly called "pipe"). You responded: "using pipe means data goes a single way". I was merely trying to clarify that, while the specific application of the concept of pipes (using `|`) in the answer doesn't completely cover the OP's question, the concept itself is in fact correct.
Daniel Pryden