博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
【转】Groovy++:与Groovy有何不同
阅读量:4110 次
发布时间:2019-05-25

本文共 3185 字,大约阅读时间需要 10 分钟。

1.Groovy++编译时检查更严格

例1:

/* Leave it commented to run the dynamic Groovy version;     Uncomment to run Groovy++ version *///@Typedpackage testdef x = { List list ->    list.size()}x(1)

对Groovy,上述代码编译不会出错,但运行时会出错。因为我们调用的是x(Integer),而定义的是x(List)。

对Groovy++,编译时即报错:"Cannot find method { List -> ...}.doCall(int)"。

例2:

/* Commented -> dynamic Groovy version;     Uncommented -> Groovy++ version *///@Typedpackage testclass Foo {    def greet() {println "Foo says hello"}}class Bar {    def greet() {println "Bar says hello"}}def c = {greeter -> greeter.greet()}c(new Foo())c(new Bar())

对Groovy,得益于duck-typing,上述代码编译时和运行时都不会出错。

对Groovy++,则会出错:"Cannot find method Object.greet()" ,因为它会依照闭包参数的静态类型来做判断。

2.通过ExpandoMetaClass即时修改类型。

例3:

/* Commented -> dynamic Groovy version; Uncommented -> Groovy++ version *///@Typedpackage testString.metaClass.foo = { ->  println "foo called" }"".foo()  /* call my new method */

对Groovy,上述代码运行得很好,并动态给String增加foo方法。

对Groovy++,静态模式下不支持这一特性,“Mixed”模式可以解决这一问题,既享用动态特性,又保持静态检查。如下例所示

例4:

@Typed(TypePolicy.MIXED)package testString.metaClass.foo = { ->  println "foo called" } // supported"".foo()

3.Groovy++闭包更像是Java的内嵌类

在Java中,内嵌类不能引用其外部范围的非final成员。如下述代码编译将出错。

例5:

void foo(){    String data = "";    class Inner {        void innerFoo() {            System.out.println(data);        }    }}

groovy把闭包看作是内嵌类,但是不限制对外部非final成员的访问,因此下属代码可以在Groovy中运行

例6:

void foo(){    String data = 'original';    def cl = {data = 'changed'} // access non-final data of its outer scope    cl()    assert data == 'changed'}foo()

Groovy++与Java更加接近,只允许以只读方式访问非final数据成员。如下例,如果试图修改这些成员,则会报 错:"Cannot modify final field test.Test$foo$1.data"

例7:

@Typedpackage testvoid foo(){    String data = 'original';    def cl = {data = 'changed'}}foo()

之所以这样,项目领导Alex Tkachman解释主要是避免并行运行风险。但如果不做并行运算,是否有什么解决之道?参见下例,用groovy.lang.Reference:

例8:

@Typedpackage testvoid foo(){    Reference data = ['original']    def cl = {data = 'changed'} // now even Groovy++ supports modification of non-final outer scope data    cl()    assert data == 'changed'}foo()

4.Groovy++不再直接访问私有成员

Groovy没有限制从外部访问一个类的私有成员,下例将正常运行。

例9:

/* Commented -> dynamic Groovy version; Uncommented -> Groovy++ version *///@Typedpackage testclass SecretService {    String secret = "secret"    String getSecret() {        "covered-" + secret    }    private launchOperation() {        "launched"    }}def ss = new SecretService()assert ss.@secret == "secret" // can access the private field directlyassert ss.launchOperation() == "launched" // can access the private method

Groovy++ 则在编译时限制这种访问,对Groovy++,上面例子"ss.@secret" 会导致 "Cannot access field test.SecretService.secret"; "ss.launchOperation()" 会导致 "Cannot access method SecretService.launchOperation()"。

5.还有一些小的差别

例10:Script binding 变量

/* Commented -> dynamic Groovy version; Uncommented -> Groovy++ version *///@Typedpackage testfoo = "foo"assert foo == "foo"

上述例子对Groovy没有问题,变量foo是在script中绑定的。但在Groovy++ 中不支持,如果要在Groovy中使用这一特性,得用@Typed(TypePolicy.MIXED)标注方式。

例11:对map的属性风格访问

/* Commented -> dynamic Groovy version; Uncommented -> Groovy++ version *///@Typedpackage testdef map = [key1: "value1"]assert map.key1 == "value1"

map.key1这种方式访问map,对Groovy没问题,但 Groovy++不支持,除非用MIXED模式。

转载地址:http://hjasi.baihongyu.com/

你可能感兴趣的文章
c++写时拷贝1
查看>>
Linux网络编程---I/O复用模型之poll
查看>>
Java NIO详解
查看>>
(正则表达式)表单验证
查看>>
在JS中 onclick="save();return false;"return false是
查看>>
VS编译器运行后闪退,处理方法
查看>>
用div+css做下拉菜单,当鼠标移向2级菜单时,为什么1级菜单的a:hover背景色就不管用了?
查看>>
idea 有时提示找不到类或者符号
查看>>
ng-class的几种用法
查看>>
matplotlib.pyplot.plot()参数详解
查看>>
拉格朗日对偶问题详解
查看>>
MFC矩阵运算
查看>>
最小二乘法拟合:原理,python源码,C++源码
查看>>
ubuntu 安装mysql
查看>>
c# 计算器
查看>>
C# 简单的矩阵运算
查看>>
gcc 常用选项详解
查看>>
c++输入文件流ifstream用法详解
查看>>
c++输出文件流ofstream用法详解
查看>>
字符编码:ASCII,Unicode 和 UTF-8
查看>>