为什么要了解和使用拉姆达——走进Java Lambda(〇)
2014-11-11 16:11
441 查看
为什么要了解和使用拉姆达
原因一:为了充分利用电脑多核的特性。由于一般的Java程序员接触大规模并发计算的经验比较少,甚至没有,所以在编写代码时也不会考虑性能问题。Lambda诞生后,你只需要简单地调用一些方法就可以解决性能问题。比如我们知道 int 的包装类是 Integer ,int基本类型占用4个字节的内存,Integer 对象要占用16个字节的内存,你可以写List<Integer>但是不能写List<int>,但是数组就可以是 [Integer] 也可以是 [int]。如果你要执行这样的操作:把int 放入 Integer ,再把 Integer 按 int 计算,再把计算结果从 Integer 中取出来。如下
Integer m = new Integer(5); m = m*2; System.out.print(m);
当然,这段代码看起来有点滑稽,我们可能经常在List<Integer>中循环处理这种滑稽的运算。这里有多滑稽呢,第一步,把 int 打包到 Integer ;第二步, Integer 解包成 int 进行计算;第三步,计算结果打包到 Integer;第四步,使用结算结果还得从包装类 Integer 解包得到 int 。我们发现,中间绝大部分操作占用了cup时间,而且涉及到一些连续性的操纵,只能在一个核里完成,这样是会影响我们程序性能的,若Integer是某个对象的一个值,那么这样的损耗更甚。使用Lambda你不在用考虑这种性能问题,就可以简单地提升性能。
原因二:代码跟简洁,方便维护。关于这一点,你需要学习一些Lambda语法后,才能了解。比如下面:有这样一个逻辑,需对List<Person> allPerson中的“男”性人数进行统计。
旧代码可能会这样写:
<pre name="code" class="java"> List<Person> allPerson = getPerson(); int count = 0; for(Person person:allPerson){ if(person.getGen().equals("男")){ count++; } } System.out.println("男性人数为"+count);
新方式可能会这样写:
List<Person> allPerson = getPerson(); System.out.println("男性人数为"+ allPerson.stream().filter(person -> person.getGen().equals("男")).count());
更多更强大的方式我们后续再说。
原因三:可以无“副作用”地修改方法。简单地讲就是,我定义一个方法,可以强行加给另外一个已经存在的类,因为我需要,然后可以用后即焚,不影响其他地方使用。
实际上Lambda就是让Java拥有了函数编程的的功能,什么是函数编程(搜),函数编程那就是千人前面。这里我们不需要定义它,只要能用就行了。这也是为什么我们可以对一个对象加入方法,因为方法就是函数。Lambda算得上是闭包(Closure)的一个翻版,那为啥不叫闭包呢,因为Java历史上已经用一个闭包了。如果你对Javascript有所了解,那么接下来的要讲的东西,或许会感觉似曾相识。比如Array.prototype里面的filter,map,some,reduce等方法。
为了各位调试测试,我先贴出后面例子中会用到的测试用例类
class PersonFactory { /** * 随机产生指定个 {@link #Person}对象,并赋初值 * * @param personNum * 生成多少个 {@link #Person}对象 * @return */ public List<Person> getPersons(int personNum) { List<Person> list = new ArrayList<Person>(); String names[] = { "军", "荣", "莉", "轩", "兴", "馨", "云浩", "欣兰" }; String firstNames[] = { "张", "陈", "王", "李", "蒲", "吴", "郝", "林" }; for (int i = 0; i < personNum; i++) { int fn = (int) (Math.random() * firstNames.length); int n = (int) (Math.random() * names.length); int age = (fn + 1) * (n + 1); Person p = new Person(); p.setAge(age); p.setFirstName(firstNames[fn]); p.setName(names ); p.setGen(age % 3 == 0 ? "女" : "男"); list.add(p); } return list; } } class Person { private int age; private String name; private String firstName; private String gen; public int getAge() { return age; } public void setAge(int age) { this.age = age; } public String getName() { return name; } public void setName(String name) { this.name = name; } public String getFirstName() { return firstName; } public void setFirstName(String firstName) { this.firstName = firstName; } public String getGen() { return gen; } public void setGen(String gen) { this.gen = gen; } @Override public String toString() { return firstName + name + " \tage:" + age + " \tgender:" + gen; } }
相关文章推荐
- 为什么 Kotlin 调用 java 时可以使用 Lambda? —— SAM 转换机制的介绍
- 为什么要使用java.io.Serializable?
- IE+Cortona+JDK(1.3.1,1.6.0_05)+VRML97.jar 无法使用Java脚本,为什么?
- 【转+分析】JAVA: 为什么要使用"抽象类"? 使用"抽象类"有什么好处?
- 委托和Lambda那点事(一步步集合案例分析,为什么使用委托 3解)
- java下Class.forName的作用是什么,为什么要使用它(和new对象的区别)
- 为什么Java中不能使用Double Checked Locking模式
- Java网络编程从入门到精通(15):为什么要使用SocketAddress来管理网络地址
- java中的String为什么可以使用==比较字符串内容?
- 为什么Java中要使用Checked Exceptions
- Java 理论和实践: 了解泛型 识别和避免学习使用泛型过程中的陷阱
- Java - 为什么要使用接口编程
- 为什么java使用人数最多呢?
- 为什么主流Java MVC框架如此难以使用(呵呵很精辟的看法了,我也很认同,值得我自己收藏和参考)
- Java - 为什么要使用接口编程
- Java 理论和实践: 了解泛型(第一次使用泛型的用户的常见陷阱)
- 为什么主流Java MVC框架如此难以使用
- 为什么JAVA要使用单继承体系
- [评论]为什么不能使用Java 7?
- java中为什么在static中不能使用this关键字