WeTest 导读
Java 9预计今年也会正式发布,Java 8这个最具变革性且变革性最适于GUI程序的版本,Android终于准备正式支持。从自己开发JavaFx的感受,说一说Java 8应该使用的新特性。程序员,你应该拥抱变化。 (注:本文不讲具体语法,具体语法请下载下方分享的《Java 8实战》。)
James Lau(google的产品经理):We’ve decided to add support for Java 8 language features directly into the current javac and dx set of tools, and deprecate the Jack toolchain. With this new direction, existing tools and plugins dependent on the Java class file format should continue to work. Moving forward, Java 8 language features will be natively supported by theAndroid build system.
我们决定弃用 Jack 工具链,改为直接在最新的 javac 和 dx 工具集中增加对 Java 8 语言功能的支持。经过这番改弦易辙,依赖于 Java 类文件格式的现有工具和插件仍可继续工作。今后,Java 8 语言功能将得到 Android 构建系统的原生支持。
一
GUI桌面类软件特点
GUI图形界面的应用程序有几个特点:
● 基于消息驱动模型
● 强交互,实时性要求高
● 用户触发执行与用户触发结束
二
Lambda表达式
举个实际应用中的例子,下面这部分的代码是过滤出某个目录下所有xml后缀的文件,java 8之前的写法是这样子的:
Java 8的写法
lambda需要解决的一个核心问题啰嗦,lambda能做的内部类都能做。Java是面向对象的语言,不支持方法。C语言的方法,在java里面可能是一个接口,可能是一个静态方法。listFiles这个方法需要的是一个行为(行为参数化,更高级的抽象),这个行为是name.endsWith(“.xml”),但是java不支持传递行为方法。所以,java 8之前我们不得不用函数接口(只包含一个方法的接口,专有名词函数接口)对象的方式来对行为进行包装。刻薄的讲FileTypeFilter类命名为FilenameFilterActionWrapper更加贴切。
1、方法引用
Lambda有一种快捷写法,方法引用。之前说,在Java中定义方法的方式,一种是接口,一种是静态方法,现有的库中已经包含有大量的方法。方法引用,可以让我们重用这些方法,让这些方法像Lambda一样能够被传递。
GUI程序中的用法,这种写法Java 8之前,在JavaFx或者Android程序中都应该会大量出现
Java 8之后的写法应该是这样的
这两者的差别,解释起来应该是这样子的。本质:”直接调用这个方法”,Lambda或者java 8之前”描述如何调用这个方法”。你没必要再去描述如何调用,因为都知道该怎么调用。我们知道GUI程序最基本的设计时MVC,解决的是视图和逻辑分离,这几乎是GUI程序设计里面最基本的。逻辑处理方法一般并不会包含在控制器的类里面,而是在逻辑层,有了方法引用你可以直接与逻辑层的方法相关联。
2、为什么要lambda
● 简洁的代码,跟利于行为参数化(高级抽象,if else->参数化-行为参数化)
● 预设的lambda接口,Predicate、Consumer、Function等,java 8大量库支持。如果你不理解lambda,你将不理解大量Java 8的接口。
● 类型检查、类型推断更优
注:写lambda的时候,参数一定要有含义,本来就不写类型了,再不写有含义的变量就真的是天书了。
三
CompetableFuture组合式异步编程
一个解析Android apk信息的类,可能会解析很长一段时间,所以需要有超时。
Java 5之前的写法
Java 5的写法
Java 8
那么CompletableFuture除了少些几句代码之外,它到底有什么好处呢?
● 约定:与设计模式一样,这是程序员的一种约定。接口返回CompletableFuture,调用者一眼就只这是个异步API,也知道如何调用它
● 同步转异步:配合lambda,几句话就能完成。
● 异常传递:apkInformation.completeExceptionally(new WeTestRuntimeException(e.getMessage(), e)),其他线程的异常可以传递过来。GUI程序里面,异常通常要转化为用户的一种视图。
● 协调:等待多个异步操作完成合并(如查找多家网站酒店价格,取最小值),等待多个异步操作中最快的一个完成,异步操作完成后回调一个函数(异步操作完成,来个Toast)。在以前这些协调性的功能,可能需要借助CountDownLatch,CyclicBarrier来完成。CompletableFuture一步到位
注:CompletableFuture配合Stream可以极大的提高并发的效率
举个简单的上面这个例子返回后的用法:
四
Stream流处理
Use stream operations to express refined data processing queries.用流Stream以表达式的方式来完成数据处理。我自己的理解是,以数据库的操作方式来完成数据的处理。Java 8的Stream内置了许多类似于数据库的操作filter、sort、map、reduce等。
Stream优点:
● 以数据库操作数据的方式,专注于如何做这个某个步骤,表达式的方式
● 高并发(看到map、reduce就应该能想到了)
举个用法的例子,业务时获取所有在线的可测试的手机:
注:Stream的写法的确对原因的思维方式会造成一定的冲击,不过写过了,加上有一定数据库使用基础的话理解起来非常容易。Stream高性能的特点的确感受不深,因为处理大量数据的情况毕竟是少数。
五
Optional
A container object which may or may not contain a non-null value.一个可能包含null指的对象包装器。null不可避免,能避免的是NullPointerException。null最大的罪在于它可以代表任何类型。下面这两个接口,不去看你的注释,我并不知道你是否可能会返回null。在业务需求变化如此快的今天,贴切非常容易出现对返回值不做检查的情况,任何人都会偷懒。Optional的处理逻辑是,强迫你去检查。如果我的返回值是Optional,这个接口显式的告诉你可能返回的是null值,这个在GUI程序里面特别常见。
GUI的弹出框用户可能并不填内容内容,返回null。
所以,Optional的核心思想就是我明确告诉你可能会返回null,你一定要处理。所以,现在模块间提供给其他人的接口,如果有可能返回为null都要声明为Optional。Java 8大量的官方接口也都会放回Optional,这个是一定要学的内容。
Java 8实战:https://share.weiyun.com/075e6cd0f306c706260fb377c38ac90b
近日,谷歌发布了安卓8.0开发者预览版。腾讯WeTest立刻在云真机产品中增加了带有安卓O系统的真机。
想要率先体验的用户可以登录:http://wetest.qq.com/product/cloudphone
如在使用中有任何疑问,欢迎联系企业qq:800024531