Java 调用 python 的接口
2018-03-06 10:55
295 查看
不管什么技术,不管什么问题,只要努力就能解决。 最近在做项目的时候,需要java 调用 python 接口,在网上找了一些方法,但是总碰到一些问题,索性将网上的方法和自己的理解总结一下,希望对各位博友有所帮助,也请各位大神不吝赐教。
一:创建环境 Python 环境
import org.python.util.PythonInterpreter; import java.util.Properties; /** * Jython环境,获取Python的实例 * @author webim * */ public class JythonEnvironment { //定义一个静态变量 private static JythonEnvironment INSTANCE = new JythonEnvironment(); /** * 私有构造方法 */ private JythonEnvironment() { } /** * 获取单例 * @return JythonEnvironment */ public static JythonEnvironment getInstance() { return INSTANCE; } /** * 获取python解释器 * @return PythonInterpreter */ public PythonInterpreter getPythonInterpreter() { Properties props = new Properties(); props.put("python.home","path to the Lib folder"); props.put("python.console.encoding", "UTF-8"); // Used to prevent: console: Failed to install '': java.nio.charset.UnsupportedCharsetException: cp0. props.put("python.security.respectJavaAccessibility", "false"); //don't respect java accessibility, so that we can access protected members on subclasses props.put("python.import.site","false"); Properties preprops = System.getProperties(); //对 python 进行初始化 PythonInterpreter.initialize(preprops, props, new String[0]); PythonInterpreter inter = new PythonInterpreter(); return inter; } }在创建 python 解释器之前,需要初始化 python 环境,参考过一些例子,是没有进行初始化,会进行报下列错误。org.python.core.PyException: nullat org.python.core.Py.ImportError(Py.java:330) ~[jython-2.7.1b3.jar:na]at org.python.core.Py.importSiteIfSelected(Py.java:1577) ~[jython-2.7.1b3.jar:na]at org.python.util.PythonInterpreter.<init>(PythonInterpreter.java:116) ~[jython-2.7.1b3.jar:na]at org.python.util.PythonInterpreter.<init>(PythonInterpreter.java:94) ~[jython-2.7.1b3.jar:na]at org.python.util.PythonInterpreter.<init>(PythonInterpreter.java:71) ~[jython-2.7.1b3.jar:na]at com.sihuatech.puzzlevideo.manage.controller.AAlarmController.getAllAlarmInfo(AAlarmController.java:85) ~[classes/:na]at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[na:1.8.0_152]at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) ~[na:1.8.0_152]at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[na:1.8.0_152]at java.lang.reflect.Method.invoke(Method.java:498) ~[na:1.8.0_152]at org.springframework.web.method.support.InvocableHandlerMethod.doInvoke(InvocableHandlerMethod.java:205) ~[spring-web-4.3.14.RELEASE.jar:4.3.14.RELEASE]at org.springframework.web.method.support.InvocableHandlerMethod.invokeForRequest(InvocableHandlerMethod.java:133) ~[spring-web-4.3.14.RELEASE.jar:4.3.14.RELEASE]at org.springframework.web.servlet.mvc.method.annotation.ServletInvocableHandlerMethod.invokeAndHandle(ServletInvocableHandlerMethod.java:97) ~[spring-webmvc-4.3.14.RELEASE.jar:4.3.14.RELEASE]at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.invokeHandlerMethod(RequestMappingHandlerAdapter.java:827) ~[spring-webmvc-4.3.14.RELEASE.jar:4.3.14.RELEASE]at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.handleInternal(RequestMappingHandlerAdapter.java:738) ~[spring-webmvc-4.3.14.RELEASE.jar:4.3.14.RELEASE]at org.springframework.web.servlet.mvc.method.AbstractHandlerMethodAdapter.handle(AbstractHandlerMethodAdapter.java:85) ~[spring-webmvc-4.3.14.RELEASE.jar:4.3.14.RELEASE]at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:967) ~[spring-webmvc-4.3.14.RELEASE.jar:4.3.14.RELEASE]at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:901) ~[spring-webmvc-4.3.14.RELEASE.jar:4.3.14.RELEASE]at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:970) [spring-webmvc-4.3.14.RELEASE.jar:4.3.14.RELEASE]at org.springframework.web.servlet.FrameworkServlet.doPost(FrameworkServlet.java:872) [spring-webmvc-4.3.14.RELEASE.jar:4.3.14.RELEASE]at javax.servlet.http.HttpServlet.service(HttpServlet.java:661) [tomcat-embed-core-8.5.27.jar:8.5.27]at org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:846) [spring-webmvc-4.3.14.RELEASE.jar:4.3.14.RELEASE]at javax.servlet.http.HttpServlet.service(HttpServlet.java:742) [tomcat-embed-core-8.5.27.jar:8.5.27]
二:调用 python 的接口
因为 python 和 java是两种不同的语言,因此在项目的 controller 、service 和 mapper 中直接出现 Python 的接口,因此自己封装 ExecPython 类,封装python的接口,目的让 python 接口和java程序分隔开。import org.python.core.PyFunction;import org.python.core.PyObject;import org.python.util.PythonInterpreter;import org.slf4j.Logger;import org.slf4j.LoggerFactory;import org.springframework.beans.factory.annotation.Value;import org.springframework.stereotype.Component;import org.springframework.stereotype.Service;import java.util.Map;/*enum的这个用法,可以作为变种的安全单例,值得借鉴哦 ^_^ */@Service@Componentpublic class ExecPython {public static final Logger logger = LoggerFactory.getLogger(Exception.class);//定义 python 解释器private static PythonInterpreter inter;public ExecPython() {this.inter = JythonEnvironment.getInstance().getPythonInterpreter();this.inter.execfile("C:\\test.py");}//设置 python 脚本的路径public void setPythonPath (String pythonPath){this.inter.execfile(pythonPath);}public void execute(String scriptFile, Map<String,String> properties){logger.info("获取解释器");try{PyFunction getNetInfo = (PyFunction) inter.get("getNetInfo", PyFunction.class);PyObject netInfo = getNetInfo.__call__();System.out.println("anwser = " + netInfo.toString());}catch (Exception e){e.printStackTrace();logger.info("Python 脚本文件执行失败");}}//获取 Python 字符串public String getString(){
//获取到python 脚本中的接口 PyFunction func = (PyFunction) inter.get("adder", PyFunction.class); PyObject pyobj = func.__call__(); System.out.println("anwser = " + pyobj.toString()); return pyobj.toString(); } // 获取当前数组 public String getArr() { PyFunction getArr = (PyFunction) inter.get("getArr", PyFunction.class); PyObject pyobjTwo = getArr.__call__(); pyobjTwo.__len__(); System.out.println("anwser = " + pyobjTwo.toString()+" len:"+pyobjTwo.__len__()); //将 PyObject 对象转换成 java 对象 //Object object = pyobjTwo.__tojava__(List.class); //List<String> list = (List<String>) object; //将查询到数据转换成一个 JSON 字符串 String result = pyobjTwo.toString(); String JsonStr = "{" + result + "}"; logger.info(JsonStr); logger.info("将查询的结果转换成 JSON 字符串:",JsonStr); return pyobjTwo.toString(); } }
三: python 脚本
def adder(): return "{'name':'leilei','age':'18'}" def getArr():return ['aaa','bbb']def getNetInfo():return [{'DNS':'192.168.12.3','ip':'45.23.16.0'},{'DNS2':'192.168.12.2','ip2':'45.23.16.2'}]相关文章推荐
- eoLinker-API_Shop_短信服务接口-调用示例代码,支持PHP、Python、Java等语言
- java调用python的webservice
- Java如何通过URL调用远程接口并读取返回信息?
- python下调用淘宝top接口例子
- ICTCLAS分词系统Java调用接口在Eclipse中的安装- Java编程
- python下调用淘宝top接口例子
- ICTCLAS分词系统Java调用接口在Eclipse中的安装
- 怎么根据linux c/c++ 开发的d-bus服务生成java 的调用接口文件
- DB2数据库、触发器、存储过程、JAVA数据库链接(JDBC)、调用层接口(CLI)
- Java调用本地接口jni与C通信----------------JNI
- Java 中通过jni接口调用native code
- Java调用webservice接口方法
- Python调用C/C++的接口(Boost)
- PY++ 自动将你的C++程序接口封装供python调用
- JAVA如何调用VOS2009接口
- 关于Java中Scanner对象的hasNext()方法对实现Readable接口的对象中的read()方法调用的探讨
- 《Java 本地接口规范》- 调用 API
- JAVA调用支付宝直充接口
- java通过jni调用C程序接口
- ICTCLAS分词系统Java调用接口在Eclipse中的安装 http://blog.csdn.net/CloneIQ/archive/2006/07/20/945909.aspx