What kind of leather does Lombok have? Springboot and idea should support it!

macrozheng 2021-01-05 17:11:54
kind leather lombok springboot idea


lately IDEA 2020 The last version was released , It's already built in Lombok plug-in unit ,SpringBoot 2.1.x Later versions are also available Starter Built in Lombok rely on . Why do they all support Lombok Well ? Today I'm going to talk about Lombok Use , See what's magical about it !

SpringBoot Actual e-commerce projects mall(40k+star) Address :https://github.com/macrozheng/mall

Lombok brief introduction

Lombok Is a Java Code enhancement Library , stay Github Previous 9.8k+Star. It will be automatically integrated into your editor and build tool , So that your Java The code is more vivid and interesting . adopt Lombok Annotations , You don't have to write getter、setter、equals Other methods ,Lombok Will be generated automatically for you at compile time .

Lombok Integrate

First of all we need to IDEA Installed in the Lombok plug-in unit , If you're using the latest version IDEA 2020.3, be Lombok The plug-in is built in , No installation required .

And then in the project pom.xml Add... To the file Lombok rely on ,SpringBoot 2.1.x There is no need to specify Lombok edition ,SpringBoot stay spring-boot-dependencies Built in .

<!--lombok rely on -->
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<optional>true</optional>
</dependency>

Lombok Use

Lombok There's a lot of notes in , These annotations make it easier to write Java Code , Here's how to use these annotations .

val

Use val Annotations can replace any type as a local variable , So we don't have to write complicated ArrayList and Map.Entry Type , Specific examples are as follows .

/**
* Created by macro on 2020/12/16.
*/
public class ValExample {
public static void example() {
//val Instead of ArrayList<String> and String type
val example = new ArrayList<String>();
example.add("Hello World!");
val foo = example.get(0);
System.out.println(foo.toLowerCase());
}
public static void example2() {
//val Instead of Map.Entry<Integer,String> type
val map = new HashMap<Integer, String>();
map.put(0, "zero");
map.put(5, "five");
for (val entry : map.entrySet()) {
System.out.printf("%d: %s\n", entry.getKey(), entry.getValue());
}
}
public static void main(String[] args) {
example();
example2();
}
}

When we use it val After the note ,Lombok The specific type is inferred from the initialization expression of the local variable , After compilation, the following code will be generated .

public class ValExample {
public ValExample() {
}
public static void example() {
ArrayList<String> example = new ArrayList();
example.add("Hello World!");
String foo = (String)example.get(0);
System.out.println(foo.toLowerCase());
}
public static void example2() {
HashMap<Integer, String> map = new HashMap();
map.put(0, "zero");
map.put(5, "five");
Iterator var1 = map.entrySet().iterator();
while(var1.hasNext()) {
Entry<Integer, String> entry = (Entry)var1.next();
System.out.printf("%d: %s\n", entry.getKey(), entry.getValue());
}
}
}

@NonNull

Use... In method @NonNull Annotations can make non null judgments , If a null value is passed in, it will be thrown directly NullPointerException.

/**
* Created by macro on 2020/12/16.
*/
public class NonNullExample {
private String name;
public NonNullExample(@NonNull String name){
this.name = name;
}
public static void main(String[] args) {
new NonNullExample("test");
// Will throw out NullPointerException
new NonNullExample(null);
}
}

After compilation, a non null judgment is added to the constructor , The specific code is as follows .

public class NonNullExample {
private String name;
public NonNullExample(@NonNull String name) {
if (name == null) {
throw new NullPointerException("name is marked non-null but is null");
} else {
this.name = name;
}
}
public static void main(String[] args) {
new NonNullExample("test");
new NonNullExample((String)null);
}
}

@Cleanup

When we're in Java When using resources in , Inevitably, resources need to be shut down after use . Use @Cleanup Annotations can automatically close resources .

/**
* Created by macro on 2020/12/16.
*/
public class CleanupExample {
public static void main(String[] args) throws IOException {
String inStr = "Hello World!";
// Use input and output streams to automatically close , No need to write try catch And call close() Method
@Cleanup ByteArrayInputStream in = new ByteArrayInputStream(inStr.getBytes("UTF-8"));
@Cleanup ByteArrayOutputStream out = new ByteArrayOutputStream();
byte[] b = new byte[1024];
while (true) {
int r = in.read(b);
if (r == -1) break;
out.write(b, 0, r);
}
String outStr = out.toString("UTF-8");
System.out.println(outStr);
}
}

