JAVA7-9个版本特性汇总

8 篇文章 0 订阅

Java新特性

一、    Java7:

Java 7 的架构图:

新特性一览表:

Swing

·        新增 JLayer 类,是一个灵活而且功能强大的Swing组件修饰器,使用方法:How to DecorateComponents with JLayer.

·        Nimbus Look andFeel 外观从 com.sun.java.swing 包移到 javax.swing 包中,详情:javax.swing.plaf.nimbus

·        更轻松的重量级和轻量级组件的混合

·        支持透明窗体以及非矩形窗体的图形界面,请看 How to CreateTranslucent and Shaped Windows

·        JColorChooser 类新增 HSV tab.

网络

·        新增 URLClassLoader.close 方法,请看 Closing aURLClassLoader.

·        支持 Sockets Direct Protocol (SDP) 提供高性能网络连接,详情请看 Understandingthe Sockets Direct Protocol.

集合

·        新增 TransferQueue 接口,是 BlockingQueue 的改进版,实现类为 LinkedTransferQueue

RIA/发布

·        拖拽的小程序使用一个默认或者定制的标题进行修饰,详情:Requesting andCustomizing Applet Decoration in Draggable Applets.

·        JNLP 文件做了如下方面的增强,详情请看 JNLP File Syntax:

·        The os attribute in the information and resources elements cannow contain specific versions of Windows, such as Windows Vista or Windows 7.

·        Applications can use the install attribute inthe shortcut element to specify their their desire to beinstalled. Installed applications are not removed when the Java Web Start cacheis cleared, but can be explicitly removed using the Java Control Panel.

·        Java Web Start applications can be deployed withoutspecifying the codebase attribute; see DeployingWithout Codebase

·        可直接在 HTML 中嵌入JNLP 文件:Embedding JNLPFile in Applet Tag.

·        可在 JavaScript 代码中检查 Applet 是否已经加载完成:HandlingInitialization Status With Event Handlers.

·        可在 Applet 从快捷方式启动或者拖出浏览器时对窗口样式和标题进行控制:Requesting andCustomizing Applet Decoration in DevelopingDraggable Applets.

XML

·        包含 Java API for XMLProcessing (JAXP) 1.4.5, 支持 Java Architecture for XML Binding (JAXB)2.2.3, 和 Java API for XMLWeb Services (JAX-WS) 2.2.4.

java.lang

·        消除了在多线程环境下的非层次话类加载时导致的潜在死锁,详情:MultithreadedCustom Class Loaders in Java SE 7.

Java 虚拟机

·        支持非 Java 语言:Java SE 7 引入一个新的 JVM 指令用于简化实现动态类型编程语言

·        Garbage-FirstCollector 是一个服务器端的垃圾收集器用于替换 Concurrent Mark-SweepCollector (CMS).

·        提升了 Java HotSpot 虚拟机的性能

Java I/O

java.nio.file 包以及相关的包 java.nio.file.attribute 提供对文件 I/O 以及访问文件系统的全面支持,请看 File I/O(featuring NIO.2).

·        目录 <Javahome>/sample/nio/chatserver/ 包含使用 java.nio.file 包的演示程序

·        目录 <Javahome>/demo/nio/zipfs/ 包含 NIO.2 NFS 文件系统的演示程序

安全性

·        新的内置对多个基于 ECC 算法(ECDSA/ECDH)的支持,详情请看:Sun PKCS#11Provider's Supported Algorithms in Java PKCS#11Reference Guide.

·        禁用了一些弱加密算法,详情请看 Appendix D:Disabling Cryptographic Algorithms in Java PKIProgrammer's Guide and DisabledCryptographic Algorithms in Java SecureSocket Extension (JSSE) Reference Guide.

·        Java 安全套接字扩展中对 SSL/TLS 的增强

并发

·        fork/join 框架,基于 ForkJoinPool 类,是 Executor 接口的实现,设计它用来进行高效的运行大量任务;使用 work-stealing 技术用来保证大量的 worker 线程工作,特别适合多处理器环境,详情请看 Fork/Join 

·        目录<Java home>/sample/forkjoin/ 包含了 fork/join 框架的演示程序

·        ThreadLocalRandom 类class 消除了使用伪随机码线程的竞争,请看 ConcurrentRandom Numbers.

·        Phaser 类是一个新的同步的屏障,与 CyclicBarrier 类似.

Java 2D

