J2EE学习总结

简介: J2EE学习总结

1、Java数据结构Pair、MutablePair、ImmutablePair详解

Java组件类Pair、MutablePair、ImmutablePair详解

2、slf4j详解

slf4j使用教程以及常见问题解决(最新稳定版)

slf4j的使用

Slf4j与Log4j的区别


3、@JsonFormat、@JSONField、@DateTimeFormat区别

1. @JsonFormat和@JSONField是处理请求参数为json格式的时间

例如前端传送时间为“2020-08-12 23:28:00”,使用@JsonFormat(pattern = “yyyy-MM-dd HH:mm:ss”, timezone = “GMT+8”),这两者前面都带JSON,接收请求和返回数据格式为json时,注解生效


2. @DateTimeFormat也是处理时间格式,但它不支持反序列化,也就是不能转化前端数据格式为json。它能接收表单形式的时间格式,

3. 总结

前端读取数据库日期字段时使用 @JsonFormat和@JSONField 可以将时间戳转为格式化的日期数据。

前端使用JSON提交时用@JsonFormat和@JSONField

前端使用Form提交时用@DateTimeForma


4、Java中时间与时间戳的转换

  1. 时间转换成时间戳
    方式一:
/**
  * 时间转换成时间戳,参数和返回值都是字符串
  * @param  s
  * @return res
  * @throws ParseException
 */
public static String dateToStamp(String s) throws ParseException {
    String res;
    //设置时间模版
    SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
    Date date = simpleDateFormat.parse(s);
    long ts = date.getTime();
    res = String.valueOf(ts);
    return res;
}


在主函数中设置参数与运行结果

 String date=dateToStamp("2021-09-07 09:09:39");
 System.out.println(date);
//结果:1630976979000


方式二:

/**
  * 日期转换成时间戳,参数可以是日期,返回值是字符串
 */
public static void Date2TimeStamp() {
   SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
   String format = sdf.format(new Date());
   try {
       String valueOf = String.valueOf(sdf.parse(format).getTime() / 1000);
       System.err.println(valueOf);
   } catch (ParseException e) {
       e.printStackTrace();
   }
}
  1. 时间戳转换成时间
    方式一:
/**
  * 将时间戳转换为时间,参数和返回值都是字符串
  * @param s
  * @return res
 */
public static String stampToDate(String s){
    String res;
    SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
    long lt = new Long(s);
    Date date = new Date(lt);
    res = simpleDateFormat.format(date);
    return res;
    }


在主函数中设置参数与运行结果

 String s="1630339200000";
 String date=stampToDate(s);
 System.out.println(date);
 //2021-08-31 00:00:00


方式二:

/**
  * 时间戳先转换成日期字符串再转换成日期类型,参数是字符串,返回值是字符串也可是日期
 */
public static void TimeStamp2Date() {
   String timestampString = "1631008034";
   String formats = "yyyy-MM-dd HH:mm:ss";
   Long timestamp = Long.parseLong(timestampString) * 1000;
   //日期格式字符串
   String dateStr = new SimpleDateFormat(formats, Locale.CHINA).format(new Date(timestamp));
   System.err.println(dateStr);
   Date date = null;
   SimpleDateFormat formater = new SimpleDateFormat();
   formater.applyPattern("yyyy-MM-dd HH:mm:ss");
   try {
       date = formater.parse(dateStr);
       System.err.println(date);
   } catch (ParseException e) {
       e.printStackTrace();
   }
}


5、@SpringBootTest注解 --基于SpringBoot2.5.7版本

6、Java中自定义注解的用法

@Target、@Retention、@Documented、@Inherited注解都是作用在注解上的注解,java把他们亲切的叫做元注解,这四个注解正是Java的四大元注解。


1.@Target :用于描述注解的使用范围

2.@Retention:用于描述注解的生命周期【源代码阶段、CLASS文件中有效、运行时有效】

3.@Documented:表示该注解是否可以生成到 API文档中。注意:@Documented是一个标记注解,没有成员。

4.@Inherited:使用@Inherited定义的注解具备继承性 假设一个注解在定义时,使用了@Inherited,然后该注解在一个类上使用,如果这个类有子类,那么通过反射我们可以从类的子类上获取到同样的注解。


@Target注解

@Target注解算是比较常见的注解了,@Target注解用于描述注解的使用范围,优雅的说就是使用了@Target去定义一个注解,那么可以决定定义好的注解能用在什么地方。

