- 浏览: 6897633 次
- 性别:
- 来自: 武汉
文章分类
最新评论
-
逐客叫我:
看完了懵了,一会原生方法栈一会堆,自己都不用一套。
深入JVM系列(一)之内存模型与内存分配 -
xhwahaha:
import java.util.Arrays;public ...
腾讯的一个面试题 -
j00131120:
总结的非常不错
从员工到总监,你要明白的8个道理 -
Will.Du:
这是thinking in java的例子吧
对象序列化 -
ping22changxin:
能否借你事例源码学习一下,谢谢了:812185421@qq.c ...
ActiveMQ发送ObjectMessage的一个问题
An Introduction to Jython
An Introduction to Jython
BY Mike
Table of Contents
Introduction
Java objects and methods in Jython
Jython import statements
Event handling
Overloaded Java methods
Classes in Jython
Public vs. private variables
Subclassing and inheritance
Simulating interfaces with multiple inheritance
Notes on static final classes
Conclusion
Jython is a version of Python written in Java and designed to run under the JVM. Because of this, it integrates closely with Java, and allows Jython programs access to all of the Java libraries. There are several reasons that Java programmers might be interested in learning Jython:
It provides an alternative to Javascript for interacting with Java, and is in many ways more powerful than Javascript. Most would also agree it is much easier to use than Javascript.
It is very easy to embed the Jython interpretor as a scripting or application control language in your Java applications.
It allows more rapid prototyping, and/or "proof of concept" applications than is possible in Java.
With this very short and brief introduction, lets jump right into some code. In the spirit of programming books, we will start with the very simple "Hello World!" program as it would be written in Jython:
print "Hello, world!"
Of course, the first thing you are likely to notice about this complete Jython program, is how simple it is. Unlike regular Java, Jython does not force us to use object oriented programming if we don't want to. We don't have to enclose our program in a class, or even in a function. In reality, this program is enclosed in a class and also in a function to satisfy the requirements of Java. However, Jython does that behind the scenes so we don't have to worry about it. Now lets look at a slightly more advanced example:
file = open("Test.txt", "r")
for line in file.readlines():
print line
file.close()
There are several significant aspects of Jython to point out here. The first is that it is very loosely typed. We don't have to declare the type of the variable that holds the file object before we can assign to it.
The second is that it demonstrates the use of Jython's for loop, which is different than the for loop you are used to in Java. In Jython, a for loop performs the body of the loop once for each item in a set of items it is given, which is usually a list (array) or tuple. (A tuple is basically an immutable array.) In this case, we have told Jython to place all of the lines in the text file into a list of strings, and then perform the body of the loop once for each string in the list, which of course, simply prints each line of the text file out to the console. This combination of opening the file and iterating over its contents shows how easy and quick it is to create and use objects for common tasks in Jython.
If you want a more traditional for loop in Jython, you can use the range() function, which will give the for loop a range of numbers to iterate over. For example:
for i in range(10):
will repeat the loop from 0 to 9, with i taking on the values of 0 through 9 with each repetition.
The final thing to note here is that in Jython, whitespace is significant. However, before you panic and have flashbacks of FORTRAN, note that Jython's use of whitespace makes a lot of sense. In the example, the body of the for loop is delimited by the start and end of indentation. Jython code blocks are always delimited by indentation rather than braces. So basically, just indent code as you normally would, and Jython's use of whitespace being significant will seem very natural.
Java objects and methods in Jython
Of course, as I mentioned at the start of this article, one of Jython's biggest strengths is its ability to use Java libraries. So lets start with a simple example using Swing components:
from javax.swing import *
frame = JFrame("Hello Jython")
label = JLabel("Hello Jython!", JLabel.CENTER)
frame.add(label)
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE)
frame.setSize(300, 300)
frame.show()
Most of this code will be immediately familiar to Java programmers. The only difference being the syntax differences of not using the new keyword, and of not requiring terminating semicolons. Once again, we also did not have to enclose our program in a class or main method.
Jython import statements
Jython import statements do require a bit more discussion here though since there are several ways we can do it. In the above example, we used the from syntax to import everything from javax.swing using the * wildcard, and we did it in such a way that we can use unqualified names. This is often considered bad style since it pollutes the global namespace. Another way we can do this is to import only what we need. For example, we could have used the following import statement in the above example:
from javax.swing import JFrame, JLabel
Here we can still use the unqualified names when we want to instantiate these classes, but we have also greatly reduced the risk of a name collision by only importing what we needed.
Another way we can import into Jython is by using import without from. For example:
import javax.swing
If we do it this way, we have to use the qualified names. For example, we would need to to type:
label = javax.swing.JLabel("Hello, Jython", javax.swing.JLabel.CENTER)
Although it is more typing, we have avoided polluting the global namespace.
Event handling
Basic event handling in Jython is also significantly easier than in Java. The following example replaces the JLabel with a JButton to show how easy it is:
from javax.swing import *
def hello(event):
print "Hello, world!"
frame = JFrame("Hello Jython")
button = JButton("Hello", actionPerformed = hello)
frame.add(button)
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE)
frame.setSize(300, 300)
frame.show()
Once again, this is simple enough that it doesn't require much explanation. We have simply created a function, and bound it to the button using the actionPerformed parameter. And we did it without having to create any listeners or anonymous inner classes. Jython handles the messy details of creating listeners and such for us. Our function receives one argument when it is called that contains a long list of properties regarding the event. If you want to see this list of properties, simply add "print event" to the hello function.
There is one problem that becomes apparent here. We do not have a way to pass any arguments to the event handler. We can't simply do something like "hello(5)". If you try, the AWT event queue will throw a TypeError exception. So what can we do if we need to pass arguments to the event handler? We can use a lambda. For those of you with some experience in a functional programming language such as LISP, you may remember that a lambda is an anonymous function. (The name is taken from the same term in calculus, which also means an anonymous function.) What we need to do here, is wrap the real event handler call in a lambda so that the AWT event queue only gets one argument. It looks like this:
button = JButton("Hello", actionPerformed = lambda x, param=5: hello(param))
This syntax may look a bit strange at first, but what we've done is pretty simple. The lambda has two parameters: x being the hello function, and param being the value 5. When actionPerformed is called, the lambda returns an anonymous function that invokes hello with the argument of 5. However, since the AWT event queue only got a single argument (the anonymous function returned by the lambda), it is happy and doesn't complain about a TypeError anymore. If this still seems a little confusing, consider that in Jython, instead of using the normal def funcName() syntax, we could, if we wanted to, define a function like this:
adder = lambda x, y: x + y
It's unorthodox, but it works. adder is now a reference to an anonymous function that takes two arguments and adds them together. We would call it like any other function, adder(5, 5), for example.
As an interesting side note, our adder function is automatically polymorphic because of the overloaded behavior of Jython's + operator. All three of the following adder calls are legal and will have the expected behavior:
adder(5, 5)
adder(5.75, 3.15)
adder("String1", "String2")
Keep this in mind as you write Jython functions and methods. Most of the ones you write will automatically be polymorphic because most of the Jython statements you will build them from are polymorphic in nature.
Overloaded Java methods
One other issue regarding calling Java methods before we move on. Because Jython is loosely typed, we can sometimes run into problems when calling overloaded Java methods. How do we determine which method to call? In this case, we can specifically tell Jython how it should treat the value we are using by passing a Java type. For example, if we have an overloaded Java method that can take either a float or a double as a parameter, we can tell Jython how to treat the passed value with something like the following:
from java.lang import Float, Double
foo(Float(5.5))
foo(Double(5.5))
Basically, you can think of it is casting the value to the correct type so that Jython knows which version of the overloaded Java method to call.
Classes in Jython
Now that we have seen the basics of using Jython, lets look into Jython's support for object oriented programming. Creating a class in Jython is quite simple. Lets look at an example.
class Hello:
def __init__(self, name="John Doe"):
self.name = name
def greeting(self):
print "Hello, %s" % self.name
jane = Hello("Jane Doe")
joe = Hello("Joe")
default = Hello()
jane.greeting()
joe.greeting()
default.greeting()
As you've probably figured out, that __init__ method is the constructor, and we can pass it default arguments for any arguments the user does not supply, as with the name argument. Note also that we can supply named parameters when we instantiate a class or call a method. For example, we could write:
jane = Hello(name = "Jane Doe")
If we do things this way, it doesn't matter what order we supply the arguments in.
So what is that self term? It is a reference to the current instance of the class. In other words, it is the equivalent of the Java this reference. Calling it self is just a Jython convention. You can use any name you want. You could call it this if you want to. Unlike Java, Jython requires us to prefix any instance variable with self. Failing to provide the self prefix will usually result in an exception being thrown. Note also that when creating a bound method, the first parameter to the method is always self. Also, if you wish to call a bound method from within the class that it is a member of, you must prefix it with self. So for example, if we want to call our greeting() method from within the class, we would write:
self.greeting()
So what do we do if we want a static variable? The following example modifies the above example slightly and uses a static variable:
class Hello:
name = ""
def __init__(self, name="John Doe"):
Hello.name = name
def greeting(self):
print "Hello, %s" % Hello.name
jane = Hello("Jane Doe")
joe = Hello("Joe")
default = Hello()
jane.greeting()
joe.greeting()
default.greeting()
We simply prefix the variable with the class name instead of with self. In the above example, all of the greeting() method calls will print John Doe because that is the last name that was assigned when the class was instantiated, thus giving us the expected behavior for a static variable.
Public vs. private variables
In Jython, variables and class methods can either be public or private. There is no "protected" level of visibility as there is in Java. The variables and methods in our previous examples were public. If we want to make them private, we can prefix them with a double underscore. For example, the following variable would be private:
self.__name = name
Subclassing and inheritance
Now lets take a look at a subclassing and inheritance example in Jython. Admittedly, this example is very contrived, but it points out the basic concepts and features of subclassing in Jython.
class Hello:
def __init__(self):
self.hello = "Hello"
class Goodbye:
def __init__(self):
self.goodbye = "Goodbye"
class Greeter(Hello, Goodbye):
def __init__(self):
Hello.__init__(self)
Goodbye.__init__(self)
def printer(self):
print self.hello
print self.goodbye
x = Greeter()
x.printer()
Uh oh... You guessed right. Yes, Jython allows multiple inheritance, as we demonstrate in the above example. The magic that Jython does behind the scenes to allow us to do this is beyond the scope of this article, and of course, no one says you have to use multiple inheritance. However, this example demonstrates how to use inheritance in Jython classes. Our Greeter class inherits from both Hello, and Goodbye. As you probably guessed, our Greeter constructor calls both superclass constructors using the ClassName.__init__ syntax. We use this same ClassName.method syntax for any method we want to call in the superclass.
Now that we have shown that Jython does allow us to use multiple inheritance, lets see an example of how Java programmers might want to use it.
Simulating interfaces with multiple inheritance
The following example shows how we can simulate an interface using multiple inheritance in Jython:
class MyInterface:
def __init__(self):
if not hasattr(self, "myMethod"):
raise AttributeError("MyClass must implement myMethod")
class MyClass(MyInterface):
def __init__(self):
MyInterface.__init__(self)
In this example, we've introduced a few new concepts. The first is the hasattr Jython built in function.
Here we have used it to simulate an interface by using multiple inheritance. If MyClass does not contain the method myMethod, then MyClass will throw an AttributeError exception when we try to instantiate it because of the inherited behavior from the MyInterface constructor. This example also shows the basics of throwing our own exceptions in Jython.
So how is this interface simulation useful? Jython has another built in method called isinstance that we can use to determine whether a given object is an instance of any given class. Although type checking is generally considered bad in Jython since we would prefer our objects to be as polymorphic as possible because of the loose typing, sometimes it is necessary. Using the hasattr and isinstance built in functions, we can set up an interface style relationship that requires a class to contain a certain method or methods, and allows us to treat that class as an object of the interface type provided it has those methods. If it does not have those methods, we will get an AttributeError exception when we try to instantiate it.
Notes on static final classes
One final note. In Java, you are used to the idea of static classes to create helper functions, or utility methods. Although it is possible to create static classes in Jython, it should almost never be done and is almost always unnecessary. Because Jython does not require us to use object oriented programming, utility "classes" can simply be implemented as modules instead. Here is an example:
# Comment: myMath "utility" class
def square(x):
return x * x
def cube(x):
return x * x * x
Later, if we want to call these utility functions from another module, we can simply do it like this:
import myMath
x = myMath.square(5)
y = myMath.cube(5)
As you can see, classes are not necessary here for these utility functions, and Python's import statement allows us to import the functions in their own namespace so that we do not pollute the global namespace despite the fact that we are not using a class.
Conclusion
This article has only provided a simple introduction to Jython, and how it can be a powerful tool in a Java programmer's arsenal. For those who want to learn more, you can use any normal Python tutorial to learn Jython. The Jython specific aspects such as using Java libraries will come naturally since it is almost identical to using those libraries in Java itself.
相关推荐
### 关于《The Definitive Guide to Jython—Python for the Java Platform》的知识点解析 #### 一、Jython简介 Jython 是一种开放源代码的实现方式,它将 Python 这种高级、动态且面向对象的脚本语言无缝集成到 ...
Jython是一种开源的高级、动态、面向对象的脚本语言Python的实现,它与Java平台无缝集成。Jython的前身JPython被认证为100%纯Java。Jython对商业和非商业使用都是免费的,并且随源代码一起分发。Jython与Java...
### 《Juneau -- The Definitive Guide to Jython -- 2010》关键知识点概览 #### 核心概念:Jython简介 - **定义**:Jython是一种能够运行在Java平台上的Python解释器,它使得开发者能够在Java虚拟机(JVM)上执行...
如果windows的用户安装插件有问题的,尝试一下换这个jython: Jython官网: https://www.jython.org/downloads.html Jython环境安装包: ...
**Burp Suite 环境 Jython 安装详解** Burp Suite 是一款广泛使用的网络安全测试工具,主要用于 web 应用程序的安全性测试。而 Jython 是 Python 语言的一个实现,它运行在 Java 虚拟机(JVM)上,使得 Python 代码...
右键 jython.Jar,Build Path->Add to Build Path,后方可使用 Jython。创建新 Jython 项目,输入语句打印 hello world。 Jython 的优点是代码简明性、方便性和易读性。它使用缩排来对代码块定界,以避免使用大括号...
**Jython 中文详细教程** Jython是一种基于Python语言的解释器,它是针对Java平台设计的,能够直接运行在Java虚拟机(JVM)上。它不仅提供了Python的全部功能,还能够无缝集成Java类库,使得开发者可以利用Python的...
### Jython 各个版本下载地址解析 Jython 是一种Python的实现,它允许Python代码在Java平台上运行。本文将详细介绍Jython不同版本的下载地址及相关文件信息。 #### Jython 2.2 版本 - **发布日期**:2007年8月24...
标题 "jython-standalone-2.7.0.zip" 提供了我们正在处理的是一个Jython的独立版本,具体是2.7.0的发行版。Jython是一种Python的实现,它允许Python代码在Java平台上运行。这个压缩包很可能包含了一个完整的Jython...
The Definitive Guide To Jython
**Jython教程** Jython是一种基于Python编程语言的开源实现,它完全兼容Python语法,并且在Java平台上运行。由IBM developerworks提供的Jython教程旨在帮助开发者理解和掌握如何在Java环境中利用Jython进行开发。 ...
《Java调用Python脚本:Jython详解及应用》 在现代软件开发中,常常需要在不同的编程语言之间进行交互,比如Java与Python。Jython是这样一种工具,它允许Java开发者无缝地运行Python代码,使得Java应用可以利用...
Jython 安装和使用方法 Jython 是一个基于 Java 语言的 Python 实现,它可以让 Python 语言运行在 Java 平台上。下面将详细介绍 Jython 的安装和使用方法。 安装 Jython 首先,需要从 Jython 官方网站下载 Jython...
Jython是一种Python编程语言的实现,它允许开发者在Java平台上编写和运行Python代码。这个"jython2.5-安装包"显然包含了Jython 2.5版本的安装程序,这是一个较旧但仍然有其用途的版本。Jython 2.5b1是该系列的beta1...
**Jython概述** Jython是一种基于Java平台的Python实现,它允许Python代码与Java平台无缝集成。Jython的出现使得Python开发者能够利用Java的强大功能,同时保持Python的简洁性和易读性。它不仅实现了Python标准库,...
标题 "Jython" 提到的是一个与Python编程语言相关的开源项目——Jython。Jython是Python的一个实现,它允许Python代码在Java平台上运行。Jython将Python语言的灵活性和简洁性与Java平台的强大功能相结合,使得开发者...
**Jython简易教程** Jython,一种Python的实现,是Python语言与Java平台的结合体。它允许开发者利用Python的简洁语法和丰富的库,同时享受到Java的高性能和跨平台优势。Jython运行在Java虚拟机(JVM)上,使得...