博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Groovy 学习手册(5)
阅读量:4482 次
发布时间:2019-06-08

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

8. 函数式编程

函数式编程(FP)是一种编程风格,侧重于函数和最小化状态的变化(使用不可变的数据结构)。它更接近于用数学来表达解决方案,而不是循序渐进的操作。

在函数式编程里,其功能应该是“无副作用”(不会改变外部功能),参考透明的(一个函数每次传递相同的参数,返回相同的值)。

函数式编程可以被看作是一种更常见的命令式编程的替代,它更接近告诉计算机遵循每个步骤。

虽然函数式编程可以在Java 8 前实现,但在 Java 8 版本,通过 Lambda 和函数接口,才真正在语言层面上支持函数式编程。

Java 8、JavaScript、Groovy,Scala都支持函数式编程,他们虽然并不是严格意义上的函数式编程语言。

1. 函数和闭包

也许你也知道,在基本的函数式编程的语言里,函数才是第一等公民,这意味着函数可以在任何地方使用。

例如,在JavaScript里,你可以把一个函数指定给一个变量,并执行它:

var func = function(x) { return x + 1; }var three = func(2); //3

尽管在 Groovy 里,函数并不具备第一等公民的特性,但有功能相似的方式实现:闭包。闭包就是在一对大括号里面包含的在“->”左边带有参数的代码块。例如:

def  closr = {x -> x + 1}println( closr(2) ); //3

在 Groovy 里,如果闭包只有一个参数,那么默认 it就作为这个参数的引用,例如:

def  closr = {it + 1}

Tip

如果返回值是最后一个表达式,则return 关键字可以省略。

使用闭包

如果闭包作为方法的最后一个参数,或者方法只有一个参数,这种情况下,闭包的实现可以放在括号的外面,例如,下面的代码,定义了一个方法用来使用闭包对 List 里面的元素进行过滤:

def  find(list, tester) {    for (item in list)        if (tester(item)) return item}

这个方法返回当闭包条件为 true时的第一个元素,下面就是调用的此闭包的代码:

find([1,2,]) { it > 1 } // 2

映射 / 过滤 / 其他

一旦你掌握了函数,你很快会意识到需要一种方法来执行数据集合(或序列或数据流)的操作。

由于有些都是常见的操作,人们发明了顺序操作,如映射,过滤,聚合等操作。
下面的例子里,使用一个装有多个 Person对象的 List 集合来演示这些操作。

1240

map(collect方法):把输入元素转化或改变成其他形式的元素。
1240
filter(findAll方法):当 predicate 函数式接口为 true 时返回子集合。
1240
reduce(inject方法):在元素上进行聚合操作(返回一个结构,例如所有元素的总和)。

1240

Limit([0..n-1]):返回前 n 个元素。

1240

Concat(+):结合两个不同的元素集合。

class Person { String name; int age }def persons = [new Person(name:'Bob',age:20), new Person(name:'Tom',age:15)]def names = persons.collect { person -> person.name }def adults = persons.findAll { person -> return person.age >= 18 }def totalAge = persons.inject(0){total, p -> return total + p.age}

上面的代码中,使用了inject方法,它会循环遍历每一个 List 中的元素,最后返回一个值。我们给total赋了一个初始值为0,最后我们把每个 Person 的年龄全部加起来得到一个总和。

转载于:https://www.cnblogs.com/IcanFixIt/p/6664082.html

你可能感兴趣的文章
学习python第七天
查看>>
Flask基础(07)-->正则自定义转换器
查看>>
C++著名程序库的比较和学习经验(STL.Boost.GUI.XML.网络等等)
查看>>
Spring Boot构建RESTful API与单元测试
查看>>
【JavaScript你需要知道的基础知识~】
查看>>
谷歌搜索语法
查看>>
static 静态变量
查看>>
Java面试题(05)
查看>>
操作符重载
查看>>
Docker 安装及问题处理
查看>>
JavaScript中的call 和apply的用途以及区别
查看>>
HashMap完全解读
查看>>
匿名内部类
查看>>
BZOJ4071: [APIO2015]八邻旁之桥
查看>>
Redis的六种特性 场景
查看>>
mysql 添加[取消]timestamp的自动更新
查看>>
码农的半衰期只有15年?
查看>>
手工释放linux内存
查看>>
2014-5-30 总结
查看>>
【H3 BPM工作流程管理产品小故事】第四篇 子表创建
查看>>