为了显得身临其境的效果,我们可以先进@Autowired注解看看

@Target({ElementType.CONSTRUCTOR, ElementType.METHOD, ElementType.PARAMETER, ElementType.FIELD, ElementType.ANNOTATION_TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface Autowired {
    boolean required() default true;
}

我想各位都应该很清楚@Autowired注解的用法了,这个时候我们再来分析分析@Target注解的用法。


内部值:ElementType[] value()数组, value值类型 ElementType枚举类型,元注解中的枚举值决定了,一个注解可以标记的范围


TYPE : 类型上面 用于描述类、接口(包括注解类型) 或enum声明

FIELD: 用于描述字段

METHOD :方法

PARAMETER: 参数 【参数名】

CONSTRUCTOR : 构造方法

LOCAL_VARIABLE: 局部变量

ANNOTATION_TYPE : 可以打在注解上面

PACKAGE :可以打在包上面

TYPE_PARAMETER: 参数类型【形式参数类型】

TYPE_USE : 任何位置都可以


这时应该更能清晰的看出,@Autowired注解用于描述注解的使用范围了~

@Retention


@Retention也是开发中经常用到注解

public enum RetentionPolicy {
    SOURCE,
    CLASS,
    RUNTIME
}


@Retention:用于描述一个注解存在的生命周期,主要包括源码,字节码文件,运行时。


这3个生命周期分别对应于:Java源文件(.java文件) —> .class文件 —> 内存中的字节码。

1、RetentionPolicy.SOURCE:注解只保留在源文件,当Java文件编译成class文件的时候,注解被遗弃;

2、RetentionPolicy.CLASS:注解被保留到class文件,但jvm加载class文件时候被遗弃【默认】

3、RetentionPolicy.RUNTIME:注解不仅被保存到class文件中,jvm加载class文件之后,仍然存在;


@Document


@Document注解较少用,简单了解即可。

该注解主要判断是否可以生成到 API文档中 ==》即生成API文档的时 检验

@Inherited

这是一个稍微复杂的注解类型. 它指明被注解的类会自动继承. 更具体地说,如果定义注解时使用了 @Inherited 标记,然后用定义的注解来标注另一个父类, 父类又有一个子类(subclass),则父类的所有属性将被继承到它的子类中.


@Inherited表示一个【注解】能够被继承,不是说注解与注解之间能否相互继承,而是说:一个类A被注解了,那么另外一个类B,继承了A类B类能够继承到A类中,的注解 (即被@Inherited注解过的注解)

7、fastjson使用详解

参考

8、java 里面添加out:极客用法

参考

9、java 中 BigDecimal 详解

参考

设置保留两位小数,并向下取整

BigDecimal scale = new BigDecimal(totalScore).setScale(2, BigDecimal.ROUND_DOWN);
totalScore = scale.doubleValue();


10、Nginx 文件上传 413 错误解决方法

我们使用ngnix做web server的时候,nginx对上传文件的大小有限制,默认是1M。

当超过大小的时候会报413(too large)错误。这个时候我们找到nginx.conf配置文件下的location /{},在里面增加client_max_body_size 20M;

注意:20M设置为你需要的大小即可,但是如果客户端没有对上传文件的大小做限制,在上传文件的时候大于你设置的值,还是会报413错误导致你的客户端服务停掉,因此如果你不希望发生这样的事,将值改为0,即改为:

client_max_body_size 0; 即可。设置为0将禁用客户端请求主体大小的检查。

以下内容为官网原文:

更多配置见官网


句法: client_max_body_size size;
默认: client_max_body_size 1m;
内容: http,server,location

设置客户端请求正文的最大允许大小,在“ Content-Length”请求标头字段中指定。如果请求中的大小超过配置的值,则会向客户端返回413(请求实体太大)错误。请注意,浏览器无法正确显示此错误。设置size为0将禁用客户端请求主体大小的检查。


11、基础工具类Joiner的使用

Guava之Joiner笔记

Guava 中有一些基础的工具类,如下所列:


Joiner 类:根据给定的分隔符把字符串连接到一起。MapJoiner 执行相同的操作,但是针对 Map 的 key 和 value。


Splitter 类:与 Joiner 操作相反的类,是根据给定的分隔符,把一个字符串分隔成若个子字符串。


CharMatcher,Strings 类:对字符串通用的操作,例如移除字符串的某一部分,字符串匹配等等操作。


其他类:针对Object操作的方法,例如 toString 和 hashCode 方法等。


Joiner

这是在我们代码中出现频率比较高的一个功能。经常需要将几个字符串,或者字符串数组、集合之类的东西,拼接成一个以指定符号分隔各个元素的字符串,比如要将一个用List保存的集合拼起来作为SQL语句的条件,在知道Joiner之前我们会这样做。


// 拼接: AND goods IN(123,1234,345)
productSql.append(" AND goods IN (");
for (Long goods : spuIdList) {
  productSql.append(goods + ",");
}
productSql.delete(productSql.length() - 1, productSql.length()).append(")");
```java
上面的代码注意的一点就是我们要移除字符串最后的一个分隔符。虽然不难,但是很无聊,下面借助 Joiner 类,代码瞬间变得优雅起来。

productSql.append(" AND goods IN (“).append(Joiner.on(”,“).skipNulls().join(spuIdList)).append(”)");

**补充:**
*   如果传入的对象中包含空指针,会直接抛出空指针异常。Joiner 提供了两个方法,让我们能够优雅的处理待拼接集合中的空指针。
*   如果我们希望忽略空指针,那么可以调用 `skipNulls`方法,得到一个会跳过空指针的 Joiner 实例。如果希望将空指针变为某个指定的值,那么可以调用 `useForNull` 方法,指定用来替换空指针的字符串。
    ```
    Joiner.on(",").skipNulls().join(spuIdList);
    Joiner.on(",").useForNull("#").join(spuIdList);
    ```
*   Joiner 不仅可以返回string ,还有方法能够处理StringBuilder类:
[](https://blog.csdn.net/LXYDSF/article/details/128011305?ops_request_misc=%257B%2522request%255Fid%2522%253A%2522167056121516800182186127%2522%252C%2522scm%2522%253A%252220140713.130102334..%2522%257D&request_id=167056121516800182186127&biz_id=0&utm_medium=distribute.pc_search_result.none-task-blog-2~all~sobaiduend~default-1-128011305-null-null.142^v68^control,201^v4^add_ask,213^v2^t3_esquery_v3&utm_term=%20Joiner.on&spm=1018.2226.3001.4187)二、Joiner.MapJoiner
--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
MapJoiner 是 Joiner 的内部静态类,用于帮助将 Map 对象拼接成字符串。


@Test
public void testJoiner(){
    Map<String, String> map = new HashMap<>();
    map.put("红楼梦", "刘姥姥");
    map.put("三国演义", "关羽");
    map.put("水浒传", "李逵");
    map.put("西游记", "猪八戒");
    String str = Joiner.on(" ").withKeyValueSeparator(":").join(map);
    System.out.println(str);//水浒传:李逵 红楼梦:刘姥姥 三国演义:关羽 西游记:猪八戒
}
[](https://blog.csdn.net/LXYDSF/article/details/128011305?ops_request_misc=%257B%2522request%255Fid%2522%253A%2522167056121516800182186127%2522%252C%2522scm%2522%253A%252220140713.130102334..%2522%257D&request_id=167056121516800182186127&biz_id=0&utm_medium=distribute.pc_search_result.none-task-blog-2~all~sobaiduend~default-1-128011305-null-null.142^v68^control,201^v4^add_ask,213^v2^t3_esquery_v3&utm_term=%20Joiner.on&spm=1018.2226.3001.4187)三、常用API总结:
------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
#### [](https://blog.csdn.net/LXYDSF/article/details/128011305?ops_request_misc=%257B%2522request%255Fid%2522%253A%2522167056121516800182186127%2522%252C%2522scm%2522%253A%252220140713.130102334..%2522%257D&request_id=167056121516800182186127&biz_id=0&utm_medium=distribute.pc_search_result.none-task-blog-2~all~sobaiduend~default-1-128011305-null-null.142^v68^control,201^v4^add_ask,213^v2^t3_esquery_v3&utm_term=%20Joiner.on&spm=1018.2226.3001.4187)appendTo
```java
// 可追加,实现了Appendable接口的都可以使用
A appendTo(A appendable, Iterable<?> parts)
// 向appendable参数后追加first、second…所有参数
A appendTo(A appendable, @Nullable Object first, @Nullable Object second, Object… rest)

比较常见的实现类: BufferedWriter, CharArrayWriter, CharBuffer, FileWriter, FilterWriter, LogStream, OutputStreamWriter, PipedWriter, PrintStream, PrintWriter, StringBuffer, StringBuilder, StringWriter, Writer

用法

String[] arr = {"a","b","c"};
StringBuilder ab = new StringBuilder("start: ");
StringBuilder ac = Joiner.on("").appendTo(ab,arr);
System.out.println(ab); // start: abc
System.out.println(ac); // start: abc

Join+on

// 将可迭代的参数中所有子元素连接。
String join(Iterable<?> parts)
// 为static对象设置分隔符
static Joiner on(char separator)


Joiner实例不可变,即用final修饰,一旦初始化不可变,所以分步调用joiner的静态函数是不起作用的。如:


@Test
public void testJoiner(){
    Joiner joiner = Joiner.on(',');
    joiner.skipNulls(); // 不起作用!
    String str = joiner.join("wrong", null, "wrong");
    System.out.println(str);
}
// 会抛出 NullPointerException


这样使得joiner线程安全,并且返回的都是final static常量

其他

Joiner skipNulls()
Joiner useForNull(String nullText)
Joiner.MapJoiner withKeyValueSeparator(String keyValueSeparator)


最后

大家有兴趣的可以去了解下Guava中其他类的用法,源码写的也很棒!

相关文章
|
存储 算法 Linux
【实战项目】网络编程:在Linux环境下基于opencv和socket的人脸识别系统--C++实现
【实战项目】网络编程:在Linux环境下基于opencv和socket的人脸识别系统--C++实现
432 7
二极管基础知识与使用详解
二极管基础知识与使用详解
369 1
|
定位技术 API 开发工具
AppsFlyer 研究(七) 非GPS设备用户归因解决方案
AppsFlyer 研究(七) 非GPS设备用户归因解决方案
565 0
|
6月前
|
存储 NoSQL MongoDB
微服务——MongoDB常用命令——MongoDB索引的类型
本节介绍了MongoDB中索引的几种类型及其特点。包括单字段索引,支持升序/降序排序,索引顺序对操作无影响;复合索引,字段顺序重要,可实现多级排序;地理空间索引,支持平面与球面几何查询;文本索引,用于字符串搜索并存储词根;哈希索引,基于字段值散列,适合等值匹配但不支持范围查询。
164 1
微服务——MongoDB常用命令——MongoDB索引的类型
|
机器学习/深度学习 人工智能 自然语言处理
【自然语言处理】TF-IDF算法在人工智能方面的应用,附带代码
TF-IDF算法在人工智能领域,特别是自然语言处理(NLP)和信息检索中,被广泛用于特征提取和文本表示。以下是一个使用Python的scikit-learn库实现TF-IDF算法的简单示例,并展示如何将其应用于文本数据。
488 65
|
7月前
|
存储 算法 C++
【c++丨STL】priority_queue(优先级队列)的使用与模拟实现
本文介绍了STL中的容器适配器`priority_queue`(优先级队列)。`priority_queue`根据严格的弱排序标准设计,确保其第一个元素始终是最大元素。它底层使用堆结构实现,支持大堆和小堆,默认为大堆。常用操作包括构造函数、`empty`、`size`、`top`、`push`、`pop`和`swap`等。我们还模拟实现了`priority_queue`,通过仿函数控制堆的类型,并调用封装容器的接口实现功能。最后,感谢大家的支持与关注。
288 1
|
10月前
|
IDE 前端开发 开发工具
如何选择跨平台开发工具?
如何选择跨平台开发工具?
225 10
|
12月前
|
监控 网络协议 网络性能优化
如何办理支持UDP协议的网络
在当今网络环境中,UDP(用户数据报协议)因传输速度快、延迟低而广泛应用于在线游戏、视频流媒体、VoIP等实时服务。本文详细介绍了办理支持UDP协议网络的方法,包括了解UDP应用场景、选择合适的ISP及网络套餐、购买支持UDP的设备并进行优化设置,以及解决常见问题的策略,帮助用户确保网络稳定性和速度满足实际需求。
|
SQL 安全 PHP
DVWA File Inclusion 通关解析
DVWA File Inclusion 通关解析
Cannot get property 'versionCode' on extra properties extension as it does not exist
Cannot get property 'versionCode' on extra properties extension as it does not exist
331 0