2017,Java诞生22周年!今天我们介绍一个Java9的功能,模块化(Modular);这可能会让Java历史上的***特性,将其长期依赖于JRE结构,转变为基于Module的组件。感觉就像一个大力士需要将胳膊、腿等一个个去掉,还能正常工作。难度可想而知。虽然Java9还没有发布,但这个特性已经期待和折磨了很多年。从1995年诞生的第一天起,Java就背负着“Writeonce,Runanywhere”的口号,一路走来,从学术实验语言到开发者青睐的语言,再到统一的企业开发语言,二十个弱冠。随着时间的推移,Java逐渐从一种创新的语言变成了一种“传统”、“古老”、“经典”的语言。同时,它也接受了很多新语言的挑战,比如Go、Scalar等。Java从来都不是一门完美的语言:GC的效率总是给高并发程序员带来很多痛苦和调整,Classpath地狱总是让许多奇怪的错误发生,高级语言特性总是在JCP(JavaCommunityProcess)中踢球而无法落地,异步模式下的多线程编程总是有一个陡峭的学习曲线,OracleJDK和OpenSDK总是有一段说不清道不明的关系,孤傲的J2EE框架让人崩溃。不过,我还是最喜欢Java编程语言,不仅因为它已经使用了20年,还有两个原因:Java生态:几乎所有的开发库都支持Java语言,Java是打开程序的钥匙worldJava语言的开源:Javasource代码设计流畅,可以学到很多设计技巧。从Java7开始就计划模块化,但由于其复杂性,不断跳过Java7和Java8,最终计划在Java9推出,让我们拭目以待!目前,Java9的功能已经基本开发完毕,还有半年的时间来解决各种bug。以下是Java9的时间表!Java9中最重要的功能Java9中最重要的功能无疑是模块化(Module),代号为Jigsaw(拉锯),这个拉锯工程拖了好几年,终于有必要了看到庞大冗余的Java被一个个Modules,方便开发部署。熟悉Java的同学都知道JRE有一个超大的rt.jar(比如Java8的rt.jar就有65M)。运行一个helloworld,还需要一个上百兆的JRE环境。如果你在J2EE环境中,情况会变得极其复杂。另外,如果你没有遭受过ClasspathHell,那说明你还不是一个深厚的Java程序员,呵呵。模块化的功能有几个目的:使JavaSE程序更简单轻量级部署改善组件之间的依赖管理,引入比Jar粒度更大的Module提高性能和安全性如果用更简单的方式解释就是“解决Classpathhell问题,提高部署能力”。模块有很多内容。为了由浅入深,我将根据一些问题和我的理解来介绍模块化。1.什么是Java模块?模块是代码和数据的包。代码指的是一些包含类型的包。Package是一些类路径名的约定,一个Module是由一个或多个Package组成的包。2.模块代码示例模块是通过module-info.java定义的。编译打包后,成为一个模块实体;在模块定义文件中,我们需要指定模块之间的依赖关系,可以导出那些模块,需要使用那些模块(requires)。这是一个例子:modulecom.foo.bar{requiresorg.baz.qux;exportscom.foo.bar.alpha;exportscom.foo.bar.beta;}META-INF/META-INF/MANIFEST.MFmodule-info.classcom/foo/bar/alpha/AlphaFactory.classcom/foo/bar/alpha/Alpha.class...3、JDK8和JDK9有什么区别?JDK8的JRE部署是单机模式,一个超大的rt.jar(60兆左右),tools.jar也有几十兆,就算你用一个HelloWorlds,也需要一整套JRE环境有几百个兆字节。JAVA9引入模块后,所有的类都被组织成模块,模块之间有一种美好的依赖关系(至少现在很整洁,不知道几个版本之后会不会继续优雅)。Java8包之间的依赖关系Java9依赖关系(模块之间的依赖关系)4.public不再意味着可访问(accessible)模块之间的关系称为可读性(readability),表示一个模块是否能找到这个模块文件并读入系统(注意:不代表类型可以访问)。在实际代码中,一种类型对另一种类型的调用称为可访问性(Accessible),表示该类型可以使用;可访问性的前提是可读性,换句话说,现有模块可读,然后进一步检查可访问性(安全性)。在Java9中,Public不再意味着任意访问!5.什么是模块的Transitivereference(indirectreference)例如:因此,标记transitive可以提供间接可读性。在myapp中,可以直接引用Logger类。6、Module和Maven是什么关系看完Module,这么详细的表达依赖关系,是不是跟任何软件都差不多?你会想到Maven还是Gradle?仔细想想,Modular跟他们还是不一样的。系统内置模块化来表达组件之间的关系,版本管理还处于最原始的状态。它管理一个强制依赖项。Maven有两个核心功能a)组件依赖管理,尤其是版本管理,这种依赖是逻辑的,不是强制的b)管理开发过程中的各种任务,初始化,测试等7.JLink简介JLink是一个打包Modules的工具帮助在目标机器上部署。打包后的文件会非常紧凑。8.Module的原理及实现在内部实现上,整个过程非常繁琐复杂。可能有几件事;a)将系统内部类模块化,不需要区分太多的J2ME、J2SE、J2EE。每个人都使用模块作为交流语言。这就需要梳理所有的类及其调用关系、调用频率等,将系统类模块化。这可能是最复杂的部分,但结果是最好的。b)分类ClassLoaderClassLoader分为三个级别。BootstrapLoader优先级和权限最高,主要是核心系统类;PlatformLoader用于一些扩展的系统类,如SQL、XML等;ApplicationLoader主要是针对应用程序的Loader。在这三个层次的Loader之下,有一个统一的Module管理,用于控制和管理模块之间的依赖关系、可读性、可访问性。注意,Java9中ClassLoader的类加载逻辑与之前相同,但是通过模块管理系统,ClassLoader.FindClass的能力将被限制在readable&accessible的条件下,而不是之前简单的Public条件。好了,啰嗦了这么多,期待简单易用的Java9,希望今年能真正用上。【本文为专栏作家“欧阳辰”原创稿件,转载请联系作者获得授权】点此阅读更多该作者好文
