Java開發的效率工具--Lombok

點擊上方“框架師”,選擇“置頂公衆號

我們一起學習進步!

正文

引言

Lombok這個插件Java開發一般都不陌生,正常情況下可以用來簡化我們的JavaBean代碼量,網上找了很多lombok相關的文章,註解介紹都不怎麼全,索性自己摸索一篇出來,供大家參考


Lombok概述
  • 官網地址: https://projectlombok.org/

  • 官網API文檔傳送門: https://projectlombok.org/features/all

  • 以下是官方簡介

Project Lombok is a java library that automatically plugs into your editor and build tools, spicing up your java.Never write another getter or equals method again, with one annotation your class has a fully featured builder, Automate your logging variables, and much more.

########################################################

大概的意思:Lombok是一個Java庫,能自動插入編輯器並構建工具,簡化Java開發。通過添加註解的方式,不需要爲類編寫getter或eques方法,同時可以自動化日誌變量。


該不該用Lombok

這個問題可以說一直有很大爭議,比如最近爆文:爲什麼要放棄Lombok,等等許多相似抨擊Lombok插件的文章,我個人是比較贊成使用Lombok的,至少目前爲止使用非常的得心應手,下面是常見的兩方觀點;


正方觀點 反方觀點
代碼乾淨整潔,工作量大大降低 強侵入性,一人用都得用,否則編譯通不過
代碼可讀性增強,保持代碼風格一致 失去了封裝意義,因爲有些屬性不一定想提供公共的getter/setter方法
Bean修改後,不需要修改模板化代碼 IDE和JDK升級存在破裂的風險

安裝

使用Lombok必須要安裝Lombok插件,在IDEA應用市場搜索lombok,定位到file/setings/plugins/markeptlace搜索Lombok

  • 在項目中導入依賴,必須是maven項目,如果是普通的項目,添加lombok的jar即可

1<dependencies>
2        <!--Lombok依賴-->
3        <dependency>
4            <groupId>org.projectlombok</groupId>
5            <artifactId>lombok</artifactId>
6            <version>1.18.12</version>
7        </dependency>
8</dependencies>
常用註解介紹

可以使用@Getter 或 @Setter標註任何字段,lombok 會幫助你自動生成默認的get、set方法。默認的get、set方法是public的,除非你額外設置AccessLevel

  • 使用Lombok方式:

 1@Getter
2@Setter
3public class Person {
4    private String name;
5    private Integer age;
6}
7
8/**
9@Getter @Setter private int age = 10; //其他寫法
10@Setter(AccessLevel.PROTECTED) private String name;
11*/

@ToString

任何類的定義上都可以被@ToString標註,lombok可以生成一個toString()的實現方法。默認會打印類名以及每個字段並且用逗號分隔。

  • 使用Lombok方式:

1@Getter
2@Setter
3@ToString
4public class Person {
5    private String name;
6    private Integer age;
7}
@Data

@Data 註解在類上面,自動生成setter/getter、equals、canEqual、hashCode、toString方法,如某個屬性爲final,則不會爲該屬性生成setter方法。

  • 使用Lombok方式

1@Data
2public class Person {
3    private String name;
4    private Integer age;
5}
@NonNull

可以在方法或構造器的參數上使用 @NonNull,lombok會爲你生成一個空值檢查的聲明。相當於以下代碼

1if (param == null) {
2        throw new NullPointerException("null");
3}
  • 使用lombok方式:

1@Data
2public class Person {
3    private String name;
4    private Integer age;
5
6    public Person(@NonNull String person) {
7        this.name = person;
8    }
9}
@Cleanup

