实际工程项目中可能会用到 Java 和 python 两种语言结合进行,这样就会涉及到一个问题,就是怎么用 Java 程序来调用已经写好的 python 脚本呢,一共有四种方法可以实现:
1、在 java 类中直接执行 python 语句
此方法需要引用 org.python包,需要下载Jpython。
Jython 是一种完整的语言,而不是一个Java翻译器或仅仅是一个Python编译器,它是一个 Python 语言在 Java 中的完全实现。
Jython 是在 JVM 上实现的 Python,由 Java 编写。Jython 将 Python 源码编译成JVM字节码,由 JVM 执行对应的字节码
。因此能很好的与JVM集成,比如利用JVM的垃圾回收和JIT,直接导入并调用JVM上其他语言编写的库和函数。 既然 Jython 是 Python 语言在 Java 平台的实现,是 Java 语言实现的,那么可以在 Jython 程序中调用Java,也能在 Java 中调用 Jython
。 Jython 也有很多从 CPython 中继承的模块库。最有趣的事情是 Jython 不像 CPython 或其他任何高级语言,它提供了对其实现语言的一切存取。所以Jython 不仅给你提供了 Python 的库,同时也提供了所有的 Java 类
,这使其有一个巨大的资源库。
(1)使用 maven 添加依赖
代码语言:javascript复制<dependency>
<groupId>org.python</groupId>
<artifactId>jython-standalone</artifactId>
<version>2.7.0</version>
</dependency>
Jetbrains全家桶1年46,售后保障稳定
(2)使用 PythonInterpreter 执行 Python 语句
代码语言:javascript复制PythonInterpreter interp = new PythonInterpreter();
// 执行Python程序语句
interp.exec("import sys");
interp.set("a", new PyInteger(42));
interp.exec("print a");
interp.exec("x = 2 2");
PyObject x = interp.get("x");
System.out.println("x: " x);
输出结果如下:
代码语言:javascript复制42
x: 4
Java 通过 Jython API 执行Python语句,相当于在Java中嵌入了Python程序,这种用法不常见,也没有太大的实际意义。
2、 在 java 中调用 python 脚本
(1)不需要传递参数,也不接收返回值
首先在本地建立一个 python 脚本,命名为 simple_python.py,写了一个简单函数,代码如下:
代码语言:javascript复制#coding=utf-8
print("Do simple thing in Python")
print("输出中文")
Python 的默认编码文件是用的 ASCII 码,因此文件中有中文时在文件开头加入 #coding=utf-8
在Java中简单调用Python程序,不需要传递参数,也不需要获取返回值:
代码语言:javascript复制String python = "E:\Programming\PyCharm\Java\javatest1.py";
PythonInterpreter interp = new PythonInterpreter();
interp.execfile(python);
interp.cleanup();
interp.close();
执行结果:
(2)需要传递参数,并接收返回值
首先在本地建立一个 python 脚本,命名为 add.py,写了一个简单的两个数做加法的函数,代码如下:
代码语言:javascript复制def add(a,b):
return a b
python的功能函数已经写好,接下来我们写一个java的测试类(同样需要用到Jpython包),来测试一下是否可以运行成功。代码如下:
代码语言:javascript复制import org.python.core.PyFunction;
import org.python.core.PyInteger;
import org.python.core.PyObject;
import org.python.util.PythonInterpreter;
public class Java_Python_test {
public static void main(String[] args) {
// TODO Auto-generated method stub
PythonInterpreter interpreter = new PythonInterpreter();
interpreter.execfile("D:\add.py");
// 第一个参数为需要执行的函数(变量)的名字,第二个参数为期望返回的对象类型
PyFunction pyFunction = interpreter.get("add", PyFunction.class);
int a = 5, b = 10;
//调用函数,如果函数需要参数,在Java中必须先将参数转化为对应的“Python类型”
PyObject pyobj = pyFunction.__call__(new PyInteger(a), new PyInteger(b));
System.out.println("the anwser is: " pyobj);
}
}
3. 使用 Runtime.getRuntime() 执行脚本文件(推荐)
(1)不需要传递参数,也不接收返回值
先写一个简单的 python 脚本 demo1,代码如下:
代码语言:javascript复制import numpy as np
a = np.arange(12).reshape(3,4)
print(a)
python 程序中用到了numpy第三方库,并初始化了一个3×4的一个矩阵。 在 Java 中使用 Runtime.getRuntime() 方法来调用 python 程序并输出该结果,java 代码如下:
代码语言:javascript复制import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
public class Demo1 {
public static void main(String[] args) {
// TODO Auto-generated method stub
Process proc;
try {
proc = Runtime.getRuntime().exec("python D:\demo1.py");// 执行py文件
//用输入输出流来截取结果
BufferedReader in = new BufferedReader(new InputStreamReader(proc.getInputStream()));
String line = null;
while ((line = in.readLine()) != null) {
System.out.println(line);
}
in.close();
proc.waitFor();
} catch (IOException e) {
e.printStackTrace();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
输出的结果:
(2)需要传递参数,并接收返回值
先写一个 python 的程序 func.py,代码如下:
代码语言:javascript复制import sys
def func(a,b):
return (a b)
if __name__ == '__main__':
a = []
for i in range(1, len(sys.argv)):
a.append((int(sys.argv[i])))
print(func(a[0],a[1]))
其中
sys.argv 用于获取参数 url1,url2 等
。而sys.argv[0] 代表 python 程序名,所以列表从 1 开始读取参数
。
在 java 中传递函数参数,代码如下:
代码语言:javascript复制import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
public class Demo1 {
public static void main(String[] args) {
// TODO Auto-generated method stub
int a = 18;
int b = 23;
try {
String[] args1 = new String[] {
"python", "D:\demo2.py", String.valueOf(a), String.valueOf(b) };
Process proc = Runtime.getRuntime().exec(args1);// 执行py文件
BufferedReader in = new BufferedReader(new InputStreamReader(proc.getInputStream()));
String line = null;
while ((line = in.readLine()) != null) {
System.out.println(line);
}
in.close();
proc.waitFor();
} catch (IOException e) {
e.printStackTrace();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
其中
args1 是 String[] { “python”, path, url1, url2 }
,path 是 python 程序所在的路径,url1 是参数1,url2 是参数2,以此类推。
执行结果:
版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。
发布者:全栈程序员栈长,转载请注明出处:https://javaforall.cn/198345.html原文链接:https://javaforall.cn