用Jython实现解释执行的Java类
(转载请注明来源于 金庆的专栏)
用Jython可以实现预编译成Java字节流的Java类,需用Jythonc进行编译。
不过更方便的用法是直接用Jython实现嵌入式的类,不需要编译。
一方面是编译很麻烦,另一面预编译并没有带来速度上的优势。
Jythonc编译程序在Jython2.3版中将不再包含。
JDK6已经新增了脚本引擎,可以使用JavaScript,不过使用Jython脚本更令人激动。
本例jyinterface项目包含4个文件:
-Main.java
-EmployeeType.java 对象接口定义
-Employee.py Python实现
-EmployeeFactory.java 对象工厂,生成一个Java对象
//
EmployeeType.java
package
jyinterface.interfaces;


public
interface
EmployeeType
...
{
publicStringgetEmployeeFirst();
publicStringgetEmployeeLast();
publicStringgetEmployeeId();
}
#
Employee.py
from
jyinterface.interfaces
import
EmployeeType

class
Employee(EmployeeType):
def
__init__
(self,first,last,id):
self.first
=
first
self.last
=
last
self.id
=
id

def
getEmployeeFirst(self):
return
self.first

def
getEmployeeLast(self):
return
self.last

def
getEmployeeId(self):
return
self.id
//
EmployeeFactory.java
package
jyinterface.factory;

import
jyinterface.interfaces.EmployeeType;
import
org.python.core.Py;
import
org.python.core.PyObject;
import
org.python.core.PyString;
import
org.python.util.PythonInterpreter;


public
class
EmployeeFactory
...
{


publicEmployeeFactory()...{
PythonInterpreterinterpreter=newPythonInterpreter();
interpreter.exec("fromEmployeeimportEmployee");
jyEmployeeClass=interpreter.get("Employee");
}


publicEmployeeTypecreate(Stringfirst,Stringlast,Stringid)...{
PyObjectpyObj=jyEmployeeClass.__call__(newPyString(first),
newPyString(last),newPyString(id));
return(EmployeeType)pyObj.__tojava__(EmployeeType.class);
}

privatePyObjectjyEmployeeClass;
}
注意:Employee.py必须在sys.path路径,这样才能导入。
如将Employee.py放在运行目录,并在jython的registry文件中的python.path添加“.”。
或直接放在jython的Lib目录下。
//
Main.java
package
jyinterface;

import
jyinterface.factory.EmployeeFactory;
import
jyinterface.interfaces.EmployeeType;


public
class
Main
...
{


privatestaticvoidprint(EmployeeTypeemployee)...{
System.out.println("Name:"+employee.getEmployeeFirst()+""
+employee.getEmployeeLast());
System.out.println("Id:"+employee.getEmployeeId());
}


publicstaticvoidmain(String[]args)...{
EmployeeFactoryfactory=newEmployeeFactory();
print(factory.create("Josh","Juneau","1"));
print(factory.create("Charlie","Groves","2"));
}
}
参考:
[1] Accessing Jython from Java Without Using jythonc
[2] Simple and Efficient Jython Object Factories
[2]中会产生一个类型转换错误:
return (EmployeeType)jyEmployeeClass.__call__(...
PyObject应该不能直接转成java对象的,不知作者为什么会这样。
[1]使用execfile()来运行py文件,也可以转成exec("import " + module)
以避免每生成一个对象就运行一遍。
但是也有好处,即可以实时更改py文件立即生效。
而import的文件会缓存,必须显示调用reload()才会重新导入。
Python/C的内嵌接口中好像没有__tojava__()这样的函数,能在语言之间转换对象类型。
看上去只能处理PyObject对象.
(还在摸索中,用Python扩展C++接口应该可以实现。可能boost::python会有。)
(转载请注明来源于 金庆的专栏)
用Jython可以实现预编译成Java字节流的Java类,需用Jythonc进行编译。
不过更方便的用法是直接用Jython实现嵌入式的类,不需要编译。
一方面是编译很麻烦,另一面预编译并没有带来速度上的优势。
Jythonc编译程序在Jython2.3版中将不再包含。
JDK6已经新增了脚本引擎,可以使用JavaScript,不过使用Jython脚本更令人激动。
本例jyinterface项目包含4个文件:
-Main.java
-EmployeeType.java 对象接口定义
-Employee.py Python实现
-EmployeeFactory.java 对象工厂,生成一个Java对象

























































注意:Employee.py必须在sys.path路径,这样才能导入。
如将Employee.py放在运行目录,并在jython的registry文件中的python.path添加“.”。
或直接放在jython的Lib目录下。
























参考:
[1] Accessing Jython from Java Without Using jythonc
[2] Simple and Efficient Jython Object Factories
[2]中会产生一个类型转换错误:
return (EmployeeType)jyEmployeeClass.__call__(...
PyObject应该不能直接转成java对象的,不知作者为什么会这样。
[1]使用execfile()来运行py文件,也可以转成exec("import " + module)
以避免每生成一个对象就运行一遍。
但是也有好处,即可以实时更改py文件立即生效。
而import的文件会缓存,必须显示调用reload()才会重新导入。
Python/C的内嵌接口中好像没有__tojava__()这样的函数,能在语言之间转换对象类型。
看上去只能处理PyObject对象.
(还在摸索中,用Python扩展C++接口应该可以实现。可能boost::python会有。)