可以使用@Cleanup來確保在代碼執行路徑退出當前作用域之前自動清除給定的資源。其實就是關閉註解標註的當前資源。【簡單瞭解一下就行,一般也用不上】

  • 使用lombok方式:

 1public static void main(String[] args) throws Exception {
2    @Cleanup InputStream in = new FileInputStream(args[0]);
3    @Cleanup OutputStream out = new FileOutputStream(args[1]);
4    byte[] b = new byte[1024];
5    while (true) {
6        int r = in.read();
7        if (r == -1break;
8        out.write(b, 0, r);
9    }
10}
@EqualsAndHashCode

任何類的定義上都可以被@EqualsAndHashCode標註,lombok可以生成一個equals(Object other)和hashCode()的實現方法。它將使用所有非靜態,但是可以通過使用@ EqualsAndHashCode.Include@EqualsAndHashCode標記類型成員來修改使用的字段。

  • 官網代碼(沒看明白):

 1import lombok.EqualsAndHashCode;
2
3@EqualsAndHashCode
4public class EqualsAndHashCodeExample {
5  private transient int transientVar = 10;
6  private String name;
7  private double score;
8  @EqualsAndHashCode.Exclude private Shape shape = new Square(510);
9  private String[] tags;
10  @EqualsAndHashCode.Exclude private int id;
11
12  public String getName() {
13    return this.name;
14  }
15
16  @EqualsAndHashCode(callSuper=true)
17  public static class Square extends Shape {
18    private final int width, height;
19
20    public Square(int width, int height) {
21      this.width = width;
22      this.height = height;
23    }
24  }
25}
@NoArgsConstructor
  • @NoArgsConstructor

  • @RequiredArgsConstructor

  • @AllArgsConstructor

這組3個註釋會生成一個構造函數,該構造函數將爲某些字段接受1個參數,並將該參數簡單地分配給該字段。

  • @NoArgsConstructor 將生成沒有參數的構造器;

  • @RequiredArgsConstructor 爲需要特殊處理的每個字段生成一個帶有1個參數的構造函數;

  • @AllArgsConstructor 爲類中的每個字段生成一個帶有1個參數的構造函數。

  • 使用Lombok方式:

 1import lombok.AccessLevel;
2import lombok.RequiredArgsConstructor;
3import lombok.AllArgsConstructor;
4import lombok.NonNull;
5
6@RequiredArgsConstructor(staticName = "of")
7@AllArgsConstructor(access = AccessLevel.PROTECTED)
8public class ConstructorExample<T{
9  private int x, y;
10  @NonNull private T description;
11
12  @NoArgsConstructor
13  public static class NoArgsExample {
14    @NonNull private String field;
15  }
16}
@Value使用

@Value是@Data的不可變形式; 默認情況下,所有字段都設爲私有和final的字段,並且不會生成setter。

  • 使用Lombok方式:

 1import lombok.AccessLevel;
2import lombok.experimental.NonFinal;
3import lombok.experimental.Value;
4import lombok.experimental.Wither;
5import lombok.ToString;
6
7@Value public class ValueExample {
8  String name;
9  @Wither(AccessLevel.PACKAGE) @NonFinal int age;
10  double score;
11  protected String[] tags;
12
13  @ToString(includeFieldNames=true)
14  @Value(staticConstructor="of")
15  public static class Exercise<T{
16    String name;
17    T value;
18  }
19}
@Builder
  • @Builder註釋會爲您的類生成複雜的構建器API。

  • @Builder可自動生成使你的類可被實例化的代碼。

  • 使用Lombok方式:

 1import lombok.Builder;
2import lombok.Singular;
3import java.util.Set;
4
5@Builder
6public class BuilderExample {
7  @Builder.Default private long created = System.currentTimeMillis();
8  private String name;
9  private int age;
10  @Singular private Set<String> occupations;
11}
  • 也可以在調用的時候使用鏈式調用

1 Book book = Book.builder()
2         .id(rs.getInt("id"))
3         .bookName(rs.getString("bookname"))
4         .bookDesc(rs.getString("bookdesc"))
5         .pic(rs.getString("pic"))
6         .price(rs.getFloat("price"))
7         .build();
@SneakyThrows

@SneakyThrows可用於偷偷地拋出已檢查的異常,而無需在方法的throws子句中實際聲明。[這個我經常使用,非常方便]

  • 使用Lombok方式:

 1import lombok.SneakyThrows;
2
3public class SneakyThrowsExample implements Runnable {
4  @SneakyThrows(UnsupportedEncodingException.class)
5  public String utf8ToString(byte[] bytes) {
6    return new String(bytes, "UTF-8");
7  }
8
9  @SneakyThrows
10  public void run() {
11    throw new Throwable();
12  }
13}
@Synchronized

@Synchronized是同步方法修飾符的更安全的變體。
與同步一樣,註釋只能在靜態和實例方法上使用。 它的操作類似於synchronized關鍵字,但是它鎖定在不同的對象上

  • 使用lombok方式:

 1import lombok.Synchronized;
2
3public class SynchronizedExample {
4  private final Object readLock = new Object();
5
6  @Synchronized
7  public static void hello() {
8    System.out.println("world");
9  }
10
11  @Synchronized
12  public int answerToLife() {
13    return 42;
14  }
15
16  @Synchronized("readLock")
17  public void foo() {
18    System.out.println("bar");
19  }
20}
@With

The next best alternative to a setter for an immutable property is to construct a clone of the object, but with a new value for this one field. A method to generate this clone is precisely what @With generates: a withFieldName(newValue) method which produces a clone except for the new value for the associated field.

說實話沒看明白這段話是什麼意思,個人理解爲:在類的字段上標註 @With 註解之後,將會自動生成一個 withFieldName(newValue) 的方法,該方法會基於 newValue 調用相應構造函數,創建一個當前類對應的實例。

  • 使用lombok方式:

 1import lombok.AccessLevel;
2import lombok.NonNull;
3import lombok.With;
4
5public class WithExample {
6  @With(AccessLevel.PROTECTED) @NonNull private final String name;
7  @With private final int age;
8
9  public WithExample(String name, int age) {
10    if (name == nullthrow new NullPointerException();
11    this.name = name;
12    this.age = age;
13  }
14}
@Getter

@Getter 註解支持一個 lazy 屬性,該屬性默認爲 false。當設置爲 true 時,會啓用延遲初始化,即當首次調用 getter 方法時才進行初始化。

  • 使用lombok方式:

 1import lombok.Getter;
2
3public class GetterLazyExample {
4  @Getter(lazy=trueprivate final double[] cached = expensive();
5
6  private double[] expensive() {
7    double[] result = new double[1000000];
8    for (int i = 0; i < result.length; i++) {
9      result[i] = Math.asin(i);
10    }
11    return result;
12  }
13}
@Accessors

@Accessors註釋用於配置lombok如何生成和查找getter和setter。
默認情況下,lombok遵循針對getter和setter的bean規範:例如,名爲Pepper的字段的getter是getPepper。 但是,有些人可能希望打破bean規範,以得到更好看的API。 @Accessors提供3種方式:
fluent--》 一個布爾值。如果爲真,pepper的getter就是 pepper(),setter方法就是pepper(T newValue)。並且,除非特別說明,chain默認爲真。
chain--》 一個布爾值。如果爲真,產生的setter返回的this而不是void。默認是假。如果fluent=true,那麼chain默認爲真。
prefix--》 一系列string類型。如果顯示,屬性必須加上某些定義的前綴。

  • 使用lombok方式:

 1import lombok.experimental.Accessors;
2import lombok.Getter;
3import lombok.Setter;
4
5@Accessors(fluent = true)
6public class AccessorsExample {
7  @Getter @Setter
8  private int age = 10;
9}
10
11class PrefixExample {
12  @Accessors(prefix = "f") @Getter
13  private String fName = "Hello, World!";
14}

今天的內容就到這裏了,祝我好運,也祝你們好運,加油!

如果覺得這篇文章還不錯的話,求在看、求轉發,明人不說暗話,我喜歡這種被大傢伙寵愛的感覺。

one more thing!如果大家想要第一時間看到墨白更新的文章,可以掃描下方的二維碼,關注我的公衆號。我們下篇文章見!

本文分享自微信公衆號 - 框架師(mohu121)。
如有侵權,請聯繫 [email protected] 刪除。
本文參與“OSC源創計劃”,歡迎正在閱讀的你也加入,一起分享。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章