通过Python获取MAPLE的输出

3 投票
3 回答
2224 浏览
提问于 2025-04-15 17:57

我想知道如何在Python中使用subprocess模块来启动一个命令行的MAPLE实例,以便将数据传给它并获取输出回到主代码中。例如,我想要:

X = '1+1;'
print MAPLE(X)

返回“2”的值。

我见过的最好的方法是使用SAGE来包装MAPLE的命令,但我不想为了我的需求去安装和使用SAGE,这样会增加额外的负担。

3 个回答

0

这里有一个示例,展示了如何在命令行程序中进行互动输入输出。我用类似的方法构建了一个基于ispell命令行工具的拼写检查器:

f = popen2.Popen3("ispell -a")
f.fromchild.readline() #skip the credit line

for word in words:
    f.tochild.write(word+'\n') #send a word to ispell
    f.tochild.flush()

    line = f.fromchild.readline() #get the result line
    f.fromchild.readline() #skip the empty line after the result

    #do something useful with the output:
    status = parse_status(line)
    suggestions = parse_suggestions(line)
    #etc..

这个方法唯一的问题是,它非常脆弱,很多时候需要反复尝试才能确保你输入的内容没有问题,并且能够处理程序可能产生的各种输出。

3

在尝试“交互式”地驱动一个子进程时,常常会遇到一些问题,比如子进程会进行缓冲,这样就会导致一些操作被阻塞。

所以我建议使用 pexpect(在Windows上用 wexpect),因为它就是为了这个目的而设计的——让你的程序能够模拟一个人类用户在终端/控制台中输入命令和查看结果。

3

我参考了Alex Martelli的建议(谢谢他!),得出了一个明确的答案。把这个分享出来,希望对其他人也有帮助:

import pexpect
MW = "/usr/local/maple12/bin/maple -tu"
X = '1+1;'
child = pexpect.spawn(MW)
child.expect('#--')
child.sendline(X)
child.expect('#--')
out = child.before
out = out[out.find(';')+1:].strip()
out = ''.join(out.split('\r\n'))
print out

输出的解析是必要的,因为MAPLE会把很长的输出分成多行。这种方法的好处是可以保持与MAPLE的连接,以便将来进行计算。

撰写回答