使用lombok的@Getter和@Setter
作為一個Java 庫,以簡單的注解方式避免工程中的繁瑣重復的代碼。常用的注解有@Getter @Setter @Slf4j等。
官網是https://projectlombok.org/。
// 配置Maven依賴
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>1.18.20</version>
</dependency>
// 類中使用注解
import lombok.Getter;
import lombok.Setter;
@Getter
@Setter
public class Student{
private String name;
private int age;
}
使用反編譯工具打開Student.class后可發現,lombok自動生成了get set方法,並且在生成的class類中沒有lombok相關的類。
lombok生成代碼原理
lombok通過jdk實現的JSR 269: Pluggable Annotation Processing API (編譯期的注解處理器) ,在編譯時把lombok的注解轉換成Java代碼,相當於在編譯時對代碼進行修改。
javac編譯的的過程大概有以下幾個步驟
1、詞法分析
2、語法分析
3、填充符號表
4、插入式注解處理器處理
5、語義分析
6、解語法糖
7、生成字節碼
lombok實現了插入式注解處理器,通過它來讀取、修改、添加抽象語法樹中的任意元素。
動手實現lombok的@Getter和@Setter
git clone git@gitee.com:viturefree/lombok.git
# 打開lombok下的lombok項目,編譯構建以及安裝jar包到本地(供lombok-test使用)
mvn clean install
在target目錄下生成了jar包
打開lombok下的lombok-test項目,直接運行
@Retention(RetentionPolicy.SOURCE)
@Target(ElementType.TYPE)
public @interface Setter {
}
@Retention(RetentionPolicy.SOURCE)
@Target(ElementType.TYPE)
public @interface Getter {
}
@interface表示注解類型,一個注解是一個類。
@Retention用來修飾注解,是注解的注解,稱為元注解。
RetentionPolicy有3個值:SOURCE、CLASS、RUNTIME。
@Retention(RetentionPolicy.SOURCE)修飾的注解,表示注解的信息保留在java源文件中。
@Retention(RetentionPolicy.CLASS)修飾的注解,表示注解的信息保留在class文件中。
@Retention(RetentionPolicy.RUNTIME)修飾的注解,表示注解的信息保留在class文件中,在運行時會被JVM讀取。
注解@Target也是元注解,ElementType值為:ANNOTATION_TYPE、CONSTRUCTOR、FIELD LOCAL_VARIABLE、METHOD、PACKAGE、PARAMETER、TYPE。
@Target(ElementType.TYPE)表示該注解作用於類型。
...
public class GetterProcessor extends AbstractProcessor {
...
private Name getNewMethodName(Name name) {
String s = name.toString();
return names.fromString("get" + s.substring(0, 1).toUpperCase() + s.substring(1, name.length()));
}
}
...
public class SetterProcessor extends AbstractProcessor {
...
private Name getNewMethodName(Name name) {
String s = name.toString();
return names.fromString("set" + s.substring(0, 1).toUpperCase() + s.substring(1, name.length()));
}
}
AbstractProcessor是抽象注解處理器類,GetterProcessor和SetterProcessor類繼承了它。
getNewMethodName用於生成抽象語法樹中get或者set方法名字,即get或者set+屬性首字母大寫。