·        一个新的基于 XRender 的Java 2D 渲染管道支持现在的 X11 桌面,改善了图形性能,请看 SystemProperties for Java 2D Technology 中的 xrender .

·        JDK 可枚举并显示出已安装的 OpenType/CFF 字体,通过 GraphicsEnvironment.getAvailableFontFamilyNames方法 See Selecting a Font.

·        TextLayout 类支持西藏语脚本

·        libfontconfig, 是一个字体配置 api ,see Fontconfig.

国际化

·        支持 Unicode 6.0.0 

·        目录 <Javahome>/demo/jfc/Font2DTest/ 包含 Unicode 6.0 的演示程序

·        Java SE 7 可容纳在 ISO 4217 中新的货币,详情请看 Currency 类.

Java 编程语言特性

·        二进制数字表达方式

·        使用下划线对数字进行分隔表达,例如 1_322_222

·        switch 语句支持字符串变量

·        泛型实例创建的类型推断

·        使用可变参数时,提升编译器的警告和错误信息

·        try-with-resources语句

·        同时捕获多个异常处理

JDBC 4.1

·        支持使用 try-with-resources 语句进行自动的资源释放,包括连接、语句和结果集

·        支持 RowSet 1.1

 

二、    java8:

 Lambda表达式

Lambda表达式可以说是Java 8最大的卖点,她将函数式编程引入了Java。Lambda允许把函数作为一个方法的参数,或者把代码看成数据。

一个Lambda表达式可以由用逗号分隔的参数列表、–>符号与函数体三部分表示。例如:

Arrays.asList( "p", "k", "u","f","o", "r","k").forEach( e ->System.out.println( e ) );

 1 Arrays.asList( "p","k", "u","f", "o","r","k").forEach( e -> System.out.println( e ) ); 

为了使现有函数更好的支持Lambda表达式,Java 8引入了函数式接口的概念。函数式接口就是只有一个方法的普通接口。java.lang.Runnable与java.util.concurrent.Callable是函数式接口最典型的例子。为此,Java 8增加了一种特殊的注解@FunctionalInterface:

1@FunctionalInterface

2publicinterface Functional {

3     void method();

4}

接口的默认方法与静态方法

我们可以在接口中定义默认方法,使用default关键字,并提供默认的实现。所有实现这个接口的类都会接受默认方法的实现,除非子类提供的自己的实现。例如:

1publicinterfaceDefaultFunctionInterface {

2     default String defaultFunction() {

3         return "default function";

4     }

5}

我们还可以在接口中定义静态方法,使用static关键字,也可以提供实现。例如:

1publicinterfaceStaticFunctionInterface {

2     static String staticFunction() {

3         return "static function";

4     }

5}

接口的默认方法和静态方法的引入,其实可以认为引入了C++中抽象类的理念,以后我们再也不用在每个实现类中都写重复的代码了。

方法引用

通常与Lambda表达式联合使用,可以直接引用已有Java类或对象的方法。一般有四种不同的方法引用:

1. 构造器引用。语法是Class::new,或者更一般的Class< T >::new,要求构造器方法是没有参数;

2. 静态方法引用。语法是Class::static_method,要求接受一个Class类型的参数;

3. 特定类的任意对象方法引用。它的语法是Class::method。要求方法是没有参数的;

4. 特定对象的方法引用,它的语法是instance::method。要求方法接受一个参数,与3不同的地方在于,3是在列表元素上分别调用方法,而4是在某个对象上调用方法,将列表元素作为参数传入;

重复注解

在Java5中使用注解有一个限制,即相同的注解在同一位置只能声明一次。Java 8引入重复注解,这样相同的注解在同一地方也可以声明多次。重复注解机制本身需要用@Repeatable注解。Java 8在编译器层做了优化,相同注解会以集合的方式保存,因此底层的原理并没有变化。

扩展注解的支持

Java 8扩展了注解的上下文,几乎可以为任何东西添加注解,包括局部变量、泛型类、父类与接口的实现,连方法的异常也能添加注解。

 Optional

Java 8引入Optional类来防止空指针异常,Optional类最先是由Google的Guava项目引入的。Optional类实际上是个容器:它可以保存类型T的值,或者保存null。使用Optional类我们就不用显式进行空指针检查了。

GStream

Stream API是把真正的函数式编程风格引入到Java中。其实简单来说可以把Stream理解为MapReduce,当然Google的MapReduce的灵感也是来自函数式编程。她其实是一连串支持连续、并行聚集操作的元素。从语法上看,也很像linux的管道、或者链式编程,代码写起来简洁明了,非常酷帅!

