更多内容可以访问我的个人博客。
问题:在原来测试版本的项目中,专业人员使用Mathematics编写算法,项目组使用JavaWeb项目直接调用Mathematics程序执行Mathematics脚本获取算法结果,极大地影响了系统的性能,同时占用服务器资源,难以应付多并发的情况
解决方案:将原本使用Mathematics编写的算法代码使用Python实现(涉及矩阵、线性拟合等操作,使用Python实现方便),再在原本的JavaWeb项目中调用这个算法。
本篇博客主要介绍几种在Java中调用Python程序的方法。
1. Jython方式调用
Jython是一个Python语言在Java中的完全实现(详细解释看另一篇博客Python语法基础的第一部分)。Jython也有很多从CPython中继承的模块库。最有趣的事情是Jython不像CPython或其他任何高级语言,它提供了对其实现语言的一切存取。所以Jython不仅给你提供了Python的库,同时也提供了所有的Java类(反射使Jython能无缝地使用任何Java类。)。这使其有一个巨大的资源库。
虽然上述网络上对Jython的描述看似很美好,但在实际使用的过程中会遇到很多的问题。最大的问题就是Jython在2015年停止更新,目前最新的是 Jython 2.7.0 Final Released(May 2015)。这就会导致Jython无法使用一些新的CPython库。当你只是想要使用Jython编写一些与Java程序混合的、简单的代码时是比较简单的——但是**当你的程序需要导入很多外部库时,Jython总会出现问题。**而且Jython的运行效率也不快。种种原因,最终没有使用Jython。
- 在Java中使用Jython调用Python中的方法:
首先加入Jython包,这里就有第一个坑,要注意添加的是jython-2.7-b1.jar而不是jython.jar。
import java.io.IOException;
import org.python.core.Py;
import org.python.core.PyFunction;
import org.python.core.PyObject;
import org.python.core.PySystemState;
import org.python.util.PythonInterpreter;
public class JythonMethod {
public static void main(String[] args) throws IOException {
PySystemState sys = Py.getSystemState();
System.out.println(sys.path.toString());
//由于Jython和JVM的ClassPath不一样,所以需要手动加入项目所需的库文件路径
sys.path.add("xxx\\libs");//项目库文件
sys.path.add("xxx\\Lib");//Python自带库文件
System.out.println(sys.path.toString());
// 1. Python面向函数式编程: 在Java中调用Python函数
String pythonFunc = "./xxx/xxx.py";//Python文件路径
//在JVM中创建一个“Python解释器”对象
PythonInterpreter pi1 = new PythonInterpreter();
// 加载python程序
pi1.execfile(pythonFunc);
// 调用Python程序中的函数
PyFunction pyf = pi1.get("methodName", PyFunction.class);
//写入方法所需的参数,注意要转换为Python的相应类型
PyObject Res = pyf.__call__(Py.newString("xxx1"),Py.newString