在Java项目开发过程中,经常需要借助Python丰富的第三方库完成数据分析、机器学习等特定功能,此时就需要在Java中调用Python脚本并传递必要的参数。Java调用Python脚本传参的核心思路是通过进程调用的方式启动Python解释器,将参数作为命令行参数传递给脚本,脚本内部再解析这些参数完成业务逻辑。

两种主流调用方式及传参实现
Java中调用外部程序主要有两种方式,分别是使用Runtime.getRuntime().exec()和ProcessBuilder类,两种方式都支持传递参数给Python脚本。
1. 使用Runtime方式传参
Runtime类的exec方法可以直接执行命令行指令,我们可以将Python脚本路径和参数拼接成命令行字符串,或者拆分为字符串数组传递,后者可以避免空格等特殊字符导致的问题。
首先准备一个简单的Python测试脚本,用于接收并打印传递的参数:
import sys
# 获取传递的参数,sys.argv[0]是脚本名称,从索引1开始是实际传递的参数
params = sys.argv[1:]
print("接收到的参数列表:", params)
for idx, param in enumerate(params):
print(f"第{idx+1}个参数:{param}")
下面是Java使用Runtime调用该脚本并传参的代码示例:
import java.io.BufferedReader;
import java.io.InputStreamReader;
public class JavaCallPythonDemo {
public static void main(String[] args) {
try {
// 定义Python脚本路径
String pythonScriptPath = "D:/test/test_script.py";
// 定义要传递的参数,这里传递三个参数
String param1 = "hello";
String param2 = "java";
String param3 = "python";
// 将命令和参数拆分为数组,避免空格问题
String[] command = new String[]{
"python",
pythonScriptPath,
param1,
param2,
param3
};
// 执行命令
Process process = Runtime.getRuntime().exec(command);
// 读取Python脚本的输出
BufferedReader reader = new BufferedReader(new InputStreamReader(process.getInputStream(), "UTF-8"));
String line;
while ((line = reader.readLine()) != null) {
System.out.println("Python输出:" + line);
}
// 等待进程执行完成
int exitCode = process.waitFor();
System.out.println("Python脚本执行完成,退出码:" + exitCode);
} catch (Exception e) {
e.printStackTrace();
}
}
}
2. 使用ProcessBuilder方式传参
ProcessBuilder相比Runtime更加灵活,支持设置工作目录、环境变量等,传参方式也更为清晰,同样是将参数依次添加到命令列表中。
还是使用上面的Python测试脚本,Java端使用ProcessBuilder的实现如下:
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.List;
public class ProcessBuilderDemo {
public static void main(String[] args) {
try {
// Python脚本路径
String scriptPath = "D:/test/test_script.py";
// 构建命令列表,第一个是python解释器,第二个是脚本路径,后面依次是参数
List<String> commandList = new ArrayList<>();
commandList.add("python");
commandList.add(scriptPath);
commandList.add("参数1");
commandList.add("参数2");
commandList.add("123");
// 创建ProcessBuilder实例
ProcessBuilder processBuilder = new ProcessBuilder(commandList);
// 可选:设置工作目录
// processBuilder.directory(new File("D:/test"));
// 启动进程
Process process = processBuilder.start();
// 读取输出
BufferedReader reader = new BufferedReader(new InputStreamReader(process.getInputStream(), "UTF-8"));
String line;
while ((line = reader.readLine()) != null) {
System.out.println("脚本输出:" + line);
}
// 读取错误流,避免进程阻塞
BufferedReader errorReader = new BufferedReader(new InputStreamReader(process.getErrorStream(), "UTF-8"));
while ((line = errorReader.readLine()) != null) {
System.out.println("错误输出:" + line);
}
int exitCode = process.waitFor();
System.out.println("执行结束,退出码:" + exitCode);
} catch (Exception e) {
e.printStackTrace();
}
}
}
Python脚本接收参数的注意事项
Python脚本中通过sys.argv接收参数时,所有参数都会被当作字符串类型,如果需要其他类型需要手动转换。如果参数中包含空格或者特殊字符,Java传递时不需要额外处理,只要保证参数作为独立的元素放在命令数组中即可,Python会自动正确接收。
如果传递的参数数量不固定,可以在Java中动态构建命令数组,将参数依次添加到列表中,再传递给ProcessBuilder或者Runtime的exec方法。
两种调用方式的对比
| 对比项 | Runtime方式 | ProcessBuilder方式 |
|---|---|---|
| 灵活性 | 较低,不支持直接设置工作目录和环境变量 | 较高,支持设置工作目录、环境变量等配置 |
| 参数处理 | 支持字符串或数组形式传参 | 仅支持列表形式传参,参数管理更清晰 |
| 错误流处理 | 需要手动获取错误流 | 可以重定向错误流到标准输出 |
| 适用场景 | 简单的脚本调用场景 | 复杂的调用场景,需要自定义环境配置 |
常见问题及解决方法
- 如果提示找不到python命令,需要检查Python是否已经添加到系统环境变量,或者使用Python解释器的完整路径,比如
C:/Python39/python.exe。 - 如果参数中包含中文出现乱码,需要保证Java端和Python端的编码一致,Java读取输出时指定UTF-8编码,Python脚本开头可以添加
# -*- coding: utf-8 -*-声明编码。 - 如果脚本执行后没有输出,可能是错误流没有读取导致进程阻塞,需要同时读取标准输出流和错误流。
JavaPython脚本传参ProcessBuilderRuntime修改时间:2026-07-08 06:45:28