HDate/Time API (JSR 310)

Java 8新的Date-TimeAPI (JSR 310)受Joda-Time的影响,提供了新的java.time包,可以用来替代 java.util.Date和java.util.Calendar。一般会用到Clock、LocaleDate、LocalTime、LocaleDateTime、ZonedDateTime、Duration这些类,对于时间日期的改进还是非常不错的。

JavaScript引擎Nashorn

Nashorn允许在JVM上开发运行JavaScript应用,允许Java与JavaScript相互调用。

 Base64

在Java8中,Base64编码成为了Java类库的标准。Base64类同时还提供了对URL、MIME友好的编码器与解码器。

除了这十大新特性之外,还有另外的一些新特性:

·更好的类型推测机制:Java 8在类型推测方面有了很大的提高,这就使代码更整洁,不需要太多的强制类型转换了。

·编译器优化:Java 8将方法的参数名加入了字节码中,这样在运行时通过反射就能获取到参数名,只需要在编译时使用-parameters参数。

·并行(parallel)数组:支持对数组进行并行处理,主要是parallelSort()方法,它可以在多核机器上极大提高数组排序的速度。

·并发(Concurrency:在新增Stream机制与Lambda的基础之上,加入了一些新方法来支持聚集操作。

·Nashorn引擎jjs:基于Nashorn引擎的命令行工具。它接受一些JavaScript源代码为参数,并且执行这些源代码。

·类依赖分析器jdeps:可以显示Java类的包级别或类级别的依赖。

·JVM的PermGen空间被移除:取代它的是Metaspace(JEP 122)。

四、Java 9:

我们将快速的,着重的浏览其中的几个新特性; 

模块化系统–Jigsaw 项目

模块化是一个很通用的概念。在软件中,模块化可以运用到编写和实现一个程序和计算系统,他们都是作为独立的模块,而不是作为一个单一的和完整的设计。

Java 9中主要的变化是已经实现的模块化系统。模块化的引入使得JDK可以在更小的设备中使用。采用模块化系统的应用程序只需要这些应用程序所需的那部分JDK模块,而非是整个JDK框架了。模块化系统也可以将公共的类封装到一个模块中。因此一个封装在模块中的定义为public的类不能再任何地方使用,除非一个模块显式的定义了这个模块。由于Java 9的这个变化,Java内部的API(例如com.sun.*)默认情况下是不能使用的。

简而言之,所有的模块将需要在所谓的module-info.java文件中进行描述,这个文件是位于Java代码结构的顶层。

module me.aboullaite.java9.modules.car {

   requires me.aboullaite.java9.modules.engines;//依赖的模块

   exports me.aboullaite.java9.modules.car.handling;//在模块中导出包

}

我们的模块car(汽车)需要依赖+模块engine(引擎)和需要导出handling(操纵)包。

需要更多深入的例子可以查看OpenJDK中项目Jigsaw:模块化系统快速入门

JShell–Java 9 REPL

你可能问:“REPL是什么”?REPL是一种快速运行语句的命令行工具。

在Java中,如果你想执行一个简单的语句,我们要么创建一个带main方法的类,要么创建一个可以执行的Test类。当你正在启动Java程序的时候,如果你想执行某些语句并且想立刻看见执行结果,上面的做法看起来不是那么有用了。

JShell试图去解决这个问题。Java开发者可以利用JShell在没有创建类的情况下直接声明变量,计算表达式,执行语句。JShell也可以从文件中加载语句或者将语句保存到文件中。并且JShell也可以是tab键进行自动补全的特性。

集合工厂方法

在Java 9之前,Java只能利用一些实用方法(例如:Collections.unmodifiableCollection(Collection<?extends T> c))创建一个不可修改视图的集合。例如,我们可以在Java 8中使用一条如下所示的语句,创建一个Collection的不可修改的视图。虽然这是最简单的创建方式,但是看起来很糟糕!不是吗?

Map<String, String> immutableMap =

Collections.unmodifiableMap(

           new HashMap<String, String>() {{

                put("key1","Value1");

                put("key2","Value2");

                put("key3","Value3");

           }});

现在,Java 9引入了一些有用的工厂方法来创建不可修改的集合。我们现在在Java 9中创建不可修改的Map集合,如下所示。

Map<String, String> immutableMap =Map.of("key1", "Value1", "key2","Value2","key3", "Value3");

下面是工厂方法的例子:

 //empty immutable collections 不可修改的空集合

List<String> emptyImmutableList =List.of();

Set<String> emptyImmutableSet =Set.of();

Map emptyImmutableMap = Map.of();

 

// immutable collections 不可修改的集合

List<String> immutableList =List.of("one", "two");

Set<String> immutableSet =Set.of("value1", "value2");

Map<String, String> immutableMap =Map.of("key1", "Value1", "key2","Value2", "key3", "Value3");

接口中的私有方法

Java 8的接口引入了默认方法和静态方法。虽然Java 8首次计划实现接口的私有方法,却是在Java 9中实现。默认方法和静态方法可以共享接口中的私有方法,因此避免了代码冗余,这也使代码更加清晰。如果私有方法是静态的,那这个方法就属于这个接口的。并且没有静态的私有方法只能被在接口中的实例调用。

interface InterfaceWithPrivateMethods {

   private static String staticPrivate() {

       return "static private";   

    }

 

   private String instancePrivate() {

       return "instance private";

    }

 

   default void check() {

       String result = staticPrivate();

 

       InterfaceWithPrivateMethods pvt = new InterfaceWithPrivateMethods() {

           // anonymous class 匿名类

       };

 

       result = pvt.instancePrivate();

    }

 

}

响应式流

JDK9中的Flow API对应响应式流规范,响应式流规范是一种事实标准。JEP 266包含了一组最小接口集合,这组接口能捕获核心的异步发布与订阅。希望在未来第三方能够实现这些接口,并且能共享其方式。

java.util.concurrent.Flow包含以下4个接口:

Flow.Processor(处理器)

Flow.Publisher(发布者)

Flow.Subscriber(订阅者)

Flow.Subscription(订阅管理器)

这些接口都支持响应式流发布-订阅框架。Java 9也提供了实用类SubmissionPublisher。一个发布者产生一个或多个物品,这些物品由一个或多个消费者消耗。并且订阅者由订阅管理器管理。订阅管理器连接发布者和订阅者。

多分辨率图像API–JEP 251

目标是定义多分辨率图像API,这样开发者就能很容易的操作和展示不同分辨率的图像了。

这个新的API定义在java.awt.image包中,这个API能给我们带来如下的帮助:

* 将不同分辨率的图像封装到一张(多分辨率的)图像中,作为它的变体。

* 获取这个图像的所有变体。

* 获取特定分辨率的图像变体–表示一张已知分辨率单位为DPI的特定尺寸大小的逻辑图像,并且这张图像是最佳的变体。

基于当前屏幕分辨率大小和运用的图像转换算法,java.awt.Graphics类可以从接口MultiResolutionImage获取所需的变体。java.awt.image.AbstractMultiResolutionImage类提供了ava.awt.image.AbstractMultiResolutionImage 默认实现。AbstractMultiResolutionImage的基础实现是java.awt.image.BaseMultiResolutionImage

进程API的改进

迄今为止,通过Java来控制和管理操作系统的进程的能力有限。例如,为了做一些简单的事情,像获取进程的PID,你要么需要访问本地代码,要么使用某种临时解决方案。不仅如此,每个(系统)平台需要一个不同实现来确保你能获得正确的结果。

在Java 9中,期望代码能获取Linux PID,现在是如下方式:

public static void main(String[] args)throws Exception

{

 Process proc = Runtime.getRuntime().exec(new String[]{"/bin/sh", "-c", "echo $PPID" });

 

  if(proc.waitFor() == 0)

   {

   InputStream in = proc.getInputStream();

   int available = in.available();

   byte[] outputBytes = new byte[available];

 

   in.read(outputBytes);

   String pid = new String(outputBytes);

 

   System.out.println("Your pid is " + pid);

   }

}

你可以变换如下的方式(同样支持所有的操作系统):

System.out.println("Your pid is "+ Process.getCurrentPid());

Try-With-Resources

在Java 7中,try-with-resouces语法要求为每一个资源声明一个新的变量,而且这些资源由try-with-resources语句进行管理。

在就Java 9中,有另外一个改进:如果一个资源被final或者等效于final变量引用,则在不需要声明一个新的变量的情况下,try-with-resources就可以管理这个资源。

MyAutoCloseable mac = newMyAutoCloseable();

try (mac) {

   //do some stuff with mac

}

 

try (new MyAutoCloseable() {}.finalWrapper.finalCloseable) {

  //do some stuff with finalCloseable

}

钻石(diamond)操作符范围的延伸

Java 7给出的钻石操作符使我们编写代码更简单了。在下面的例子中,你可以看见Java 7中List(列表)的可读性更强了,并且使代码更加的简洁了。

List<String> preJava7 = newArrayList<String>();//java 7 之前的写法

List<String> java7 = newArrayList<>();//java 7 之后的写法

但是Java 7中钻石操作符不允许在匿名类上使用。但在Java 9中改善了这一情况,允许钻石操作符在匿名类上使用。下面的例子只有在Java 9中才能通过编译。

List<String> list = newArrayList<>(){ };

增强的注释Deprecated

注释@Deprecated可以标记Java API。注释@Deprecated有很多种含义,例如它可以表示在不远的将来的某个时间,被标记的API将会被移除。它也可以表示这个API已经被破坏了,并不应该再被使用。它还有其它很多含义。为了提供更多有关@Deprecated的信息,@Deprecated添加了forRemoval元素和since元素。

Java SE 9 中也提供了扫描jar文件的工具jdeprscan。这款工具也可以扫描一个聚合类,这个类使用了Java SE中的已废弃的API元素。 这个工具将会对使用已经编译好的库的应用程序有帮助,这样使用者就不知道这个已经编译好的库中使用了那些已废弃的API。

统一的JVM日志

如今,我们很难知道导致JVM性能问题和导致JVM崩溃的根本原因。解决这个问题的一个方法是对所有的JVM组件引入一个单一的系统,这些JVM组件支持细粒度的和易配置的JVM日志。目前,不同的JVM组件对于日志使用的是不同的机制和规则,这使得JVM难以进行调试。

注释SafeVarargs范围的延伸

直到Java 8@SafeVarargs才能在静态方法、final方法和构造器上使用。但是这些方法或者构造器是不能被覆盖的。这些方法中缺少另一个不能被覆盖的方法,这个方法就是私有方法。Java 9可以将@SafeVarargs添加到私有方法上。下面的例子在Java 9中是正确的,但是在Java 8中就会抛出编译时错误: 注释@SafeVarargs不能在非final的实例方法iAmSafeVaragrsMethod上使用

@SafeVarargs

 private void iAmSafeVaragrsMethod(String... varagrgs)

  {

    for (String each: varagrgs) {

       System.out.println(each);

    }

  }

HTTP 2 客户端

Java 9采用了全新的HTTP客户端API,这些API支持HTTP/2协议和WebSocket协议,并且替换了遗留的HTTPURLConnectionAPI。这些改变并不应该在Java 9中完成。这些API可以从Incubator(孵化器)模块中获取。因此在默认情况下,这个模块是不能根据classpath获取的,需要使用--add-modules命令选项配置这个模块,将这个模块添加到classpath中。

我们创建一个HTTPRequest请求和获取异步的响应:

 URItestPageURI = new URI("http://127.0.0.1:8080/testPage");

 CompletableFuture<HttpResponse> nonBlockingResponse =  HttpRequest

         .create(testPageURI)

         .GET().responseAsync();

  inttries = 0;

 while(!nonBlockingResponse.isDone() && tries++ < 5) {Thread.sleep(5); } if (nonBlockingResponse.isDone()) { HttpResponse response =nonBlockingResponse.get(); System.out.println("status code : " +response.statusCode() + " --> " + response.body(HttpResponse.asString()));

  }

 else {

     nonBlockingResponse.cancel(true);

     System.out.println("Cancelling, could not get response");

  }

HTML5风格的Java帮助文档

Java 8以及之前的版本生成的Java帮助文档是在HTML 4中,而HTML4已经是很久的标准了。在Java 9中,javadoc命令行中选项部分添加了输出选项,这个选项的值要么是HTML 4,要么是HTML 5。现在HTML4是默认的输出标记语言,但是在之后发布的JDK中,HTML 5将会是默认的输出标记语言。Java帮助文档还是由三个框架组成的结构构成,这是不会变的,并且以HTML 5输出的Java帮助文档也保持相同的结构。

更多的特性

* 保留下划线字符。变量不能被命名为_

* 废弃Applet API

javac不再支持Java1.4以及之前的版本;

* 废弃Java浏览器插件;

* 栈遍历API–栈遍历API能过滤和迟访问在堆栈跟踪中的信息。

 

 


  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值