After compiling Lombok The following code will be generated .

public class CleanupExample {
public CleanupExample() {
}
public static void main(String[] args) throws IOException {
String inStr = "Hello World!";
ByteArrayInputStream in = new ByteArrayInputStream(inStr.getBytes("UTF-8"));
try {
ByteArrayOutputStream out = new ByteArrayOutputStream();
try {
byte[] b = new byte[1024];
while(true) {
int r = in.read(b);
if (r == -1) {
String outStr = out.toString("UTF-8");
System.out.println(outStr);
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();
}
}
}
}

@Getter/@Setter

With @Getter/@Setter annotation , We no longer have to write getter/setter The method . Just imagine before even if we used IDEA Automatic generation getter/setter Method , If the type and name of a class property change , It's going to regenerate getter/setter The method is also a very troublesome thing .

/**
* Created by macro on 2020/12/17.
*/
public class GetterSetterExample {
@Getter
@Setter
private String name;
@Getter
@Setter(AccessLevel.PROTECTED)
private Integer age;
public static void main(String[] args) {
GetterSetterExample example = new GetterSetterExample();
example.setName("test");
example.setAge(20);
System.out.printf("name:%s age:%d",example.getName(),example.getAge());
}
}

After compiling Lombok The following code will be generated .

public class GetterSetterExample {
private String name;
private Integer age;
public GetterSetterExample() {
}
public String getName() {
return this.name;
}
public void setName(final String name) {
this.name = name;
}
public Integer getAge() {
return this.age;
}
protected void setAge(final Integer age) {
this.age = age;
}
}

@ToString

Write all class properties to toString Method is convenient to print log , What a boring thing it is . Use @ToString Annotations can be generated automatically toString Method , All class properties are included by default , Use @ToString.Exclude Annotations can exclude the generation of attributes .

/**
* Created by macro on 2020/12/17.
*/
@ToString
public class ToStringExample {
@ToString.Exclude
private Long id;
private String name;
private Integer age;
public ToStringExample(Long id,String name,Integer age){
this.id =id;
this.name = name;
this.age = age;
}
public static void main(String[] args) {
ToStringExample example = new ToStringExample(1L,"test",20);
// automatically toString Method , Output ToStringExample(name=test, age=20)
System.out.println(example);
}
}

After compiling Lombok The following code will be generated .

public class ToStringExample {
private Long id;
private String name;
private Integer age;
public ToStringExample(Long id, String name, Integer age) {
this.id = id;
this.name = name;
this.age = age;
}
public String toString() {
return "ToStringExample(name=" + this.name + ", age=" + this.age + ")";
}
}

@EqualsAndHashCode

Use @EqualsAndHashCode Annotations can be generated automatically hashCode and equals Method , All class properties are included by default , Use @EqualsAndHashCode.Exclude You can exclude the generation of attributes .

/**
* Created by macro on 2020/12/17.
*/
@Getter
@Setter
@EqualsAndHashCode
public class EqualsAndHashCodeExample {
private Long id;
@EqualsAndHashCode.Exclude
private String name;
@EqualsAndHashCode.Exclude
private Integer age;
public static void main(String[] args) {
EqualsAndHashCodeExample example1 = new EqualsAndHashCodeExample();
example1.setId(1L);
example1.setName("test");
example1.setAge(20);
EqualsAndHashCodeExample example2 = new EqualsAndHashCodeExample();
example2.setId(1L);
//equals Methods only compare id, return true
System.out.println(example1.equals(example2));
}
}

After compiling Lombok The following code will be generated .

public class EqualsAndHashCodeExample {
private Long id;
private String name;
private Integer age;
public EqualsAndHashCodeExample() {
}
public boolean equals(final Object o) {
if (o == this) {
return true;
} else if (!(o instanceof EqualsAndHashCodeExample)) {
return false;
} else {
EqualsAndHashCodeExample other = (EqualsAndHashCodeExample)o;
if (!other.canEqual(this)) {
return false;
} else {
Object this$id = this.getId();
Object other$id = other.getId();
if (this$id == null) {
if (other$id != null) {
return false;
}
} else if (!this$id.equals(other$id)) {
return false;
}
return true;
}
}
}
protected boolean canEqual(final Object other) {
return other instanceof EqualsAndHashCodeExample;
}
public int hashCode() {
int PRIME = true;
int result = 1;
Object $id = this.getId();
int result = result * 59 + ($id == null ? 43 : $id.hashCode());
return result;
}
}

@XxConstructor

Use @XxConstructor Annotations can automatically generate construction methods , Yes @NoArgsConstructor、@RequiredArgsConstructor and @AllArgsConstructor Three annotations can be used .

  • @NoArgsConstructor: Generate parameterless constructor .
  • @RequiredArgsConstructor: Generate a constructor that contains the required parameters , Use @NonNull The class property of the annotation is a required parameter .
  • @AllArgsConstructor: Generate a constructor with all the parameters .
/**
* Created by macro on 2020/12/17.
*/
@NoArgsConstructor
@RequiredArgsConstructor(staticName = "of")
@AllArgsConstructor
public class ConstructorExample {
@NonNull
private Long id;
private String name;
private Integer age;
public static void main(String[] args) {
// Parameterless constructors
ConstructorExample example1 = new ConstructorExample();
// All parameter constructors
ConstructorExample example2 = new ConstructorExample(1L,"test",20);
//@NonNull Annotation must be a parameter constructor
ConstructorExample example3 = ConstructorExample.of(1L);
}
}

After compiling Lombok The following code will be generated .

public class ConstructorExample {
@NonNull
private Long id;
private String name;
private Integer age;
public ConstructorExample() {
}
private ConstructorExample(@NonNull final Long id) {
if (id == null) {
throw new NullPointerException("id is marked non-null but is null");
} else {
this.id = id;
}
}
public static ConstructorExample of(@NonNull final Long id) {
return new ConstructorExample(id);
}
public ConstructorExample(@NonNull final Long id, final String name, final Integer age) {
if (id == null) {
throw new NullPointerException("id is marked non-null but is null");
} else {
this.id = id;
this.name = name;
this.age = age;
}
}
}

@Data

@Data It's a handy combination annotation , yes @ToString、@EqualsAndHashCode、@Getter、@Setter and @RequiredArgsConstructor The combination of .

/**
* Created by macro on 2020/12/17.
*/
@Data
public class DataExample {
@NonNull
private Long id;
@EqualsAndHashCode.Exclude
private String name;
@EqualsAndHashCode.Exclude
private Integer age;
public static void main(String[] args) {
//@RequiredArgsConstructor In force
DataExample example1 = new DataExample(1L);
//@Getter @Setter In force
example1.setName("test");
example1.setAge(20);
//@ToString In force
System.out.println(example1);
DataExample example2 = new DataExample(1L);
//@EqualsAndHashCode In force
System.out.println(example1.equals(example2));
}
}

After compiling Lombok The following code will be generated .

public class DataExample {
@NonNull
private Long id;
private String name;
private Integer age;
public DataExample(@NonNull final Long id) {
if (id == null) {
throw new NullPointerException("id is marked non-null but is null");
} else {
this.id = id;
}
}
@NonNull
public Long getId() {
return this.id;
}
public String getName() {
return this.name;
}
public Integer getAge() {
return this.age;
}
public void setId(@NonNull final Long id) {
if (id == null) {
throw new NullPointerException("id is marked non-null but is null");
} else {
this.id = id;
}
}
public void setName(final String name) {
this.name = name;
}
public void setAge(final Integer age) {
this.age = age;
}
public boolean equals(final Object o) {
if (o == this) {
return true;
} else if (!(o instanceof DataExample)) {
return false;
} else {
DataExample other = (DataExample)o;
if (!other.canEqual(this)) {
return false;
} else {
Object this$id = this.getId();
Object other$id = other.getId();
if (this$id == null) {
if (other$id != null) {
return false;
}
} else if (!this$id.equals(other$id)) {
return false;
}
return true;
}
}
}
protected boolean canEqual(final Object other) {
return other instanceof DataExample;
}
public int hashCode() {
int PRIME = true;
int result = 1;
Object $id = this.getId();
int result = result * 59 + ($id == null ? 43 : $id.hashCode());
return result;
}
public String toString() {
return "DataExample(id=" + this.getId() + ", name=" + this.getName() + ", age=" + this.getAge() + ")";
}
}

@Value

Use @Value Annotations can declare classes immutable , After the declaration, this kind of work is equivalent to final class , Cannot be inherited , Its attribute will also become final attribute .

/**
* Created by macro on 2020/12/17.
*/
@Value
public class ValueExample {
private Long id;
private String name;
private Integer age;
public static void main(String[] args) {
// Only full parameter constructors can be used
ValueExample example = new ValueExample(1L,"test",20);
// example.setName("andy") // No generation setter Method , Will report a mistake
// example.name="andy" // Field is set to final type , Will report a mistake
}
}

After compiling Lombok The following code will be generated .

public final class ValueExample {
private final Long id;
private final String name;
private final Integer age;
public static void main(String[] args) {
new ValueExample(1L, "test", 20);
}
public ValueExample(final Long id, final String name, final Integer age) {
this.id = id;
this.name = name;
this.age = age;
}
public Long getId() {
return this.id;
}
public String getName() {
return this.name;
}
public Integer getAge() {
return this.age;
}
}

@Builder

Use @Builder Annotations can create objects through builder mode , Builder mode plus chain call , It's so convenient to create objects !

/**
* Created by macro on 2020/12/17.
*/
@Builder
@ToString
public class BuilderExample {
private Long id;
private String name;
private Integer age;
public static void main(String[] args) {
BuilderExample example = BuilderExample.builder()
.id(1L)
.name("test")
.age(20)
.build();
System.out.println(example);
}
}

After compiling Lombok The following code will be generated .

public class BuilderExample {
private Long id;
private String name;
private Integer age;
BuilderExample(final Long id, final String name, final Integer age) {
this.id = id;
this.name = name;
this.age = age;
}
public static BuilderExample.BuilderExampleBuilder builder() {
return new BuilderExample.BuilderExampleBuilder();
}
public String toString() {
return "BuilderExample(id=" + this.id + ", name=" + this.name + ", age=" + this.age + ")";
}
public static class BuilderExampleBuilder {
private Long id;
private String name;
private Integer age;
BuilderExampleBuilder() {
}
public BuilderExample.BuilderExampleBuilder id(final Long id) {
this.id = id;
return this;
}
public BuilderExample.BuilderExampleBuilder name(final String name) {
this.name = name;
return this;
}
public BuilderExample.BuilderExampleBuilder age(final Integer age) {
this.age = age;
return this;
}
public BuilderExample build() {
return new BuilderExample(this.id, this.name, this.age);
}
public String toString() {
return "BuilderExample.BuilderExampleBuilder(id=" + this.id + ", name=" + this.name + ", age=" + this.age + ")";
}
}
}

@SneakyThrows

Also manually catching and throwing exceptions ? Use @SneakyThrows Try to implement annotation automatically !

/**
* Created by macro on 2020/12/17.
*/
public class SneakyThrowsExample {
// Automatically throw an exception , No need to deal with
@SneakyThrows(UnsupportedEncodingException.class)
public static byte[] str2byte(String str){
return str.getBytes("UTF-8");
}
public static void main(String[] args) {
String str = "Hello World!";
System.out.println(str2byte(str).length);
}
}

After compiling Lombok The following code will be generated .

public class SneakyThrowsExample {
public SneakyThrowsExample() {
}
public static byte[] str2byte(String str) {
try {
return str.getBytes("UTF-8");
} catch (UnsupportedEncodingException var2) {
throw var2;
}
}
}

@Synchronized

When we access the same resource in multiple threads , There are always thread safety issues , We used to use synchronized Keyword modification method to achieve synchronous access . Use @Synchronized Annotations can also achieve synchronous access .

package com.macro.mall.tiny.example;
import lombok.*;
/**
* Created by macro on 2020/12/17.
*/
@Data
public class SynchronizedExample {
@NonNull
private Integer count;
@Synchronized
@SneakyThrows
public void reduceCount(Integer id) {
if (count > 0) {
Thread.sleep(500);
count--;
System.out.println(String.format("thread-%d count:%d", id, count));
}
}
public static void main(String[] args) {
// add to @Synchronized Three threads can simultaneously call reduceCount Method
SynchronizedExample example = new SynchronizedExample(20);
new ReduceThread(1, example).start();
new ReduceThread(2, example).start();
new ReduceThread(3, example).start();
}
@RequiredArgsConstructor
static class ReduceThread extends Thread {
@NonNull
private Integer id;
@NonNull
private SynchronizedExample example;
@Override
public void run() {
while (example.getCount() > 0) {
example.reduceCount(id);
}
}
}
}

After compiling Lombok The following code will be generated .

public class SynchronizedExample {
private final Object $lock = new Object[0];
@NonNull
private Integer count;
public void reduceCount(Integer id) {
try {
synchronized(this.$lock) {
if (this.count > 0) {
Thread.sleep(500L);
Integer var3 = this.count;
Integer var4 = this.count = this.count - 1;
System.out.println(String.format("thread-%d count:%d", id, this.count));
}
}
} catch (Throwable var7) {
throw var7;
}
}
}

@With

Use @With Annotation can clone the original object , And change one of its attributes , When using, you need to specify the full parameter construction method .

@With
@AllArgsConstructor
public class WithExample {
private Long id;
private String name;
private Integer age;
public static void main(String[] args) {
WithExample example1 = new WithExample(1L, "test", 20);
WithExample example2 = example1.withAge(22);
// Make the original object clone And set up age, return false
System.out.println(example1.equals(example2));
}
}

After compiling Lombok The following code will be generated .

public class WithExample {
private Long id;
private String name;
private Integer age;
public WithExample withId(final Long id) {
return this.id == id ? this : new WithExample(id, this.name, this.age);
}
public WithExample withName(final String name) {
return this.name == name ? this : new WithExample(this.id, name, this.age);
}
public WithExample withAge(final Integer age) {
return this.age == age ? this : new WithExample(this.id, this.name, age);
}
public WithExample(final Long id, final String name, final Integer age) {
this.id = id;
this.name = name;
this.age = age;
}
}

@Getter(lazy=true)

When we get an attribute to compare resource consumption , You can give @Getter add to lazy=true Property to achieve lazy loading , Will generate Double Check Lock Template code loads properties lazily .

/**
* Created by macro on 2020/12/17.
*/
public class GetterLazyExample {
@Getter(lazy = true)
private 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;
}
public static void main(String[] args) {
// Use Double Check Lock Template code loads properties lazily
GetterLazyExample example = new GetterLazyExample();
System.out.println(example.getCached().length);
}
}

After compiling Lombok The following code will be generated .

public class GetterLazyExample {
private final AtomicReference<Object> cached = new AtomicReference();
public GetterLazyExample() {
}
private double[] expensive() {
double[] result = new double[1000000];
for(int i = 0; i < result.length; ++i) {
result[i] = Math.asin((double)i);
}
return result;
}
public double[] getCached() {
Object value = this.cached.get();
if (value == null) {
synchronized(this.cached) {
value = this.cached.get();
if (value == null) {
double[] actualValue = this.expensive();
value = actualValue == null ? this.cached : actualValue;
this.cached.set(value);
}
}
}
return (double[])((double[])(value == this.cached ? null : value));
}
}

@Log

Use @Log annotation , Log objects can be generated directly log, adopt log Object can print the log directly .

/**
* Created by macro on 2020/12/17.
*/
@Log
public class LogExample {
public static void main(String[] args) {
log.info("level info");
log.warning("level warning");
log.severe("level severe");
}
}

After compiling Lombok The following code will be generated .

public class LogExample {
private static final Logger log = Logger.getLogger(LogExample.class.getName());
public LogExample() {
}
public static void main(String[] args) {
log.info("level info");
log.warning("level warning");
log.severe("level severe");
}
}

@Slf4j

Use Lombok Error generating log object , According to the use of different logs , There are a variety of annotations available . such as @Log、@Log4j、@Log4j2、@Slf4j etc. .

/**
* Created by macro on 2020/12/17.
*/
@Slf4j
public class LogSlf4jExample {
public static void main(String[] args) {
log.info("level:{}","info");
log.warn("level:{}","warn");
log.error("level:{}", "error");
}
}

After compiling Lombok The following code will be generated .

public class LogSlf4jExample {
private static final Logger log = LoggerFactory.getLogger(LogSlf4jExample.class);
public LogSlf4jExample() {
}
public static void main(String[] args) {
log.info("level:{}", "info");
log.warn("level:{}", "warn");
log.error("level:{}", "error");
}
}

Lombok principle

If IDEA Not to install Lombok Plug in , Let's open it and use it Lombok The project for cannot be compiled . After installation IDEA It will remind us Lombok Methods and properties generated for us .

Used @Data After annotation , Looking at the class structure, you can see that getter、setter、toString Other methods .

open target In the catalog .class file , We can see Lombok Code generated for us , so Lombok By parsing annotations , Then generate code at compile time to implement Java Code enhanced .

Reference material

Official documents :https://projectlombok.org/fea...

Project source address

https://github.com/macrozheng...

this paper GitHub https://github.com/macrozheng/mall-learning Included , Welcome to Star!
版权声明
本文为[macrozheng]所创,转载请带上原文链接,感谢
https://javamana.com/2020/12/20201231092258179D.html

