@Data // 生成getter和setter方法
@AllArgsConstructor // 有参构造器
@NoArgsConstructor // 无参构造器
@ToString // toString方法
@Accessors(chain = true)
@TableName("user") // 指定表名称
public class User {
private String id;
private String name;
private Integer age;
private Date bir;
}
# 例如
@TableName("user_tbl")
public class User {
// 标注在id属性上,用于映射数据库中的id
@TableId(value="id")
private int id;
// 标注在属性上,用于映射数据库中的属性
@TableField(value="bir")
private Date birthday;
//标注在属性上,表示该属性在数据库中不存在,则不会映射
@TableField(exist = false)
private String userName;
}
- @Accessors(chain = true)详解
@Accessors(chain = true) // 为 true 时,对应字段的 setter 方法调用后,会返回当前对象
# 检查参数是否为空
public void nonNullDemo(@NonNull Employee employee, @NonNull Account account) {
// just do stuff
}
//成员方法参数加上@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();
}
父类实体类中通常设置为@EqualsAndHashCode(callSuper = false)
子类继承父类后设置为@EqualsAndHashCode(callSuper = true)
用于重写equals和hashcode方法
@Data 是 @Getter、 @Setter、 @ToString、 @EqualsAndHashCode 和 @RequiredArgsConstructor 的快捷方式
用@Data(staticConstructor=”methodName”)来生成一个静态方法,返回一个调用相应的构造方法产生的对象
# 例如
@Data(staticConstructor = "of")
public class Student {
@Setter(AccessLevel.PROTECTED)
@NonNull
private String name;
private Integer age;
}
# 等同于
package com.cauchy6317.common.Data;
import lombok.NonNull;
public class Student {
@NonNull
private String name;
private Integer age;
private Student(@NonNull String name) {
if (name == null) {
throw new NullPointerException("name is marked non-null but is null");
} else {
this.name = name;
}
}
public static Student of(@NonNull String name) {
return new Student(name);
}
@NonNull
public String getName() {
return this.name;
}
public Integer getAge() {
return this.age;
}
public void setAge(Integer age) {
this.age = age;
}
public boolean equals(Object o) {
if (o == this) {
return true;
} else if (!(o instanceof Student)) {
return false;
} else {
Student other = (Student)o;
if (!other.canEqual(this)) {
return false;
} else {
Object this$name = this.getName();
Object other$name = other.getName();
if (this$name == null) {
if (other$name != null) {
return false;
}
} else if (!this$name.equals(other$name)) {
return false;
}
Object this$age = this.getAge();
Object other$age = other.getAge();
if (this$age == null) {
if (other$age != null) {
return false;
}
} else if (!this$age.equals(other$age)) {
return false;
}
return true;
}
}
}
protected boolean canEqual(Object other) {
return other instanceof Student;
}
public int hashCode() {
int PRIME = true;
int result = 1;
Object $name = this.getName();
int result = result * 59 + ($name == null ? 43 : $name.hashCode());
Object $age = this.getAge();
result = result * 59 + ($age == null ? 43 : $age.hashCode());
return result;
}
public String toString() {
return "Student(name=" + this.getName() + ", age=" + this.getAge() + ")";
}
protected void setName(@NonNull String name) {
if (name == null) {
throw new NullPointerException("name is marked non-null but is null");
} else {
this.name = name;
}
}
}
@Value注解会把所有成员变量默认定义为private final修饰,并且不会生成set方法
等同于@Getter、@ToString、@EqualsAndHashCode、@RequiredArgsConstructor
public class Car {
private String make;
private String model;
private String bodyType;
private int yearOfManufacture;
private int cubicCapacity;
private List<LocalDate> serviceDate;
}
# 使用该注解时,构建1个对象
Car muscleCar = Car.builder().make("Ford")
.model("mustang")
.bodyType("coupe")
.build();
# 例如
public class User {
private final String username;
private final String emailAddress;
@With
private final boolean isAuthenticated;
//getters, constructors
}
public class User {
private final String username;
private final String emailAddress;
private final boolean isAuthenticated;
//getters, constructors
public User withAuthenticated(boolean isAuthenticated) {
return this.isAuthenticated == isAuthenticated ? this : new User(this.username, this.emailAddress, isAuthenticated);
}
}
User immutableUser = new User("testuser", "test@mail.com", false);
User authenticatedUser = immutableUser.withAuthenticated(true);
assertNotSame(immutableUser, authenticatedUser);
assertFalse(immutableUser.isAuthenticated());
assertTrue(authenticatedUser.isAuthenticated());
# 这个注解用在变量前面,可以保证此变量代表的资源会被自动关闭,默认是调用资源的close()方法,如果该资源有其它关闭方法,可使用@Cleanup(“methodName”)来指定要调用的方法
# 例如
public static void main(String[] args) throws IOException {
@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);
}
}
使用类中所有带有@NonNull注解的或者带有final修饰的成员变量生成对应的构造方法,成员变量都是非静态的
如果类中含有final修饰的成员变量,是无法使用@NoArgsConstructor注解的
用@RequiredArgsConstructor(staticName=”methodName”)的形式生成一个指定名称的静态方法,返回一个调用相应的构造方法产生的对象
# 例如
@RequiredArgsConstructor(staticName = "sunsfan")
@AllArgsConstructor(access = AccessLevel.PROTECTED)
@NoArgsConstructor
public class Shape {
private int x;
@NonNull
private double y;
@NonNull
private String name;
}
# 等同于
public class Shape {
private int x;
private double y;
private String name;
public Shape(){
}
protected Shape(int x,double y,String name){
this.x = x;
this.y = y;
this.name = name;
}
public Shape(double y,String name){
this.y = y;
this.name = name;
}
public static Shape sunsfan(double y,String name){
return new Shape(y,name);
}
}
# 将方法中的代码用try-catch语句包裹起来
# 捕获异常并在catch中用Lombok.sneakyThrow(e)把异常抛出
# 可以使用@SneakyThrows(Exception.class)的形式指定抛出哪种异常
# 例如
public class SneakyThrows implements Runnable {
@SneakyThrows(UnsupportedEncodingException.class)
public String utf8ToString(byte[] bytes) {
return new String(bytes, "UTF-8");
}
@SneakyThrows
public void run() {
throw new Throwable();
}
}
# 等同于
public class SneakyThrows implements Runnable {
@SneakyThrows(UnsupportedEncodingException.class)
public String utf8ToString(byte[] bytes) {
try{
return new String(bytes, "UTF-8");
}catch(UnsupportedEncodingException uee){
throw Lombok.sneakyThrow(uee);
}
}
@SneakyThrows
public void run() {
try{
throw new Throwable();
}catch(Throwable t){
throw Lombok.sneakyThrow(t);
}
}
}
# 例如
public class Synchronized {
private final Object readLock = new Object();
@Synchronized
public static void hello() {
System.out.println("world");
}
@Synchronized
public int answerToLife() {
return 42;
}
@Synchronized("readLock")
public void foo() {
System.out.println("bar");
}
}
# 等同于
public class Synchronized {
private static final Object $LOCK = new Object[0];
private final Object $lock = new Object[0];
private final Object readLock = new Object();
public static void hello() {
synchronized($LOCK) {
System.out.println("world");
}
}
public int answerToLife() {
synchronized($lock) {
return 42;
}
}
public void foo() {
synchronized(readLock) {
System.out.println("bar");
}
}
}
依赖 + 插件 + 注解 + log.info()
@Data
@EqualsAndHashCode(callSuper = false)
@Accessors(chain = true)
@ApiModel(value="TestInfo对象", description="实体类详情") // knife4j注解
@TableName("test_info")
public class TestInfo implements Serializable {
private static final long serialVersionUID = 1l;
@TableId(value = "id", type = IdType.ASSIGN_UUID) // 自动生成不含中划线的 UUID 作为主键
private String id;
@TableField(fill = FieldFill.INSERT) // MyBatis-Plus设置自动填充时间
private Date created;
@TableField(fill = FieldFill.INSERT_UPDATE) // 自动更新时间
private Date updated;
@TableField(value="deleted")
private Integer deleted;
@ApiModelProperty(value = "test_id") // knife4j注解
@TableField(value="test_id")
private String testId;
}
@GetMapping(value = "/getAll")
@ApiOperation(value="接口标题")
@ApiImplicitParams({
@ApiImplicitParam(name="testDTO",value="测试dto",dataType = "TestDTO",required = true),
})
@ApiResponses({
@ApiResponse(code = 200, message = "ok", response = TestInfo.class)
})
public JSONResult getAll(TestDTO testDTO){
IPage<TestInfo> all = testInfoService.getAll(testDTO);
return new JSONResult(all);
}
public class User implements Serializable {
@TableId(value = "id", type = IdType.AUTO)
private Integer id;
private String username;
private String password;
private Date birthday;
}
ASSIGN_ID(雪花算法)
ASSIGN_UUID(排除中划线的UUID)
AUTO(数据库ID自增)
INPUT(插入前自行设置主键值)
NONE(无状态)