記事ディレクトリ
導入
公式サイト: https: //projectlombok.org/
Lombok は Java 開発プラグインで、Java 開発者は、特に単純な Java モデル オブジェクト (POJO) に対して定義されたいくつかのアノテーションを通じて、ビジネス エンジニアリングにおける冗長で煩わしいコードを排除できます。
開発環境で Lombok プラグインを使用すると、Java 開発者は、さまざまなビジネス オブジェクト モデルの hashCode や equals などのメソッド、accessor や ToString などのメソッドを繰り返し構築する作業にかかる時間を大幅に節約できます。これらのメソッドについては、ソース コードのコンパイル中に自動的に生成され、リフレクションのようにプログラムのパフォーマンスが低下することはありません。
Maven 依存関係をインポートする
最新バージョン 1.18.24 を使用する
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<scope>provided</scope>
<version>1.18.24</version>
</dependency>
よく使用される注釈
@NoArgsConstructor /@ AllArgsConstructor
- @NoArgsConstructor/@AllArgsConstructor は、パラメーターのないコンストラクターと、このクラスのすべてのパラメーターを含むコンストラクターを生成します。
テストケース 1:
@AllArgsConstructor
public class Demo extends Parent{
private String name;
private int age;
}
@AllArgsConstructor
@NoArgsConstructor
class Parent {
private Integer id;
}
コンパイルされた 2 つのクラス ファイルは次のとおりです。
このアノテーションは、親クラスの属性 ID を Demo コンストラクターに取り込みません。これには注意が必要です。
public class Demo {
private String name;
private int age;
public Demo() {
}
public Demo(String name, int age) {
this.name = name;
this.age = age;
}
}
class Parent {
private Integer id;
public Parent(Integer id) {
this.id = id;
}
public Parent() {
}
}
IDEA のクラス構造を通じて、何が生成されるかを確認することもできます
テストケース 2:
@AllArgsConstructor ( access = AccessLevel.PROTECTED) を通じて、コンストラクターのアクセス権を指定できます。
@AllArgsConstructor(access = AccessLevel.PROTECTED)
public class Demo{
private String name;
private int age;
}
コンパイル後に生成されるもの:
public class Demo {
private String name;
private int age;
protected Demo(String name, int age) {
this.name = name;
this.age = age;
}
}
テストケース 3:
@AllArgsConstructor(access = AccessLevel.PROTECTED、staticName = “test”)
@AllArgsConstructor(access = AccessLevel.PROTECTED, staticName = "test")
public class Demo{
private final int finalVal = 10;
private String name;
private int age;
}
コンパイル後:
public class Demo {
private String name;
private int age;
private Demo(String name, int age) {
this.name = name;
this.age = age;
}
protected static Demo test(String name, int age) {
return new Demo(name, age);
}
}
上記の効果は、生成されたコンストラクターのアクセス権を指定できることです。ただし、静的メソッドが指定されている場合、コンストラクターは自動的にprivateになり、アクセスは静的メソッドを通じてのみ提供され、最終的な属性値はコンストラクターに入力されないことがわかりました。
@NoArgsConstructor は @AllArgsConstructor と同じ方法で使用されます
@RequiredArgsConstructor
@RequiredArgsConstructor アノテーションは、クラス内の対応するすべてのコンストラクターを生成し@NonNull注解 / org.jetbrains.annotations.NotNull注解
ますfinal修饰的成员变量
。
テストケース:
@RequiredArgsConstructor
public class Demo {
@NonNull
private final int finalVal;
@NonNull
private String name;
@NonNull
private int age;
}
コンパイル後に生成されるもの:
import lombok.NonNull;
public class Demo {
@NonNull
private final int finalVal;
@NonNull
private String name;
@NonNull
private int age;
public Demo(@NonNull int finalVal, @NonNull String name, @NonNull int age) {
if (name == null) {
throw new NullPointerException("name is marked non-null but is null");
} else {
this.finalVal = finalVal;
this.name = name;
this.age = age;
}
}
}
説明: このアノテーションは、@NonNull フィールドと最終的に変更されたフィールドを識別し、このフィールドを要素として持つコンストラクターを生成します。
すべてのフィールドに @NonNull アノテーションがない場合、効果は @NoArgsConstructor と同じになります。
@RequiredArgsConstructor アノテーションのパラメータは他の 2 つのアノテーションと同じです。
注: もちろん、これら 3 つのコンストラクター アノテーションでは、メンバー変数が非静的であることが必要です。そうでない場合、静的変数はコンストラクターで割り当てられません。
@ゲッター/@セッター
このアノテーションのペアは、名前から容易に理解できます。メンバー変数またはクラスで使用すると、メンバー変数に対応する get メソッドと set メソッドを生成するのと同等になります。同時に、生成されたメソッドに対してアクセス修飾子を指定することもできます。もちろんデフォルトはpublicです
// 如果指定在类上,所有字段都会生成get/set方法
// 指定在字段上, 只有标注的字段才会生成get/set方法
@Getter
@Setter
public class Demo {
private String name;
private int age;
}
これら 2 つのアノテーションはクラスで直接使用され、このクラス内のすべての非静的メンバー変数に対して対応する get メソッドと set メソッドを生成できます。最終変数の場合は get メソッドのみになります
@ToString/@EqualsAndHashCode
これら 2 つのアノテーションも比較的理解しやすいものです。つまり、toString、equals、および hashcode メソッドが生成され、後者はオブジェクトが現在のクラスのインスタンスであるかどうかを判断する canEqual メソッドも生成します。メソッドの生成時には、クラス内の非静的メンバー変数のみが使用されます。
@ToString
@EqualsAndHashCode
public class Demo {
private String name;
private int age;
}
いくつかの主要なプロパティは toString の出力を制御できます。以下のことがわかります。
//@EqualsAndHashCode也有类似的下面的属性,
@ToString(
includeFieldNames = true, //是否使用字段名
exclude = {
"name"}, //排除某些字段
of = {
"age"}, //只使用某些字段
callSuper = true //是否让父类字段也参与 默认false
)
@データ
アノテーションコレクションに相当します。この効果は、@Getter + @Setter + @ToString + @EqualsAndHashCode + @RequiredArgsConstructorおよびこれら 5 つのアノテーションの効果と同等です。
@NoArgsConstructor と @AllArgsConstructor はここには含まれていないことに注意してください。
- したがって、一般に @Data を使用する場合は、これら 2 つのアノテーションと一緒に使用する必要があります。
@Data
public class Demo {
private String name;
private int age;
}
@ビルダー
@Builder は、値オブジェクトを構築するためのより尊重された方法を提供し、値オブジェクトを構築するための非常に推奨される方法です。
欠点は、親クラスのプロパティをビルダーで生成できないことです。
@Builder でマークされたクラスは、クラス内に内部クラスを生成して値オブジェクトを生成します。
@Builder
public class Demo {
private final int finalVal = 10;
private String name;
private int age;
}
コンパイル後に生成されるもの:
public class Demo {
private final int finalVal = 10;
private String name;
private int age;
Demo(String name, int age) {
this.name = name;
this.age = age;
}
public static Demo.DemoBuilder builder() {
return new Demo.DemoBuilder();
}
public static class DemoBuilder {
private String name;
private int age;
DemoBuilder() {
}
public Demo.DemoBuilder name(String name) {
this.name = name;
return this;
}
public Demo.DemoBuilder age(int age) {
this.age = age;
return this;
}
public Demo build() {
return new Demo(this.name, this.age);
}
public String toString() {
return "Demo.DemoBuilder(name=" + this.name + ", age=" + this.age + ")";
}
}
}
使い方:
public class Main {
public static void main(String[] args) {
Demo demo = Demo.builder().name("zss").age(20).build();
System.out.println(demo);
}
}
一般に、POJO クラスに対してマークする Lombok アノテーションの 90% は次の 4 つです: @Data、@NoArgsConstructor、@AllArgsConstructor、@Builder
@アクセサー
@Accessors getter メソッドと setter メソッド用に設計された、より流暢なアノテーション
このアノテーションは、setter メソッドと getter メソッドのデフォルト形式を変更するために @Getter および @Setter とともに使用する必要があります。
@Accessors属性の詳しい説明
- fluent 属性: 連鎖形式は特に使いやすく、メソッドの連結はますます便利です
- chain プロパティ: ストリーミング形式 (指定されたチェーンの値が表示されない場合、チェーンも true に設定されます)
- prefix 属性: 指定された接頭辞を持つプロパティのゲッター メソッドとセッター メソッドを生成します。生成されたゲッター メソッドとセッター メソッドは接頭辞を削除します。
@Accessors を使用せずにテストする場合
流暢な属性
デフォルトは false で、値が true の場合、対応するフィールドの getter メソッドの前に get は存在せず、setter メソッドに set も存在しません。
コンパイル後に生成されるもの:
public class Demo {
private final int finalVal = 10;
private String xxName;
private int yyAge;
public Demo() {
}
public int finalVal() {
Objects.requireNonNull(this);
return 10;
}
public String xxName() {
return this.xxName;
}
public int yyAge() {
return this.yyAge;
}
public Demo xxName(String xxName) {
this.xxName = xxName;
return this;
}
public Demo yyAge(int yyAge) {
this.yyAge = yyAge;
return this;
}
public String toString() {
int var10000 = this.finalVal();
return "Demo(finalVal=" + var10000 + ", xxName=" + this.xxName() + ", yyAge=" + this.yyAge() + ")";
}
}
使用:
public class Main {
public static void main(String[] args) {
Demo demo = new Demo();
// setter方法; 这里包含了chain=true的功能,可以链式设置值
demo.xxName("lucky").yyAge(20);
// getter方法
System.out.println(demo.xxName() + "," + demo.yyAge());
System.out.println("demo = " + demo);
}
}
チェーン属性
書かれていない場合、デフォルトは false です。値が true の場合、対応するフィールドの setter メソッドが呼び出された後、現在のオブジェクトが返され、チェーン内の値が設定されます。
コンパイル後に生成されるもの:
public class Demo {
private final int finalVal = 10;
private String xxName;
private int yyAge;
public Demo() {
}
public int getFinalVal() {
Objects.requireNonNull(this);
return 10;
}
public String getXxName() {
return this.xxName;
}
public int getYyAge() {
return this.yyAge;
}
public Demo setXxName(String xxName) {
this.xxName = xxName;
return this;
}
public Demo setYyAge(int yyAge) {
this.yyAge = yyAge;
return this;
}
public String toString() {
int var10000 = this.getFinalVal();
return "Demo(finalVal=" + var10000 + ", xxName=" + this.getXxName() + ", yyAge=" + this.getYyAge() + ")";
}
}
使用
public class Main {
public static void main(String[] args) {
Demo demo = new Demo();
// setter方法
demo.setXxName("lucky").setYyAge(20);
System.out.println("demo = " + demo);
}
}
プレフィックス属性
この属性は文字列の配列であり、配列に値がある場合、フィールド内の対応するプレフィックスを無視し、対応するゲッター メソッドとセッター メソッドを生成することを意味します。
@Accessors の属性値に接頭辞を追加すると、接頭辞がないかのようにフィールドのゲッター メソッドとセッター メソッドを呼び出すことができます。
ここでは、元の属性の接頭辞を削除するだけです
その他のメモ
@sneakythrows
このアノテーションはメソッドで使用されます。try-catch ステートメントでメソッド内のコードをラップし、例外をキャッチし、Lombok.sneakyThrow(e) を使用してキャッチで例外をスローできます。@SneakyThrows の形式を使用できます。 (Exception.class) どの例外をスローするかを指定します
public class Demo {
@SneakyThrows(UnsupportedEncodingException.class)
public String utf8ToString(byte[] bytes) {
return new String(bytes, "UTF8");
}
}
コンパイルして生成した後:
public class Demo {
public String utf8ToString(byte[] bytes) {
try {
return new String(bytes, "UTF8");
} catch (UnsupportedEncodingException var3) {
throw var3;
}
}
}
@価値
@Value アノテーションは @Data に似ていますが、デフォルトですべてのメンバー変数をプライベートの Final として定義し、set メソッドを生成しない点が異なります。
したがって、 @Value はより多くの読み取り専用クラスに適しているため、特殊な場合でも使用できます。
@掃除
@Cleanup はリソースを自動的に解放できます。try-with-resources との違い: try-with-resources と lombok の @Cleanup
このアノテーションは、局部变量
この変数によって表されるリソースが自動的に閉じられるようにするために使用されます。デフォルトでは、リソースの close() メソッドが呼び出されます。
リソースに他の終了メソッドがある場合は、それを使用して@Cleanup(“methodName”)
呼び出すメソッドを指定できます。例として入力ストリームと出力ストリームを使用してみましょう。
@SneakyThrows(Exception.class)
public static void main(String[] args) {
@Cleanup InputStream in = new FileInputStream(args[0]);
@Cleanup OutputStream out = new FileOutputStream(args[1]);
byte[] b = new byte[1024];
while (true) {
int r = in.read(b);
if (r == -1) break;
out.write(b, 0, r);
}
}
コンパイル後に生成されるもの:
public static void main(String[] args) {
try {
FileInputStream in = new FileInputStream(args[0]);
try {
FileOutputStream out = new FileOutputStream(args[1]);
try {
byte[] b = new byte[1024];
while(true) {
int r = in.read(b);
if (r == -1) {
return;
}
out.write(b, 0, r);
}
} finally {
if (Collections.singletonList(out).get(0) != null) {
out.close();
}
}
} finally {
if (Collections.singletonList(in).get(0) != null) {
in.close();
}
}
} catch (Exception var15) {
throw var15;
}
}
@NotNull
このアノテーションは、メンバー メソッドまたはコンストラクターのパラメーターで使用でき、このパラメーターの非 null チェックを自動的に生成します。パラメーターが null の場合、null ポインター例外がスローされます。
//成员方法参数加上@NonNull注解
public String getName(@NonNull Person p){
return p.getName();
}
コンパイルして生成した後:
public String getName(@NonNull Person p){
if(p == null){
throw new NullPointerException("person");
}
return p.getName();
}
@同期
メソッドに基づいて動作し、同期されたキーワードまたはロック ロックを置き換えることができます
このアノテーションは、クラス メソッドまたはインスタンス メソッドで使用されます。効果は synchronized キーワードと同じです。違いは、ロック オブジェクトが異なることです。クラス メソッドとインスタンス メソッドの場合、synchronized キーワードのロック オブジェクトはクラス オブジェクトとそれぞれクラスのこのオブジェクト。
@Synchronized のロック オブジェクトは、それぞれプライベート スタティック 最終オブジェクト ロックとプライベート 最終オブジェクト ロックです。もちろん、ロック オブジェクトを自分で指定することもできます
注意: 属性値はロック オブジェクトを指定します。ロック オブジェクトが存在しない場合、コンパイルは失敗します。デフォルト値は "" です。
public class Demo {
private Object obj;
@Synchronized
public static void hello() {
System.out.println("world");
}
@Synchronized
public int answerToLife() {
return 42;
}
@Synchronized("obj")
public void foo() {
System.out.println("bar");
}
}
コンパイル後に生成されるもの:
public class Demo {
private static final Object $LOCK = new Object[0];
private final Object $lock = new Object[0];
private Object obj;
public Demo() {
}
public static void hello() {
synchronized($LOCK) {
System.out.println("world");
}
}
public int answerToLife() {
synchronized(this.$lock) {
return 42;
}
}
public void foo() {
synchronized(this.obj) {
System.out.println("bar");
}
}
}
@Log、@Log4j、@Slf4j、@Log4j2、@CommonsLog、@XSlf4j などのログ アノテーション
ログの詳細については、私のブログ「ログ シリーズ」を参照してください。
これらのアノテーションにはトピック属性があります。 getLogger(String name) メソッドのパラメータを設定します。
これらのアノテーションはクラスで使用され、ログ ファクトリからログ オブジェクトを生成するステップを省略し、直接ログを記録できます。
特定のアノテーションはログ ツールによって異なりますが、同時にトピックをアノテーションで使用して、ログ オブジェクトを生成するときにクラス名を指定することもできます。さまざまなログの注釈を次のように要約します (上記は注釈であり、以下は実際の効果です)。
@Log アノテーション
デフォルトでは、java.util.logging.Logger オブジェクトが生成されます (JUL)
private static final java.util.logging.Logger log = java.util.logging.Logger.getLogger(LogExample.class.getName());
JUL ロギング フレームワークの使用
@Log
public class LombokJULTest {
/*
日志入口程序
java.util.logging.Logger
*/
// @Log标注在JULTest类上,就表示自动生成了下面这行代码
// Logger log = Logger.getLogger("com.lucky.jul.JULTest");
@Test
public void test01() {
// 方式1
log.info("输出info信息1");
// 方式2
log.log(Level.INFO, "输出info信息2");
}
}
控制台输出:
八月 14, 2022 9:17:13 上午 com.lucky.jul.JULTest test01
信息: 输出info信息1
八月 14, 2022 9:17:13 上午 com.lucky.jul.JULTest test01
信息: 输出info信息2
コンパイル後に生成されるもの:
public class LombokJULTest {
private static final Logger log = Logger.getLogger(LombokJULTest.class.getName());
public LombokJULTest() {
}
@Test
public void testLombokLog() {
log.info("输出info信息1");
log.log(Level.INFO, "输出info信息2");
}
}
@Log4j アノテーション
デフォルトでは、org.apache.log4j.Logger オブジェクトが生成されます。
private static final org.apache.log4j.Logger log = org.apache.log4j.Logger.getLogger(LogExample.class);
Log4j フレームワークを使用するケース:
<dependency>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
<version>1.2.17</version>
</dependency>
log4j 設定ファイル (リソースの下の log4j.properties ファイル)
log4j.rootLogger=trace,console,
#配置appender输出方式
log4j.appender.console=org.apache.log4j.ConsoleAppender
#配置输出的格式
log4j.appender.console.layout=org.apache.log4j.PatternLayout
log4j.appender.console.layout.conversionPattern=[%-5p]%r %c%t%d{yyyy-MM-dd HH:mm:ss:SSS} %m%n
@Log4j
public class LombokLog4jTest {
// 使用Lombok的@Log4j注解, 相当于会自动生成下面这个logger对象
// Logger log = Logger.getLogger(LombokLog4jTest.class);
@Test
public void testLombokLog4j() {
// BasicConfigurator.configure(); // 默认指定了log4j的logger,输出位置,输出格式;不需要配置文件也可以打印日志
// debug是默认的级别, 所以不会输出trace信息
log.fatal("fatal信息");
log.error("error信息");
log.warn("warn信息");
log.info("info信息");
log.debug("debug信息");
log.trace("trace信息");
}
}
控制台输出:
[FATAL]0 com.lucky.log4j.LombokLog4jTestmain2022-08-14 11:02:45:720 fatal信息
[ERROR]2 com.lucky.log4j.LombokLog4jTestmain2022-08-14 11:02:45:722 error信息
[WARN ]2 com.lucky.log4j.LombokLog4jTestmain2022-08-14 11:02:45:722 warn信息
[INFO ]3 com.lucky.log4j.LombokLog4jTestmain2022-08-14 11:02:45:723 info信息
コンパイル後に生成されるコード:
public class LombokLog4jTest {
private static final Logger log = Logger.getLogger(LombokLog4jTest.class);
public LombokLog4jTest() {
}
@Test
public void testLombokLog4j() {
log.fatal("fatal信息");
log.error("error信息");
log.warn("warn信息");
log.info("info信息");
log.debug("debug信息");
log.trace("trace信息");
}
}
@Log4j2 アノテーション
最も優れた Java ログ フレームワークである Log4j2 は、単純なログ ファサードとしても使用できます
private static final org.apache.logging.log4j.Logger log = org.apache.logging.log4j.LogManager.getLogger(LogExample.class);
使用例: (今回は単純なログ出力を実現するためにログ ファサードとして Log4j2 を使用します)
<dependencies>
<!-- log4j2日志门面 -->
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-api</artifactId>
<version>2.12.1</version>
</dependency>
<!-- log4j2日志实现 -->
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-core</artifactId>
<version>2.12.1</version>
</dependency>
<!-- 异步日志依赖 -->
<dependency>
<groupId>com.lmax</groupId>
<artifactId>disruptor</artifactId>
<version>3.3.7</version>
</dependency>
</dependencies>
リソースディレクトリの下のlog4j2.xml
<?xml version="1.0" encoding="utf-8" ?>
<Configuration status="debug">
<!-- 配置appender -->
<Appenders>
<Console name="consoleAppender" target="SYSTEM_ERR">
<PatternLayout pattern="[%-5level] %d{yyyy-MM-dd HH:mm:ss.SSS} %c %M %L %thread %m%n"/>
</Console>
</Appenders>
<!-- 配置logger -->
<Loggers>
<!-- 配置root logger -->
<Root level="trace">
<!-- 引用appender -->
<AppenderRef ref="consoleAppender"/>
</Root>
</Loggers>
</Configuration>
import lombok.extern.log4j.Log4j2;
import org.junit.Test;
@Log4j2
public class LombokLog4j2Test {
// @Log4j2会自动生成下面的Logger对象
// Logger log = LogManager.getLogger(Log4j2Test.class);
@Test
public void lombokLog4jTest() {
log.fatal("fatal信息");
log.error("error信息");
log.warn("warn信息");
log.info("info信息");
log.debug("debug信息");
log.trace("trace信息");
}
}
控制台输出:
[FATAL] 2022-08-14 11:43:31.845 com.lucky.Log4j2Test lombokLog4jTest 14 main fatal信息
[ERROR] 2022-08-14 11:43:31.849 com.lucky.Log4j2Test lombokLog4jTest 15 main error信息
[WARN ] 2022-08-14 11:43:31.849 com.lucky.Log4j2Test lombokLog4jTest 16 main warn信息
[INFO ] 2022-08-14 11:43:31.849 com.lucky.Log4j2Test lombokLog4jTest 17 main info信息
[DEBUG] 2022-08-14 11:43:31.850 com.lucky.Log4j2Test lombokLog4jTest 18 main debug信息
[TRACE] 2022-08-14 11:43:31.850 com.lucky.Log4j2Test lombokLog4jTest 19 main trace信息
コンパイル後に生成されるもの:
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.junit.Test;
public class LombokLog4j2Test {
private static final Logger log = LogManager.getLogger(LombokLog4j2Test.class);
public LombokLog4j2Test() {
}
@Test
public void lombokLog4jTest() {
log.fatal("fatal信息");
log.error("error信息");
log.warn("warn信息");
log.info("info信息");
log.debug("debug信息");
log.trace("trace信息");
}
}
@Slf4j アノテーション
Slf4j ログ ファサード (Simple Logging Facade For Java), Slf4j は主に Java ログ アクセス用の標準化された API フレームワークを提供することです。その主な意義はインターフェイスを提供することであり、特定の実装は他のログ フレームワークに引き渡すことができます。 log4j と logback の待機
private static final org.slf4j.Logger log = org.slf4j.LoggerFactory.getLogger(LogExample.class);
使用例: (Slf4j + Log4j2 でログ出力を実現)
<!-- slf4j日志门面 -->
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>1.7.25</version>
</dependency>
<!-- log4j2适配器 -->
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-slf4j-impl</artifactId>
<version>2.12.1</version>
</dependency>
<!-- log4j2日志门面 -->
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-api</artifactId>
<version>2.12.1</version>
</dependency>
<!-- log4j2日志实现 -->
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-core</artifactId>
<version>2.12.1</version>
</dependency>
<!-- 异步日志依赖 -->
<dependency>
<groupId>com.lmax</groupId>
<artifactId>disruptor</artifactId>
<version>3.3.7</version>
</dependency>
リソースディレクトリの下のlog4j2.xml
<?xml version="1.0" encoding="utf-8" ?>
<Configuration status="debug">
<!-- 配置appender -->
<Appenders>
<Console name="consoleAppender" target="SYSTEM_ERR">
<PatternLayout pattern="[%-5level] %d{yyyy-MM-dd HH:mm:ss.SSS} %c %M %L %thread %m%n"/>
</Console>
</Appenders>
<!-- 配置logger -->
<Loggers>
<!-- 配置root logger -->
<Root level="trace">
<!-- 引用appender -->
<AppenderRef ref="consoleAppender"/>
</Root>
</Loggers>
</Configuration>
import lombok.extern.slf4j.Slf4j;
import org.junit.Test;
@Slf4j
public class LombokSlf4jTest {
// @Slf4j会自动生成下面这个Logger对象
// Logger log = LoggerFactory.getLogger(LombokSlf4jTest.class);
@Test
public void lombokSlf4jTest() {
log.error("error信息");
log.warn("warn信息");
log.info("info信息");
log.debug("debug信息");
log.trace("trace信息");
}
}
コンパイル後に生成されるもの:
import org.junit.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class LombokSlf4jTest {
private static final Logger log = LoggerFactory.getLogger(LombokSlf4jTest.class);
public LombokSlf4jTest() {
}
@Test
public void lombokSlf4jTest() {
log.error("error信息");
log.warn("warn信息");
log.info("info信息");
log.debug("debug信息");
log.trace("trace信息");
}
}
その他のロンボク島ログのコメントは自分で理解してください
@CommonsLog
private static final org.apache.commons.logging.Log log = org.apache.commons.logging.LogFactory.getLog(LogExample.class);
@JBossLog
private static final org.jboss.logging.Logger log = org.jboss.logging.Logger.getLogger(LogExample.class);
@XSlf4j
private static final org.slf4j.ext.XLogger log = org.slf4j.ext.XLoggerFactory.getXLogger(LogExample.class);
@デリゲート
@Delegate によって注釈が付けられた属性は、この属性タイプのパブリック非静的メソッドを現在のクラスに結合します。
public class Person {
public void personMsg() {
System.out.println("Person.personMsg");
}
public String printName(String name) {
return name;
}
private Integer printAge(Integer age) {
return age;
}
public static void printOther() {
System.out.println("Person.printOther");
}
}
@Getter
@Setter
public class Demo {
@Delegate
private Person person;
}
コンパイル後に生成されるもの:
public class Demo {
private Person person;
public Demo() {
}
public Person getPerson() {
return this.person;
}
public void setPerson(Person person) {
this.person = person;
}
public void personMsg() {
this.getPerson().personMsg();
}
public String printName(String name) {
return this.getPerson().printName(name);
}
}
使用:
public class Main {
public static void main(String[] args) {
Demo demo = new Demo();
demo.setPerson(new Person());
demo.personMsg();
System.out.println(demo.printName("lucky"));
}
}
@特異な
@Singular を使用してコレクション フィールドに注釈を付けます (value 属性値が指定されていない場合、コレクション フィールド名は複数形である必要があります)。コレクションに単一の要素を追加する要素追加メソッドが生成されます。
@Builder アノテーションでのみ使用できます。これはフィールドとパラメーターに作用し、通常はコレクション プロパティとコレクション パラメーターで使用されます。
使用:
public class Main {
public static void main(String[] args) {
Demo demo = Demo.builder().name("lucky")
.num(1).num(2).num(3)
.build();
System.out.println("demo = " + demo);
}
}
控制台输出:
demo = Demo(name=lucky, nums=[1, 2, 3])