对比groovy和java不同点。
Groovy是一种基于JVM(Java虚拟机)的敏捷开发语言,它结合了Python、Ruby和Smalltalk的许多强大的特性,Groovy 代码能够与 Java 代码很好地结合,也能用于扩展现有代码。由于其运行在 JVM 上的特性,Groovy 可以使用其他 Java 语言编写的库。 目前对我来说,groovy主要是用于编写gradle脚本。对于java开发者来说,学习groovy相当容易,只需要注意下groovy和java的不同点。 1.默认imports相对java,groovy的默认引用是 java.io.*
java.lang.*
java.math.BigDecimal
java.math.BigInteger
java.net.*
java.util.*
groovy.lang.*
groovy.util.*
2.重载方法groovy,方法参数类型是在运行时选择的,相比java是编译时就选择好了。来看下下面的代码 int method(String arg) { return 1; } int method(Object arg) { return 2; } Object o = "Object";
int result = method(o);
调用方式,groovy 对比 java //Java调用
assertEquals(2,result);
//groovy调用
assertEquals(1,result);
3.初始化数组在Java中定义数组,如下 int[] array = { 1,2,3}
但是在groovy中,{}是保留给闭包使用的,所以就不能使用{}来初始化数组,看下groovy怎么实现。 int[] array = [1,3]
4.默认可见域class Person {
String name
}
在Java中,上面默认的可见域是包可见;但是在groovy中,上面默认的可见域是private,在groovy要使用包可见域,可以使用@PackageScope来修饰,如下: class Person {
@PackageScope String name
}
5.ARM blocks我们知道ARM是Java1.7的特性,也叫自动资源管理。看下Java如何使用的。 Path file = Paths.get("/path/to/file");
Charset charset = Charset.forName("UTF-8");
try (BufferedReader reader = Files.newBufferedReader(file,charset)) {
String line;
while ((line = reader.readLine()) != null) {
System.out.println(line);
}
} catch (IOException e) {
e.printStackTrace();
}
groovy使用如下方式: new File('/path/to/file').eachLine('UTF-8') {
println it
} //或者更接近Java的方式
new File('/path/to/file').withReader('UTF-8') { reader ->
reader.eachLine {
println it
}
}
6.内部类这点groovy和Java有些不同,groovy的实现方式看起来更像是来自于groovy.lang.Closure,外部类无法访问它的私有field和私有方法,另外一个方面,内部类访问外部的本地变量,不像Java一样,要使用final修饰 6.1 静态内部类class A {
static class B {}
}
new A.B()
这种是groovy使用内部类的最好方式 6.2 匿名内部类import java.util.concurrent.CountDownLatch
import java.util.concurrent.TimeUnit
CountDownLatch called = new CountDownLatch(1)
Timer timer = new Timer()
timer.schedule(new TimerTask() {
void run() {
called.countDown()//called不需要使用fianal修饰
}
},0)
assert called.await(10,TimeUnit.SECONDS)
创建非静态内部类的实例//Java代码
public class Y {
public class X {}
public X foo() {
return new X();
}
public static X createX(Y y) {
return y.new X();
}
}
但是groovy不支持y.newX()的语法,可以使用new X(y)来代替 //groovy
public class Y {
public class X {}
public X foo() {
return new X()
}
public static X createX(Y y) {
return new X(y)
}
}
7.Lambdas的使用Java8和groovy的lambdas使用略有不同 //java8
Runnable run = () -> System.out.println("Run");
list.forEach(System.out::println);
//groovy
Runnable run = { println 'run' }
list.each { println it } // or list.each(this.&println)
8.GStrings在groovy中,双引号字符串被解释为GString类型,如果String字符串中包括”$”字符,groovy就会报出编译错误或者产生很微妙的不同代码。 一般情况下,Groovy会在GString和String之间自动转换,如果API声明参数的类型,请注意接受Object参数的Java API,然后检查实际类型。 9.String和Character在groovy中,单引号字符串作为String使用,双引号字符串可以作为GString或者String,取决于字符串是否有插值。看下下面的代码就明白了 assert 'c'.getClass()==String
assert "c".getClass()==String
assert "c${1}".getClass() in GString
Groovy将在分配给char类型的变量时自动将单个字符的String转换为char,当调用类型为char的参数的方法时,我们需要显式地转换或者确保已经提前转换了该值。 char a='a'
assert Character.digit(a,16)==10 : 'But Groovy does boxing',所以要像下面显示转换
assert Character.digit((char) 'a',16)==10
try {
assert Character.digit('a',16)==10
assert false: 'Need explicit cast'
} catch(MissingMethodException e) {
}
Groovy支持两种风格的char转换,但是有多个char的字符串转换是,需要注意 // for single char strings,both are the same
assert ((char) "c").class==Character
assert ("c" as char).class==Character
// for multi char strings they are not
try {
((char) 'cx') == 'c'
assert false: 'will fail - not castable'
} catch(GroovyCastException e) {
}
assert ('cx' as char) == 'c'
assert 'cx'.asType(char) == 'c'
10.原始类型和其包装因为Groovy为任何使用Objects,它会自动包装原型类型的引用。 正因为如此,它并没有遵循Java的扩大优先于box的行为。 这是一个使用int的例子 int i
m(i)
//java
void m(long l) {
println "in m(long)"
}
//groovy
void m(Integer i) {
println "in m(Integer)"
}
==的使用在java中,“==”意味着 原始类型相等或者对象一样。在groovy中, 12.转换Java支持自动放宽和变窄转换。 - Y :支持自动转换 - C :支持显示转换 - T :支持转换,但是会产生位数截断,比如long转换成float会产生截断 - N :不支持转换 下面是groovy的转换表
13.其他关键字groovy比java多一些关键字,不能使用它们来定义变量 - as - def - in - trait (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |