我使用 Rust 来加速数据处理管道,但我必须按原样运行一些现有的 Python 代码,我想并行化这些代码。在另一个 question 中讨论,鉴于我的项目的特定约束,创建多个 Python 进程是一种可能的方法。但是,运行下面的代码会产生无限循环。我不太明白为什么。
use cpython::Python;
fn main() {
let gil = Python::acquire_gil();
let py = gil.python();
py.run(r#"
import sys
from multiprocessing import Process
def f(name):
print('hello', name)
if __name__ == '__main__':
print('start')
sys.argv=['']
p = Process(target=f, args=('bob',))
p.start()
p.join()
"#, None,None).unwrap();
}
输出(一直持续到 Ctrl-C):
start
start
start
start
start
start
start
start
编辑
正如下面评论中提到的,我放弃了尝试从 Python 代码创建进程。 Windows、Python 多处理模块以及如何使用 Rust 创建进程之间的干扰太模糊而无法正确管理。
因此,我将从 Rust 创建和管理它们。因此,该代码更具教科书:
use std::process::Command;
fn main() {
let mut cmd = Command::new("python");
cmd.args(&["-c", "print('test')"]);
let process = cmd.spawn().expect("Couldn't spawn process.");
println!("{:?}", process.wait_with_output().unwrap());
}
最佳答案
我无法重现这个;对我来说它只是打印start
然后 hello bob
正如预期的那样。无论出于何种原因,在您的情况下,__name__
总是等于 "__main__"
你得到这个无限递归。我在 Arch Linux 上使用 cpython crate 版本 v0.4.1 和 Python 3.8.1。
解决方法是不依赖 __name__
完全没有,而是将您的 Python 代码定义为带有 main()
的模块。函数,然后调用该函数:
use cpython::{Python, PyModule};
fn main() {
let gil = Python::acquire_gil();
let py = gil.python();
let module = PyModule::new(py, "bob").unwrap();
py.run(r#"
import sys
from multiprocessing import Process
def f(name):
print('hello', name)
def main():
print('start')
sys.argv=['']
p = Process(target=f, args=('bob',))
p.start()
p.join()
"#, Some(&module.dict(py)), None).unwrap();
module.call(py, "main", cpython::NoArgs, None).unwrap();
}
关于python - 在 Rust 中使用 python 的多处理库,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/60391839/