Lombok
作用:帮使用者提高编码效率,减少重复与冗余的代码
原理:ASM 动态修改class文件
配置
maven
依赖
<dependency><groupId>org.projectlombok</groupId><artifactId>lombok</artifactId><version>1.16.8</version></dependency>
编译
<build><plugins><plugin><groupId>org.projectlombok</groupId><artifactId>lombok-maven-plugin</artifactId><version>1.16.6.1</version></plugin></plugins></build>
idea
- 安装插件

常用注解:
java bean相关
@Setter
功能
生成setter方法
源码
@Setterpublic class LombokDemo {private Integer id;private String name;}
编译后
package xyz.mrwood.study.lombok;public class LombokDemo {private Integer id;private String name;public LombokDemo() {}public void setId(Integer id) {this.id = id;}public void setName(String name) {this.name = name;}}
@Getter
功能
生成getter方法
源码
@Getterpublic class LombokDemo {private Integer id;private String name;}
编译后
package xyz.mrwood.study.lombok;public class LombokDemo {private Integer id;private String name;public LombokDemo() {}public Integer getId() {return this.id;}public String getName() {return this.name;}}
@ToString
功能
生成toString方法
源码
@ToStringpublic class LombokDemo {private Integer id;private String name;}
编译后
package xyz.mrwood.study.lombok;public class LombokDemo {private Integer id;private String name;public LombokDemo() {}public String toString() {return "LombokDemo(id=" + this.id + ", name=" + this.name + ")";}}
@Getter(lazy = true)
功能
懒加载属性
注意:
这个与上面@Getter不同,那个是修饰在类上的,也可以修饰在属性上。如果有lazy=true只能修饰在属性,并且还要是private final修饰,限制很大
编码
public class LombokDemo {@Getter(lazy = true) private final List<Integer> ids = Arrays.asList(1, 2, 3, 4);private String name;}
编译后
package xyz.mrwood.study.lombok;import java.util.Arrays;import java.util.List;import java.util.concurrent.atomic.AtomicReference;public class LombokDemo {private final AtomicReference<Object> ids = new AtomicReference();private String name;public LombokDemo() {}public List<Integer> getIds() {Object value = this.ids.get();if(value == null) {AtomicReference var2 = this.ids;synchronized(this.ids) {value = this.ids.get();if(value == null) {List actualValue = Arrays.asList(new Integer[]{Integer.valueOf(1), Integer.valueOf(2), Integer.valueOf(3), Integer.valueOf(4)});value = actualValue == null?this.ids:actualValue;this.ids.set(value);}}}return (List)((List)(value == this.ids?null:value));}}
@EqualsAndHashCode
功能
生成equals方法与hashCode方法
源码
@EqualsAndHashCodepublic class LombokDemo {private Integer id;private String name;}
编译后
package xyz.mrwood.study.lombok;public class LombokDemo {private Integer id;private String name;public LombokDemo() {}public boolean equals(Object o) {if(o == this) {return true;} else if(!(o instanceof LombokDemo)) {return false;} else {LombokDemo other = (LombokDemo)o;if(!other.canEqual(this)) {return false;} else {Integer this$id = this.id;Integer other$id = other.id;if(this$id == null) {if(other$id != null) {return false;}} else if(!this$id.equals(other$id)) {return false;}String this$name = this.name;String other$name = other.name;if(this$name == null) {if(other$name != null) {return false;}} else if(!this$name.equals(other$name)) {return false;}return true;}}}protected boolean canEqual(Object other) {return other instanceof LombokDemo;}public int hashCode() {boolean PRIME = true;byte result = 1;Integer $id = this.id;int result1 = result * 59 + ($id == null?43:$id.hashCode());String $name = this.name;result1 = result1 * 59 + ($name == null?43:$name.hashCode());return result1;}}
@NoAragsConstructor
功能
添加一个无参构造函数
注意
这个注解在没有其它有参构造函数的情况下使用意义不大,因为在这种情况下java默认会添加一个无参构造函数
源码
@NoArgsConstructorpublic class LombokDemo {private Integer id;private String name;}
编译后
package xyz.mrwood.study.lombok;public class LombokDemo {private Integer id;private String name;public LombokDemo() {}}
@AllArgsConstructor
功能
添加一个所有参数的构造函数
源码
@AllArgsConstructorpublic class LombokDemo {private Integer id;private String name;}
编译后
package xyz.mrwood.study.lombok;import java.beans.ConstructorProperties;public class LombokDemo {private Integer id;private String name;@ConstructorProperties({"id", "name"})public LombokDemo(Integer id, String name) {this.id = id;this.name = name;}}
@RequiredArgsConstructor
功能
生成一个包含必填参数的构造函数
注意
要与@NonNull 搭配使用,该注解修饰的属性就是必填参数
源码
@RequiredArgsConstructorpublic class LombokDemo {@NonNull private Integer id;private String name;}
编译后
package xyz.mrwood.study.lombok;import java.beans.ConstructorProperties;import lombok.NonNull;public class LombokDemo {@NonNullprivate Integer id;private String name;@ConstructorProperties({"id"})public LombokDemo(@NonNull Integer id) {if(id == null) {throw new NullPointerException("id");} else {this.id = id;}}}
@Data
功能
这是一个综合注解了,等于同时使用
@Getter,@Setter,@ToString,@EqualsAndHashCode,@RequiredArgsConstructor
源码
@Datapublic class LombokDemo {@NonNull private Integer id;private String name;}
编译后
package xyz.mrwood.study.lombok;public class LombokDemo {private Integer id;private String name;public LombokDemo() {}public Integer getId() {return this.id;}public String getName() {return this.name;}public void setId(Integer id) {this.id = id;}public void setName(String name) {this.name = name;}public boolean equals(Object o) {if(o == this) {return true;} else if(!(o instanceof LombokDemo)) {return false;} else {LombokDemo other = (LombokDemo)o;if(!other.canEqual(this)) {return false;} else {Integer this$id = this.getId();Integer other$id = other.getId();if(this$id == null) {if(other$id != null) {return false;}} else if(!this$id.equals(other$id)) {return false;}String this$name = this.getName();String other$name = other.getName();if(this$name == null) {if(other$name != null) {return false;}} else if(!this$name.equals(other$name)) {return false;}return true;}}}protected boolean canEqual(Object other) {return other instanceof LombokDemo;}public int hashCode() {boolean PRIME = true;byte result = 1;Integer $id = this.getId();int result1 = result * 59 + ($id == null?43:$id.hashCode());String $name = this.getName();result1 = result1 * 59 + ($name == null?43:$name.hashCode());return result1;}public String toString() {return "LombokDemo(id=" + this.getId() + ", name=" + this.getName() + ")";}}
@Value
功能
不可变类的@Data, 他会默认给属性加上final
源码
@Valuepublic class LombokDemo {private Integer id;private String name;}
编译后
package xyz.mrwood.study.lombok;import java.beans.ConstructorProperties;public final class LombokDemo {private final Integer id;private final String name;@ConstructorProperties({"id", "name"})public LombokDemo(Integer id, String name) {this.id = id;this.name = name;}public Integer getId() {return this.id;}public String getName() {return this.name;}public boolean equals(Object o) {if(o == this) {return true;} else if(!(o instanceof LombokDemo)) {return false;} else {LombokDemo other = (LombokDemo)o;Integer this$id = this.getId();Integer other$id = other.getId();if(this$id == null) {if(other$id != null) {return false;}} else if(!this$id.equals(other$id)) {return false;}String this$name = this.getName();String other$name = other.getName();if(this$name == null) {if(other$name != null) {return false;}} else if(!this$name.equals(other$name)) {return false;}return true;}}public int hashCode() {boolean PRIME = true;byte result = 1;Integer $id = this.getId();int result1 = result * 59 + ($id == null?43:$id.hashCode());String $name = this.getName();result1 = result1 * 59 + ($name == null?43:$name.hashCode());return result1;}public String toString() {return "LombokDemo(id=" + this.getId() + ", name=" + this.getName() + ")";}}
@Accessors
功能
这个注解要搭配@Getter与@Setter使用,用来修改默认的setter与getter方法的形式
注意
@Accessors有三个参数可以使用
chain 链式的形式
fluent 流式的形式
prefix 生成指定前缀的属性的getter与setter方法,并且生成的getter与setter方法时会去除前缀
源码 chain = true
@Accessors(chain = true)@Setter@Getterpublic class LombokDemo {private Integer id;private String name;}
编译后 chain = true
package xyz.mrwood.study.lombok;public class LombokDemo {private Integer id;private String name;public LombokDemo() {}public LombokDemo setId(Integer id) {this.id = id;return this;}public LombokDemo setName(String name) {this.name = name;return this;}public Integer getId() {return this.id;}public String getName() {return this.name;}}
源码 fluent = true
@Accessors(fluent = true)@Setter@Getterpublic class LombokDemo {private Integer id;private String name;}
编译后 fluent = true
package xyz.mrwood.study.lombok;public class LombokDemo {private Integer id;private String name;public LombokDemo() {}public LombokDemo id(Integer id) {this.id = id;return this;}public LombokDemo name(String name) {this.name = name;return this;}public Integer id() {return this.id;}public String name() {return this.name;}}
源码 prefix = "xxx"
@Accessors(prefix = "xxx")@Setter@Getterpublic class LombokDemo {private Integer xxxId;private String name;}
编译后 prefix = "xxx"
package xyz.mrwood.study.lombok;public class LombokDemo {private Integer xxxId;private String name;public LombokDemo() {}public void setId(Integer xxxId) {this.xxxId = xxxId;}public Integer getId() {return this.xxxId;}}
其它注解:
日志相关
@Log4j
源码
@Log4jpublic class LombokDemo {private Integer xxxId;private String name;}
编译后
package xyz.mrwood.study.lombok;import org.apache.log4j.Logger;public class LombokDemo {private static final Logger log = Logger.getLogger(LombokDemo.class);private Integer xxxId;private String name;public LombokDemo() {}}
@CommonsLog
源码
@CommonsLogpublic class LombokDemo {private Integer xxxId;private String name;}
编译后
package xyz.mrwood.study.lombok;import org.apache.commons.logging.Log;import org.apache.commons.logging.LogFactory;public class LombokDemo {private static final Log log = LogFactory.getLog(LombokDemo.class);private Integer xxxId;private String name;public LombokDemo() {}}
@Log
源码
@Logpublic class LombokDemo {private Integer xxxId;private String name;}
编译后
package xyz.mrwood.study.lombok;import java.util.logging.Logger;public class LombokDemo {private static final Logger log = Logger.getLogger(LombokDemo.class.getName());private Integer xxxId;private String name;public LombokDemo() {}}
@Log4j2
源码
@Log4j2public class LombokDemo {private Integer xxxId;private String name;}
编译后
package xyz.mrwood.study.lombok;import org.apache.logging.log4j.LogManager;import org.apache.logging.log4j.Logger;public class LombokDemo {private static final Logger log = LogManager.getLogger(LombokDemo.class);private Integer xxxId;private String name;public LombokDemo() {}}
@Slf4j
源码
@Slf4jpublic class LombokDemo {private Integer xxxId;private String name;}
编译后
package xyz.mrwood.study.lombok;import org.slf4j.Logger;import org.slf4j.LoggerFactory;public class LombokDemo {private static final Logger log = LoggerFactory.getLogger(LombokDemo.class);private Integer xxxId;private String name;public LombokDemo() {}}
设计模式相关
@Builder
功能
通过建造者模块来生成bean
源码
@Builderpublic class LombokDemo {private Integer id;private String name;}
编译后
package xyz.mrwood.study.lombok;public class LombokDemo {private Integer id;private String name;LombokDemo(Integer id, String name) {this.id = id;this.name = name;}public static LombokDemo.LombokDemoBuilder builder() {return new LombokDemo.LombokDemoBuilder();}public static class LombokDemoBuilder {private Integer id;private String name;LombokDemoBuilder() {}public LombokDemo.LombokDemoBuilder id(Integer id) {this.id = id;return this;}public LombokDemo.LombokDemoBuilder name(String name) {this.name = name;return this;}public LombokDemo build() {return new LombokDemo(this.id, this.name);}public String toString() {return "LombokDemo.LombokDemoBuilder(id=" + this.id + ", name=" + this.name + ")";}}}
@Delegate
功能
@Delegate注释的属性,会把这个属性对象的公有非静态方法合到当前类
注意
公共 非静态方法
源码
public class LombokDemo {@Delegateprivate Integer id;private String name;}
编译后
package xyz.mrwood.study.lombok;public class LombokDemo {private Integer id;private String name;public LombokDemo() {}public byte byteValue() {return this.id.byteValue();}public short shortValue() {return this.id.shortValue();}public int intValue() {return this.id.intValue();}public long longValue() {return this.id.longValue();}public float floatValue() {return this.id.floatValue();}public double doubleValue() {return this.id.doubleValue();}public int compareTo(Integer arg0) {return this.id.compareTo(arg0);}}
工具相关
@Cleanup
功能
关闭流
注意
关闭流的方式有点怪异,而且没有在finally里面关闭,如果出现异常的就不会关闭了
源码
public class LombokDemo {public void test() throws IOException {@Cleanup InputStream inputStream = new FileInputStream("xxx.txt");}}
编译后
package xyz.mrwood.study.lombok;import java.io.FileInputStream;import java.io.IOException;import java.util.Collections;public class LombokDemo {public LombokDemo() {}public void test() throws IOException {FileInputStream inputStream = new FileInputStream("xxx.txt");if(Collections.singletonList(inputStream).get(0) != null) {inputStream.close();}}}
@Synchronized
功能
给方法加一个同步块
源码
public class LombokDemo {@Synchronizedpublic void test() throws IOException {System.out.println("test");}}
编译后
package xyz.mrwood.study.lombok;import java.io.IOException;public class LombokDemo {private final Object $lock = new Object[0];public LombokDemo() {}public void test() throws IOException {Object var1 = this.$lock;synchronized(this.$lock) {System.out.println("test");}}}
@SneakyThrows
功能
忽略异常
源码
public class LombokDemo {@SneakyThrowspublic void test() {String s = new String("test".getBytes(), "utf-8");}}
编译后
package xyz.mrwood.study.lombok;import java.io.IOException;public class LombokDemo {private final Object $lock = new Object[0];public LombokDemo() {}public void test() throws IOException {Object var1 = this.$lock;synchronized(this.$lock) {System.out.println("test");}}}
@NonNull
功能
设置不能为空的参数
源码
public class LombokDemo {public void test(@NonNull String val) {}}
编译后
package xyz.mrwood.study.lombok;import lombok.NonNull;public class LombokDemo {public LombokDemo() {}public void test(@NonNull String val) {if(val == null) {throw new NullPointerException("val");}}}
@UtilityClass
功能
把普通类转为工具类
源码
@UtilityClasspublic class LombokDemo {private Integer id = 1;private String name = "kiwi";public void util(){System.out.println("xxx");}}
编译后
package xyz.mrwood.study.lombok;public final class LombokDemo {private static Integer id = Integer.valueOf(1);private static String name = "kiwi";public static void util() {System.out.println("xxx");}private LombokDemo() {throw new UnsupportedOperationException("This is a utility class and cannot be instantiated");}}