  1. 【计算机网络 12(1),尚学堂马士兵Java视频教程
  2. 【程序猿历程,史上最全的Java面试题集锦在这里
  3. 【程序猿历程(1),Javaweb视频教程百度云
  4. Notes on MySQL 45 lectures (1-7)
  5. [computer network 12 (1), Shang Xuetang Ma soldier java video tutorial
  6. The most complete collection of Java interview questions in history is here
  7. [process of program ape (1), JavaWeb video tutorial, baidu cloud
  8. Notes on MySQL 45 lectures (1-7)
  9. 精进 Spring Boot 03:Spring Boot 的配置文件和配置管理,以及用三种方式读取配置文件
  10. Refined spring boot 03: spring boot configuration files and configuration management, and reading configuration files in three ways
  11. 精进 Spring Boot 03:Spring Boot 的配置文件和配置管理,以及用三种方式读取配置文件
  12. Refined spring boot 03: spring boot configuration files and configuration management, and reading configuration files in three ways
  13. 【递归,Java传智播客笔记
  14. [recursion, Java intelligence podcast notes
  15. [adhere to painting for 386 days] the beginning of spring of 24 solar terms
  16. K8S系列第八篇(Service、EndPoints以及高可用kubeadm部署)
  17. K8s Series Part 8 (service, endpoints and high availability kubeadm deployment)
  18. 【重识 HTML (3),350道Java面试真题分享
  19. 【重识 HTML (2),Java并发编程必会的多线程你竟然还不会
  20. 【重识 HTML (1),二本Java小菜鸟4面字节跳动被秒成渣渣
  21. [re recognize HTML (3) and share 350 real Java interview questions
  22. [re recognize HTML (2). Multithreading is a must for Java Concurrent Programming. How dare you not
  23. [re recognize HTML (1), two Java rookies' 4-sided bytes beat and become slag in seconds
  24. 造轮子系列之RPC 1:如何从零开始开发RPC框架
  25. RPC 1: how to develop RPC framework from scratch
  26. 造轮子系列之RPC 1:如何从零开始开发RPC框架
  27. RPC 1: how to develop RPC framework from scratch
  28. 一次性捋清楚吧,对乱糟糟的,Spring事务扩展机制
  29. 一文彻底弄懂如何选择抽象类还是接口,连续四年百度Java岗必问面试题
  30. Redis常用命令
  31. 一双拖鞋引发的血案,狂神说Java系列笔记
  32. 一、mysql基础安装
  33. 一位程序员的独白:尽管我一生坎坷,Java框架面试基础
  34. Clear it all at once. For the messy, spring transaction extension mechanism
  35. A thorough understanding of how to choose abstract classes or interfaces, baidu Java post must ask interview questions for four consecutive years
  36. Redis common commands
  37. A pair of slippers triggered the murder, crazy God said java series notes
  38. 1、 MySQL basic installation
  39. Monologue of a programmer: despite my ups and downs in my life, Java framework is the foundation of interview
  40. 【大厂面试】三面三问Spring循环依赖,请一定要把这篇看完(建议收藏)
  41. 一线互联网企业中,springboot入门项目
  42. 一篇文带你入门SSM框架Spring开发,帮你快速拿Offer
  43. 【面试资料】Java全集、微服务、大数据、数据结构与算法、机器学习知识最全总结,283页pdf
  44. 【leetcode刷题】24.数组中重复的数字——Java版
  45. 【leetcode刷题】23.对称二叉树——Java版
  46. 【leetcode刷题】22.二叉树的中序遍历——Java版
  47. 【leetcode刷题】21.三数之和——Java版
  48. 【leetcode刷题】20.最长回文子串——Java版
  49. 【leetcode刷题】19.回文链表——Java版
  50. 【leetcode刷题】18.反转链表——Java版
  51. 【leetcode刷题】17.相交链表——Java&python版
  52. 【leetcode刷题】16.环形链表——Java版
  53. 【leetcode刷题】15.汉明距离——Java版
  54. 【leetcode刷题】14.找到所有数组中消失的数字——Java版
  55. 【leetcode刷题】13.比特位计数——Java版
  56. oracle控制用户权限命令
  57. 三年Java开发,继阿里,鲁班二期Java架构师
  58. Oracle必须要启动的服务
  59. 万字长文!深入剖析HashMap,Java基础笔试题大全带答案
  60. 一问Kafka就心慌?我却凭着这份,图灵学院vip课程百度云