zoukankan      html  css  js  c++  java
  • python调用java--JPype

    JPype 是一个能够让 python 代码方便地调用 Java 代码的工具,从而克服了 python 在某些领域(如服务器端编程)中的不足。
    JPype 的使用
    一个简单的 hello world 程序
    下面是一个简单的 python 程序,通过 JPype 调用 Java 的打印函数,打印出字符串。
    1. hello world

    import jpype
    jvmPath = jpype.getDefaultJVMPath()
    jpype.startJVM(jvmPath)
    jpype.java.lang.System.out.println( “ hello world! ” )
    jpype.shutdownJVM()

    启动 JVM
    JPype 提供的 startJVM() 函数的作用是启动 JAVA 虚拟机,所以在后续的任何 JAVA 代码被调用前,必须先调用此方法启动 JAVA 虚拟机。
    jpype.startJVM() 的定义

    startJVM(jvm, *args)
    jpype.startJVM() 的参数
    参数 1: jvm, 描述你系统中 jvm.dll 文件所在的路径,如“ C:Program FilesIBMJava50jreinj9vmjvm.dll ”。可以通过调用 jpype.getDefaultJVMPath() 得到默认的 JVM 路径。
    参数 2: args, 为可选参数,会被 JPype 直接传递给 JVM 作为 Java 虚拟机的启动参数。此处适合所有合法的 JVM 启动参数,例如:

    -agentlib:libname[=options]
    -classpath classpath
    -verbose
    -Xint
    2. jpype.startJVM() 的用法示例

    import jpype
    jvmPath = jpype.getDefaultJVMPath()
    jvmArg = “ -Xint ”
    jpype.startJVM(jvmPath,jvmArg)
    判断 JVM 是否启动
    JPype 提供的 jpype.isJVMStarted() 函数的作用是判断 JVM 是否已启动。
    jpype.isJVMStarted() 的定义
    isJVMStarted()
    jpype.isJVMStarted() 的返回值
    返回值为 True 表示 JVM 已经启动,返回值为 False 表示 JVM 还未启动
    3. jpype.isJVMStarted() 的用法示例

    import jpype
    jvmPath = jpype.getDefaultJVMPath()
    jvmArg = “ -Xint ”
    if not jpype.isJVMStarted():
    jpype.startJVM(jvmPath,jvmArg)

    关闭 JVM
    当使用完 JVM 后,可以通过 jpype.shutdownJVM() 来关闭 JVM,该函数没有输入参数。当 python 程序退出时,JVM 会自动关闭。
    引用第三方的 Java 扩展包
    很多时候,在 python 项目中需要调用第三方的 Java 扩展包,这也是 JPype 的一个重要用途。为了使编程者方便地在 python 代码中调用已有的 Java 扩展包,我们可以再在 JVM 启动参数增加:
    -Djava.class.path=ext_classpath
    以下为调用第三方 Java 扩展包示例,(假设第三方 Java 扩展包的所在路径是 E:JavaExt)
    4. 调用第三方 Java 扩展包示例

    import jpype
    jvmPath = jpype.getDefaultJVMPath()
    ext_classpath = “ E:\JavaExt ”
    jvmArg = “ -Djava.class.path = ” + ext_classpath
    if not jpype.isJVMStarted():
    jpype.startJVM(jvmPath, jvmArg)
    访问 Java 的系统属性
    有时,某些 Java 应用需要设置或者获取 JVM 中的系统属性。
    在 JVM 启动时设置系统变量示例:
    在 JVM 的启动参数中加入如下参数:
    -Dproperty=value
    假设你要设置的属性名为 yourProperty,属性值为 yourValue 。
    5. JVM 启动时设置系统变量示例

    import jpype
    jvmPath = jpype.getDefaultJVMPath()
    jvmArg = “ -DyourProperty=yourValue ”
    if not jpype.isJVMStarted():
    jpype.startJVM(jvmPath,jvmArg)
    6. 在程序中设置系统变量示例

    import jpype
    prop = “ yourProperty ”
    value = “ yourValue ”
    system = jpype.JClass('java.lang.System')
    system.setProperty(str(prop),str(value))
    7. 在程序中获取系统变量示例

    import jpype
    prop = “ yourProperty ”
    system = jpype.JClass('java.lang.System')
    value = system.getProperty(str(prop))

    1. Java 类型到 python 类型的转换
    Java 类型 转换成的 python 类型
    byte, short and int int
    long long
    float and double float
    boolean int of value 1 or 0
    char unicode of length 1
    String unicode
    arrays JArray
    other Java object JavaObject
    Class JavaClass
    array Class JavaArrayClass
    使用 Java 对象
    8. Java 类定义

    package src.com.ibm.javaproject;

    public class JavaClass {
    public String value = "";

    /**
    * Creates a new JavaClass object.
    *
    * @param value
    */
    public JavaClass(String value) {
    this.value = value;
    }

    public String getValue() {
    return this.value;
    }

    public void setValue(String val) {
    this.value = val;
    }
    }
    对于上述的 Java 类,以下的代码介绍了如何在 Python 中构造并且使用相应的对象。 首先是获得对应 Java 类:
    9. 获得对应 Java 类

    import jpype
    javaClass = jpype.JClass('src.com.ibm.javaproject.JavaClass')
    调用 Java 类的构造函数生成实例:
    10. 调用 Java 类的构造函数生成实例

    value = “ oldvalue ”
    javaInstance = javaClass(value)
    调用 Java 方法:
    11. 调用 Java 方法

    print javaInstance.getValue()
    javaInstance.setValue( “ newvalue ” )
    print javaInstance.getValue()
    运行结果:
    12. Python 代码的运行结果

    oldvalue
    newvalue
    Java exception 错误处理
    异常处理是程序编写者们必须考虑的问题,在使用 JPype 的过程中,所有的 Java exception 将被自动转换成 jpype.JavaException 。 以下是 Jpype 处理 Java exception 的示例:
    13. 处理 Java exception

    from jpype import JavaException
    try:
    #Code that throws a java.lang.RuntimeException
    except JavaException, ex:
    if JavaException.javaClass() is java.lang.RuntimeException:
    print "Caught the runtime exception : ", JavaException.message()
    print JavaException.stackTrace()
    应用实例(Password Cipher)
    下面我们用一个简单的应用实例来说明如何在 python 代码中调用 Java 类。
    Java 类定义
    假设我们已用 Java 语言编写了一个类:PasswordCipher,该类的功能是对字符串进行加密和解密。它提供了一个对外的接口 run() 函数,定义如下 :
    14. PasswordCipher 定义

    public class PasswordCipher {
    ……
    public static String run(String action, String para){
    ……
    }
    ……
    }
    run 函数接收两个参数,第一个参数代表所要进行的操作,传入“ encrypt ”表示对第二个参数 para 做加密操作,返回加密结果。如果第一个参数为“ decrypt ”则返回对 para 的解密操作的结果。在 run 函数中有可能会有异常抛出。
    Python 代码
    我们先将 PasswordCipher.class 存放在目录“ F: estcipher ”下,然后用 python 语言编写下面的代码:
    15. Python 代码

    import jpype
    from jpype import JavaException

    jvmPath = jpype.getDefaultJVMPath() #the path of jvm.dll
    classpath = "F:\test\cipher" #the path of PasswordCipher.class
    jvmArg = "-Djava.class.path=" + classpath
    if not jpype.isJVMStarted(): #test whether the JVM is started
    jpype.startJVM(jvmPath,jvmArg) #start JVM
    javaClass = jpype.JClass("PasswordCipher") #create the Java class
    try:
    testString = "congratulations"
    print "original string is : ", testString
    #call the run function of Java class
    encryptedString = javaClass.run("encrypt", testString)
    print "encrypted string is : ", encryptedString

    #call the run function of Java class

    decryptedString = javaClass.run("decrypt", encryptedString)
    print "decryped string is : ", decryptedString
    except JavaException, ex:
    print "Caught exception : ", JavaException.message()
    print JavaException.stackTrace()
    except:
    print "Unknown Error"
    finally:
    jpype.shutdownJVM() #shut down JVM
    运行该程序后得到的结果:
    16. 该程序运行的结果是:

    original string is : congratulations
    encrypted string is : B0CL+niNYwJLgx/9tisAcQ==
    decryped string is : congratulations

  • 相关阅读:
    Spring bean
    spring bean初始化及销毁你必须要掌握的回调方法
    一张图搞懂Spring bean的完整生命周期
    获取Spring的ApplicationContext的几种方式
    你必须了解Spring的生态
    Spring的核心模块解析
    Spring 5.0
    纯分享scp协议如何工作
    我眼中的SAML (Security Assertion Markup Language)
    7z文件格式及其源码的分析(五)
  • 原文地址:https://www.cnblogs.com/niansi/p/7788830.html
Copyright © 2011-2022 走看看