lombok使用详解

官网地址: https://www.projectlombok.org/

  Project Lombok是一个java库,它可以自动插入到编辑器中,并构建工具,使java更加丰富。再也不要写另一个getter或equals方法了。尽早访问未来的java特性,比如val,等等。

  不仅仅只有get/set/tostring方法的自动生成哦,还有exception/log/资源自动释放(如文件流的输入输出,数据库驱动的关闭等)。而且万一有一天不想用lombok的话也是很方便的,官网有提供和delombok可以使用。官方原文翻译如下:Delombok将您的源文件复制到另一个目录,用它们的desugared形式替换所有lombok注释。它会将@Getter返回到实际的getter中。然后删除注释。这在各种原因中都很有用;如果您想停止使用lombok,您可以很容易地在源代码中删除所有的跟踪,您可以使用delombok对源文件进行预处理,比如javadoc和GWT。有关如何运行delombok的更多信息,包括构建工具的说明。

一些常用的注解:(官网有很详尽的demo)

@Setter/.@Getter/@ToString

import lombok.AccessLevel;
import lombok.Getter;
import lombok.Setter;

public class GetterSetterExample {
  /**
   * Age of the person. Water is wet.
   
   @param age New value for this person's age. Sky is blue.
   @return The current value of this person's age. Circles are round.
   */
  @Getter @Setter private int age = 10;
  
  /**
   * Name of the person.
   * -- SETTER --
   * Changes the name of this person.
   
   @param name The new value.
   */
  @Setter(AccessLevel.PROTECTEDprivate String name;
  
  @Override public String toString() {
    return String.format("%s (age: %d)", name, age);
  }
}

import lombok.ToString;

@ToString(exclude="id")
public class ToStringExample {
  private static final int STATIC_VAR = 10;
  private String name;
  private Shape shape = new Square(510);
  private String[] tags;
  private int id;
  
  public String getName() {
    return this.name;
  }
  
  @ToString(callSuper=true, includeFieldNames=true)
  public static class Square extends Shape {
    private final int width, height;
    
    public Square(int width, int height) {
      this.width = width;
      this.height = height;
    }
  }
}

@Log:您将@Log的变体放到了您的类上(无论哪种类型应用于您所使用的日志系统);然后,您有一个静态的最终日志字段,初始化为类的名称,然后您可以使用它来编写日志语句。

传统的写法:

public class LogExampleOther {
  private static final org.slf4j.Logger log = org.slf4j.LoggerFactory.getLogger(LogExampleOther.class);
  
  public static void main(String... args) {
    log.error("Something else is wrong here");
  }
}

lombok的写法不需要创建Log对象,只需要加上注解就可以随意用日志的各种方法。

有几种选择:

@CommonsLogCreates  private static final org.apache.commons.logging.Log log = org.apache.commons.logging.LogFactory.getLog(LogExample.class); @JBossLogCreates  private static final org.jboss.logging.Logger log = org.jboss.logging.Logger.getLogger(LogExample.class); @LogCreates  private static final java.util.logging.Logger log = java.util.logging.Logger.getLogger(LogExample.class.getName()); @Log4jCreates  private static final org.apache.log4j.Logger log = org.apache.log4j.Logger.getLogger(LogExample.class); @Log4j2Creates  private static final org.apache.logging.log4j.Logger log = org.apache.logging.log4j.LogManager.getLogger(LogExample.class); @Slf4jCreates  private static final org.slf4j.Logger log = org.slf4j.LoggerFactory.getLogger(LogExample.class); @XSlf4j

Creates private static final org.slf4j.ext.XLogger log = org.slf4j.ext.XLoggerFactory.getXLogger(LogExample.class);

import lombok.extern.java.Log;
import lombok.extern.slf4j.Slf4j;

@Log
public class LogExample {
  
  public static void main(String... args) {
    log.error("Something's wrong here");
  }
}

@Slf4j
public class LogExampleOther {
  
  public static void main(String... args) {
    log.error("Something else is wrong here");
  }
}

@CommonsLog(topic="CounterLog")
public class LogExampleCategory {

