Groovy文档翻译——Groovy软件开发包GDK

Groovy开发工具

(对JDK的扩展GDK)

1.操作IO

Groovy为操作IO提供了很多有用的方法。您可以使用默认的java代码在Groovy中处理IO操作(Groovy完全兼容),不仅如此,Groovy还提供了更多更 方便的方法处理文件、二进制流、字符流、……

特别的,您应该看一下增加的方法。

  • java.io.File类: http://docs.groovy-lang.org/latest/html/groovy-jdk/java/io/File.html

  • java.io.InputStream 类: http://docs.groovy-lang.org/latest/html/groovy-jdk/java/io/InputStream.html

  • java.io.OutputStream 类: http://docs.groovy-lang.org/latest/html/groovy-jdk/java/io/OutputStream.html

  • java.io.Reader 类: http://docs.groovy-lang.org/latest/html/groovy-jdk/java/io/Reader.html

  • the java.io.Writer 类: http://docs.groovy-lang.org/latest/html/groovy-jdk/java/io/Writer.html

  • java.nio.file.Path 类: http://docs.groovy-lang.org/latest/html/groovy-jdk/java/nio/file/Path.html

接下来的部分着重关注使用上面提到更加有帮助的方法来编写更加符合语言习惯的结构,但是并不意味着是所有可用方法的完整描述。如果您想要关于那些方法的完整描述的话,请阅读GDK API。

1.1读取文件

第一个例子然我们看看您 怎样在Groovy中输出一个文本文件的所有内容:

eachLine方法是Groovy自动添加到File类中的(关于如何扩展类之后相关章节会有详细描述)并且拥有许多的方法变体,例如如果您需要知道行数,您能够使用这个变量:

如果由于某些原因在ecahLine的方法体内抛出了异常,这个方法会将资源正确的关闭。Groovy添加的所有使用IO资源的方法都会那么做。

例如某些情况下您选择使用Reader但您仍能够从Groovy的自动资源管理中受益。在下一个例子中,字符流将会被关闭即使发生了异常。

加入您需要手机一个文本文件的所有行到一个列表里(文本文件的一行为一个元素),您能够这么做:

您甚至可以使用as操作符使文件的内容变为一个数组,数组的每个元素为文本文件的一行的内容。

有多少次您不得不使用一个byte数组来获得一个文件的内容但又有多少代码是必须的额br> Groovy使他实际上变的非常简单:

操作I/O并不仅仅局限于文件。事实上许多操作依赖于输入输出流,这也是为什么Groovy添加了了许多推荐的方法去操作输入输出流,您能够在这个文档中看到。

在下面的这个例子中,您能够非常简单的从一个File类中获取InputStream:

然而在上面的例子中您需要自己去关闭InputStream。在Groovy中其实有个更符合习惯的withInputStream方法,他能为您自动关闭InputStream:

1.2.写文件

当然某些情况下您并不像读文件而想写文件。一个写文件的方法是使用Writer:

但是对于这样一个简单的例子,使用

当然我们并不总是处理文本内容,所以您可以直接在这个例子中写入字节:

当然您也可以直接处理输出流。下面的例子展示了您怎样创建一个输出流写入文件:

然而你会发现这需要你自己去关闭输出流,与上文的输入流一样您可以使用更符合语言规范的并且会帮助您自动处理错误和关闭输出流的withOutputStream方法:

1.3.遍历文件树

在脚本上下文为了寻找一些特定的文件并且对他们进行一些操作进行文件树遍历操作是一个常见的任务。Groovy提供了多种方法实现文件树遍历。例如您能够在一个文件夹下的所有文件中执行:

(1)在文件夹找到的每个文件中执行闭包。
(2)在文件夹符合正则表达式的文件中执行闭包。

你经常不得不处理有很深层次的文件,在这种情况下您能够使用eachFileRecurse:

(1)在文件夹中的所有文件和文件夹递归的执行闭包。
(2)只在文件中(不包括文件夹子)递归的执行闭包。

你能够使用traverse方法来运用更多的复合遍历技术,这需要您设置一个特殊的标志指明您想要怎样遍历:

(1) 如果当前文件是一个文件夹并且他的名字是bin就停止遍历。
(2)否则输出文件名并继续。

1.4.数据与对象

Java中分别使用 java.io.DataOutputStreamjava.io.DataInputStream类来进行序列化和反序列化数据的场景很常见。Groovy是他们处理起来更加易于使用。例如,您能够使用一下代码将数据序列化到文件中或者从文件中反序列化:

