这个将需要一些解释。请耐心等待。
我拥有一些Fortran源代码和一些从该代码编译的二进制文件。我没有进行编译,但是有一个构建脚本,建议G77用来做它。
除了Fortran之外,还有一些Java代码为用户提供围绕二进制文件的GUI“包装器”。它通过输入/输出/错误管道在自身和二进制文件之间传递信息。 Java代码非常混乱,这种做法增加了许多样板和冗余,但是它完成了工作并且我知道它有效。
不幸的是,我想做一些改变:
我想为二进制文件创建一个新的Python包装器(或者更确切地说,扩展现有的Python程序以成为新的包装器)。
我希望能够将Fortran代码编译为现有程序构建过程的一部分。我想使用gfortran,因为MinGW在构建中的其他地方使用,因此它将随时可用。
当我自己使用gfortran编译Fortran代码时,我无法将生成的二进制文件与当前的Java包装器或新的Python包装器“对话”。
以下是我在Fortran代码中尝试打印到控制台的各种方法:
subroutine printA(message)
write(6,*) message
end
subroutine printB(message)
write(*,*) message
end
subroutine printC(message)
use iso_fortran_env
write(output_unit,*) message
end
还有read
个命令,但代码甚至没有更改执行该部分,所以我还没有担心它。
我必须使用-ffixed-line-length-132
标志调用gfortran以便代码编译,但除此之外我不使用任何其他内容。我已经尝试使用-ff2c
标志,模糊地希望它能有所作为。它没有。
这个stackoverflow post提供了丰富的信息,但没有提供任何有效的信息。
relavant manual page表示printA应该可以正常工作。
我正在使用Windows,但需要将其作为多平台。
如果您遇到了Juse,Java代码使用Runtime.getRuntime().exec("prog.exe")
来调用二进制文件,然后使用生成的Process
对象的各种“流”方法来与它们进行通信。 Python代码使用Popen
模块的subprocess
对象提供的等价物。
我还应该说,我知道有其他选择。重写Python中的代码(或其他类似C ++的代码),或进行修改以便可以通过F2Py调用已被排除为选项。使用g77也是不行的;我们有足够的依赖关系。我希望能够使用gfortran正确地向控制台写入/读取,或者知道这是不可能的。
答案 0 :(得分:1)
很难说没有看到Fortran和Python代码中的更多细节。以下代码对我有用(至少在Linux下):
Fortran程序逐行重复输入行,前缀为行号:
program test_communication
use iso_fortran_env, stdout => output_unit, stdin => input_unit
implicit none
character(100) :: buffer
integer :: ii
ii = 1
do while (.true.)
read(stdin, *) buffer
write(stdout, "(I0,A,A)") ii, "|", trim(buffer)
flush(stdout)
ii = ii + 1
end do
end program test_communication
Python程序调用Fortran二进制文件。您可以使用控制台中的任意字符串来提供它。
import subprocess as sub
print "Starting child"
proc = sub.Popen("./a.out", stdin=sub.PIPE, stdout=sub.PIPE)
while True:
send = raw_input("Enter a string: ")
if not send:
print "Exiting loop"
break
proc.stdin.write(send)
proc.stdin.write("\n")
proc.stdin.flush()
print "Sent:", send
recv = proc.stdout.readline()
print "Received:", recv.rstrip()
print "Killing child"
proc.kill()