在以前的Java版本中,开发者只能将注解(Annotation)写在声明中。对于Java 8,注解可以写在使用类型的任何地方,例如声明、泛型和强制类型转换等语句:
@Encrypted String data; List<@NonNull String> strings; myGraph = (@Immutable Graph) tmpGraph;
乍一看,类型注解并不是Java新版本最炫的特性。事实上,注解只是语法!工具决定了注解的的语义(即,它们的含义和行为)。本文介绍新的注解语法和实用工具,以提高生产力和构建更高质量的软件。
在金融行业,我们的市场波动和监管环境决定了上市时间比以往任何时候都更加重要。但牺牲安全性或质量绝对不是一个可选项:简单的百分点和基点混乱就可能造成严重后果。这种情况同样存在于所有其它行业。
作为一名Java程序员,也许你已经采用注解来提高软件质量。想想早在Java 1.5中引入的@Override注解。在具有复杂继承层次结构的大型项目中,要跟踪系统运行时会执行方法的哪一种实现是很困难的。如果你不小心修改了某个方法的声明,可能会导致子类方法没有被调用。这种方式取消了一个方法调用,将会引入缺陷或者安全漏洞。为此,Java引入了@Override注解,开发者可以用它来说明该方法覆盖了父类方法。如果程序没有匹配这种意图,Java编译器将使用这些注解来警告开发者。如此,注解扮演了机器检查文档的形式。
开发者可以通过元编程(Metaprogramming)等技术提高生产率,注解在其中扮演了核心角色。其思想是通过注解够告诉工具如何生成新代码、转换代码或者决定运行期的行为。以Java Persistence API(JPA)为例,这也是Java 1.5引入的功能。它允许开发者以声明的方式如@Entity,指定Java对象与数据库实体之间的关系。然后Hibernate这类工具就可以使用这些注解,在运行期生成映射文件和SQL查询。
在JPA和Hibernate的场景中,注解用于支持DRY(Don't Repeat Yourself)原则。有趣的是,无论你在哪寻找支持最佳实践的开发工具,都不难发现注解的存在。一些著名的例子包括使用依赖注入(Dependency Injection)降低耦合,使用面向切面编程(Aspect Oriented Programming)分离关注点。
问题来了:如果注解已经被用于提升质量和提高生产率,为什么我们还需要类型注解?
这个问题的简单回答是:类型注解提供更多的功能。它们帮助自动检测更多的缺陷,为你提供生产力工具的更多控制。
类型注解的语法
在Java 8中,类型注解可以写在使用类型的任何地方,以下是一些例子:
@Encrypted String data List<@NonNull String> strings MyGraph = (@Immutable Graph) tmpGraph;
引入一个新的类型注解非常简单,只要定义一个注解,并且其target为ElementType.TYPE_PARAMETER或ElementType.TYPE_USE,或者两个都包含:
@Target({ElementType.TYPE_PARAMETER, ElementType.TYPE_USE}) public @interface Encrypted { }
ElementType.TYPE_PARAMETER表示注解能写在类型变量的声明语句中(如:class MyClass {...})。而ElementType.TYPE_USE表示注解能写在使用类型的任何语句中(例如声明语句、泛型和强制转换语句中的类型)。
一旦源码中的类型有了注解,就像声明中的注解一样,它可以同时存在于类文件中并在运行时可以通过反射获取(定义注解时使用RetentionPolicy.CLASS或RetentionPolicy.RUNTIME策略)。类型注解与以前的注解有两个主要区别:首先,局域变量声明中的类型注解也可以保留在类文件中;其次,完整泛型被保留,并且在运行期可以访问。
尽管注解可以保存在类文件中,但它不影响程序的常规运行。例如,开发人员可能在方法体中声明了两个File变量和一个Connection变量:
File file = ...; @Encrypted File encryptedFile = ...; @Open Connection connection = ...;
当程序运行时,传递其中任何一个文件给connection的send(...)方法,都会调用同一个方法实现。
// 以下代码将调用同一个方法 connection.send(file); connection.send(encryptedFile);
正如你预期的那样,运行期没有区别,也就是说,尽管参数的类型是有注解的,但方法不会基于注解的类型进行重载:
public class Connection{ void send(@Encrypted File file) { ... } // Impossible: // void send( File file) { ... } . . . }
以上是小编为您精心准备的的内容,在的博客、问答、公众号、人物、课程等栏目也有的相关内容,欢迎继续使用右上角搜索按钮进行搜索java
, 注解
, 方法
, 类型
, 语句
, 开发者
, 注解实体类
, 使用注解
, tomcaturlwebsocket注解404
, 注解全局变量
, sql servermybatis注解
, 注解hibernate基类jpa字段
, java注解
Java 注解 override
java官网、java教程、java下载、java7、java jdk,以便于您获取更多的相关知识。