与此相像,如果您想要序列化的数据实现了Serializable接口,您能够使用一个对象输出流处理它,就像这儿说明的那样:

1.5.执行外部进程(调用命令行)

之前的部分描述了用Groovy处理文件,字符流,字节流的简便之处。但在系统管理和开发领域经常需要与外部进程进行通信。
Groovy提供了一个简便的方法执行命令行进程。简单的写下命令行命令并将其作为一个字符串然后调用他的**execute()**方法。例如:在一个类unix系统上(或者一个安装了类unix命令行工具的windows系统上),您能够执行这些:

(1)在外部进程中执行ls命令。
(2)消耗命令行的输出并取到文本中。

execute()方法将返回一个包含要被处理的in/out/err流和要被检查的退出值的java.lang.Process实例。

例如这是与上面的例子同样的命令但现在我们将一次只处理结果流的一行:

(1)在外部进程中执行ls命令。
(2)进程输入流的每一行。
(3)输出该行。

值得注意的是in指向一个指向默认命令输出流的输入流。out将指向一个您能够发送数据前往的进程的流(该进程的默认输入)。

请记住许多的命令是shell内置的并且需要特殊的处理。所以,如果您想要在windows机器上列出一个文件夹下所有文件的话并写下如下语句:

你将会得到一个IOException异常说:Cannot run program “dir”: CreateProcess error=2, The system cannot find the file specified.
这是因为dir是Windows shell(cmd.exe)的内建命令并且不能简单的运行为一个可执行文件。相反,你需要写:

另外由于这个功能现阶段底层使用java.lang.Process,所以必须要考虑那个类本身的不足之处。特别的,javadoc对于这个类说明如下:

因为一些本地平台只为默认的输入输出流提供有限的缓冲区大小,如果没有及时的写入子进程的输入流或者及时的读出子进程的输出流可能引起子进程的阻塞,甚至是死锁。

因为这个原因Groovy提供了一些附加的更有用的方法来使处理进程流更简单。

下面是如何从进程中获取所有输出(包括错误流输出):

也有许多使用StringBuffer,InputStream, OutputStream等等的
consumeProcessOutput的变体。为了获取完整的列表,请阅读GDK API for java.lang.Process

此外还有一个将一个进程的输出流送入另一个进程的输入流的pipeTo命令(映射成**|**来允许重载)。
下面是一些使用的例子:
Pipes的使用:

消费错误:

2.操作集合

Groovy提供了丰富的集合类型的原生支持,包括 lists, maps 或者ranges。
他们中许多基于Java集合类型同时被Groovy development kit中的附加方法所修饰。

2.1.列表

2.1.1.列表字面量

您能够像下面这样创建一个列表。注意**[]**是空列表的表达式。

每个列表表达式创建了一个java.util.Lis的实现。
当然列表也能作为构建另一个列表的源列表。

一个列表是一个有序的对象的集合:

#####2.1.2.列表作为布尔表达式
列表能够被视作是一个布尔值:

2.1.3.列表的迭代

元素的迭代经常依靠调用eacheachWithIndex方法来完成,他们在列表的每个元素上执行代码:

此外为了迭代,经常要通过改变转变一个列表自身的所有元素到另一个元素来创建一个新列表。这个操作,经常被叫做mapping,在Groovycollect方法已经实现了这个目的:

2.1.4.操纵集合
筛选和查询

Groovy开发工具包含了许多用来增加强默认集合的 实用方法,其中一些方法说明如下:

assert [1, 2, 3].find { it > 1 } == 2           // 寻找符合条件的第一个方法assert [1, 2, 3].findAll { it > 1 } == [2, 3]   // 寻找所有符合条件的元素assert ['a', 'b', 'c', 'd', 'e'].findIndexOf {      //  寻找第一个符合条件的元素索引    it in ['c', 'e', 'g']} == 2assert ['a', 'b', 'c', 'd', 'c'].indexOf('c') == 2  // 返回索引assert ['a', 'b', 'c', 'd', 'c'].indexOf('z') == -1 // 索引-1意味着列表中不存在此元素assert ['a', 'b', 'c', 'd', 'c'].lastIndexOf('c') == 4assert [1, 2,

来源:GUI113

声明:本站部分文章及图片转载于互联网,内容版权归原作者所有,如本站任何资料有侵权请您尽早请联系jinwei@zod.com.cn进行处理,非常感谢!

上一篇 2019年6月8日
下一篇 2019年6月8日

相关推荐