Project Lombok是一個非常有用的工具,適用於Java項目,可以減少樣板代碼。
問題陳述
在Java與其他語言的辯論中,其他語言支持者首先批評的是Java需要大量的樣板代碼,你無法克服它,也無法自衛。同樣的問題也在多個平台和開發者社區中報告過。讓我們看一下一段有樣板代碼的代碼示例。
package com.askrakesh.java.manage_boilerplate;
import java.time.LocalDate;
public class Person {
String firstName;
String lastName;
LocalDate dateOfBirth;
public Person(String firstName, String lastName, LocalDate dateOfBirth) {
super();
this.firstName = firstName;
this.lastName = lastName;
this.dateOfBirth = dateOfBirth;
}
public String getFirstName() {
return firstName;
}
public void setFirstName(String firstName) {
this.firstName = firstName;
}
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
this.lastName = lastName;
}
public LocalDate getDateOfBirth() {
return dateOfBirth;
}
public void setDateOfBirth(LocalDate dateOfBirth) {
this.dateOfBirth = dateOfBirth;
}
@Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + ((dateOfBirth == null) ? 0 : dateOfBirth.hashCode());
result = prime * result + ((firstName == null) ? 0 : firstName.hashCode());
result = prime * result + ((lastName == null) ? 0 : lastName.hashCode());
return result;
}
@Override
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
Person other = (Person) obj;
if (dateOfBirth == null) {
if (other.dateOfBirth != null)
return false;
} else if (!dateOfBirth.equals(other.dateOfBirth))
return false;
if (firstName == null) {
if (other.firstName != null)
return false;
} else if (!firstName.equals(other.firstName))
return false;
if (lastName == null) {
if (other.lastName != null)
return false;
} else if (!lastName.equals(other.lastName))
return false;
return true;
}
@Override
public String toString() {
return "Person [firstName=" + firstName + ", lastName=" + lastName + "dateOfBirth=" + dateOfBirth + "]";
}
}
A class should have getter-setters for the instance variables, equals
& hashCode
method implementation, all field constructors and an implementation of toString
method. This class so far has no business logic and even without it is 80+ lines of code. This is insane.
Project Lombok
Project Lombok是一個Java庫,它可以自動插入到您的編輯器和構建工具中,幫助減少樣板代碼。讓我們首先看一下如何設置Lombok項目。
Java Project Lombok如何工作?
Lombok 具有各種註釋,可在我們的代碼中使用,這些註釋在編譯時進行處理,根據使用的註釋進行適當的代碼擴展。 Lombok 只在查看時間進行代碼減少,在編譯後,字節碼將注入所有樣板。這有助於保持我們的代碼庫小,乾淨,易於閱讀和維護。
項目 Lombok Maven
將 Lombok 添加到您的項目中很簡單。只需在您的 maven 項目 pom.xml 文件中添加以下依賴即可。
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>1.16.20</version>
</dependency>
在 IDE(Eclipse)中添加 Lombok 插件
以下是 Windows 的安裝步驟:
- 從 https://projectlombok.org/download 下載 jar 文件,或使用從您的 maven 構建中下載的 jar 文件。
- 在終端中執行以下命令:
java -jar lombok.jar
- 此命令將打開如下圖所示的窗口,安裝並退出安裝程序,然後重新啟動 eclipse。
如果您使用 MacOS,則以下是在項目中使用 Lombok 的步驟。
- 將 lombok.jar 複製到
Eclipse.app/Contents/MacOS
目錄中。 - 將
-javaagent:lombok.jar
添加到Eclipse.app/Contents/Eclipse/eclipse.ini
檔案的末尾。 - 重新啟動 Eclipse,並在項目屬性中啟用“注解處理”,如下圖所示。
Lombok 在 Eclipse 大綱中的預覽
安裝完成後,讓我們檢查如何查看我們減少的樣板代碼?我已重新建立了與 PersonLombok
相同的類別。Eclipse 大綱顯示了 firstName 的 getter 和 setter。這是基於 Lombok 的 @Getter
和 @Setter
註釋 設置的實例變量 firstName。
Lombok 在 Java 字節碼中的預覽
我們可以從類別字節碼中檢查對於 firstName 的 getter 和 setter 方法的添加。
Project Lombok 注解
Project Lombok 提供許多注解,可幫助在各種情境中減少樣板代碼。讓我們來看看其中一些。
-
建構子注解
@AllArgsConstructor public class PersonLombok { @NonNull String firstName; String lastName; LocalDate dateOfBirth; public static void main(String[] args) { new PersonLombok(null, "Kumar", LocalDate.now()); } }
上述程式碼在類別中注入以下內容:
- 通過 @AllArgsConstructor 創建具有所有引數的建構子
- 通過 @NonNull 在建構子中對引數進行空值檢查。在將引數作為方法參數傳遞時,也可以使用 @NonNull 注解
這是程式運行的結果。
@RequiredArgsConstructor
會為每個需要特殊處理的欄位生成一個參數的建構子。所有未初始化的最終欄位都會得到一個參數,以及所有被標記為@NonNull
但在宣告處未初始化的欄位。 -
Getter/Setter註釋
這些註釋可以在字段或類級別使用。如果您想要細粒度控制,請在字段級別使用它。當在類級別使用時,將創建所有getter/setter。讓我們來處理上面創建的類。
@AllArgsConstructor @Getter @Setter public class PersonLombok { String firstName; String lastName; LocalDate dateOfBirth; }
-
equals, hashCode 和 toString 註釋
在創建類時,建議覆寫
hashCode()
和equals()
方法。在 Lombok 中,我們有@EqualsAndHashCode
註釋,它會注入equals()和hashCode()方法的代碼,因為它們是一起使用的。此外,@ToString
註釋提供了toString()的實現。讓我們看看這個:@AllArgsConstructor @Getter @Setter @EqualsAndHashCode @ToString public class PersonLombok { String firstName; String lastName; LocalDate dateOfBirth; }
現在我們已經使用 Lombok 註釋成功創建了 Person 類,而無需任何樣板代碼。然而,更好的是,我們可以用
@Data
替換上面類中使用的所有註釋,並獲得相同的功能。 -
基於設計模式的註釋
@Builder
讓您自動生成所需的代碼,以使您的類別可使用 建造者模式 進行實例化。@Builder public class Employee { String firstName; String lastName; LocalDate dateOfBirth; public static void main(String[] args) { Employee emp = new EmployeeBuilder().firstName("Rakesh") .lastName("Kumar") .dateOfBirth(LocalDate.now()) .build(); } }
@Delegate
生成將呼叫轉發到使用該註釋的字段的委派方法。”優先選擇組合而不是繼承”,但這會創建很多類似於 適配器模式 的樣板代碼。Lombok 在實現此功能時從 Groovy 的同名註釋中得到了提示。讓我們看一個實現:@RequiredArgsConstructor public class AdapterImpl implements Adapter { @Delegate private final Adaptee instance; public static void main(String[] args) { AdapterImpl impl = new AdapterImpl(new Adaptee()); impl.display(); } } interface Adapter { public void display(); } class Adaptee { public void display() { System.out.println("In Adaptee.display()"); } }
Lombok 為所有註釋提供了細粒度控制的功能。
樣板程式碼:Java 架構師是否在聽?
是的,它們是。你需要明白,與其他語言不同,Java 已經非常注意升級語言,使其不會破壞任何舊版本 Java 中的現有代碼庫。這本身就是一個巨大的任務,不能被低估。他們已經在語言中修改並建立了更好的類型推斷能力。Java 10 計劃的重要功能之一是局部變量類型推斷。儘管這個功能更多地與添加動態類型有關,而不是簡化冗長的程式碼,但這只是管理冗長程式碼的冰山一角。
總結
簡化冗長的程式碼有助於提高可讀性,代碼量減少也意味著錯誤減少。Project Lombok 今天在幾乎所有主要組織中都被大量使用。我們為您提供了 Lombok 中最有用的功能。希望您試試看。源代碼:您可以訪問我的Github 鏈接來下載本教程中使用的完整源代碼。
Source:
https://www.digitalocean.com/community/tutorials/java-project-lombok