  public static void main(String... args) {
    log.error("Calling the 'CounterLog' with a message");
  }
}

val/var:类似于将java变量的定义变成js这种不严谨的变量声明方式。:var与val完全相同,除了局部变量没有被标记为final。

val: 您可以使用val作为局部变量声明的类型,而不是实际编写类型。当您这样做时,类型将从初始化器表达式推断出来。本地变量也将是最终的。这个特性只对局部变量有效,对每个循环都是这样,而不是在字段上。需要初始化器表达式。

var:  该类型仍然完全来自于强制初始化表达式,以及任何其他的赋值,而现在是合法的(因为变量不再是final),因此没有考虑确定合适的类型。例如,var x = "Hello";x = Color.RED;不工作;x的类型将被推断为java.lang。因此,x =颜色。红色的任务将会失败。如果x的类型被推断为java.lang。这个代码会编译,但这不是howvar作品。

@NonNull

如果(param == null)抛出新的NullPointerException(“param”);并将插入到您的方法的最顶端。对于构造函数,将在任何显式的this()或super()调用之后立即插入null检查。

@Cleanup: 普遍的写法一般是加上try-catch-finally来关闭输入输出流,但这里简单的几行代码就可以了(源码来自官网)。

import lombok.Cleanup;
import java.io.*;

public class CleanupExample {
  public static void main(String[] argsthrows IOException {
    @Cleanup InputStream in = new FileInputStream(args[0]);
    @Cleanup OutputStream out = new FileOutputStream(args[1]);
    byte[] b = new byte[10000];
    while (true) {
      int r = in.read(b);
      if (r == -1break;
      out.write(b, 0, r);
    }
  }
}

@EqualsAndHashCode

import lombok.EqualsAndHashCode;

@EqualsAndHashCode(exclude={"id""shape"})
public class EqualsAndHashCodeExample {
  private transient int transientVar = 10;
  private String name;
  private double score;
  private Shape shape = new Square(510);
  private String[] tags;
  private int id;
  
  public String getName() {
    return this.name;
  }
  
  @EqualsAndHashCode(callSuper=true)
  public static class Square extends Shape {
    private final int width, height;
    
    public Square(int width, int height) {
      this.width = width;
      this.height = height;
    }
  }
}

@NoArgsConstructor, @RequiredArgsConstructor and @AllArgsConstructor:构造器注解

@Data:@ data是一种方便快捷注释,包@ToString的特点,@EqualsAndHashCode,@ getter / @ setter和@RequiredArgsConstructor:换句话说,@ data生成的所有样板通常是与简单的pojo(传统的普通Java对象)和bean:getter的所有字段,setter不是final字段,和适当的toString,equals和hashCode实现涉及类的字段,和一个构造函数,初始化所有final字段,以及所有不是final字段没有初始化已标有@NonNull,订货单
@Value:和@data一样都是放在类前面的。是@Data的不可变变量;所有字段在默认情况下都是私有的和最终的,而setter不是生成的。类本身也在默认情况下进行了final,因为不变性并不是一种可以强制转换到子类的东西。与@Data一样,也生成了有用的toString()、equals()和hashCode()方法,每个字段都有一个getter方法,以及一个包含所有参数(字段声明中初始化的final字段除外)的构造函数。
@Builder: 
@Builder允许您自动生成所需的代码,以使您的类具有可实例化的代码。可以放在类,构造方法和方法上。

import lombok.Builder;
import lombok.Singular;
import java.util.Set;

@Builder
public class BuilderExample {
  @Builder.Default private long created = System.currentTimeMillis();
  private String name;
  private int age;
  @Singular private Set<String> occupations;
}

@ sneakythrow:可以用来偷偷地抛出检查过的异常,而不必在方法的throw子句中声明它。当然,这种有争议的能力应该被谨慎使用。lombok生成的代码不会忽略、

包装、替换或修改被抛出的检查异常;它只是伪造了编译器。在JVM(类文件)级别上,不管是否选中了所有异常,都可以抛出,而不管您的方法的抛出子句是什么,这

就是它的工作原理。

import lombok.SneakyThrows;

public class SneakyThrowsExample implements Runnable {
  @SneakyThrows(UnsupportedEncodingException.class)
  public String utf8ToString(byte[] bytes) {
    return new String(bytes, "UTF-8");
  }
  
  @SneakyThrows
  public void run() {
    throw new Throwable();
  }
}
@Synchronized是同步方法修饰符的一个更安全的变体。与synchronized一样,注释也只能在静态和实例方法上使用。它的操作类似于synchronized关键字,但它锁定不

同的对象。关键字锁定了这个,但是在一个名为$lock的字段上的注释锁是私有的。


@Getter(lazy=true):您可以让lombok生成一个getter,该getter将计算一次值,第一次调用这个getter,然后将其缓存。如果计算值

需要大量CPU,或者值占用大量内存,那么这将非常有用。要使用这个特性,创建一个私有的最终变量,使用代价高昂的表达式初始

化它,并使用@Getter(lazy=true)注释您的字段。该字段将被隐藏在您的代码的其余部分中,并且表达式将在第一次调用getter时被计

算一次。没有什么神奇的标记值(即使结果是o)。

mport lombok.Getter;

public class GetterLazyExample {
  @Getter(lazy=trueprivate final double[] cached = expensive();
  
  private double[] expensive() {
    double[] result = new double[1000000];
    for (int i = 0; i < result.length; i++) {
      result[i= Math.asin(i);
    }
    return result;
  }
}

mport lombok.Getter;

public class GetterLazyExample {
  @Getter(lazy=trueprivate final double[] cached = expensive();
  
  private double[] expensive() {
    double[] result = new double[1000000];
    for (int i = 0; i < result.length; i++) {
      result[i= Math.asin(i);
    }
    return result;
  }
}






猜你喜欢

转载自blog.csdn.net/ademoa/article/details/80043696