JDK8——新增时间类、有关时间数据的交互问题

目录

一、实体类

二、数据库

三、数据交换 

四、关于LocalDateTime类型 (java 8)

4.1 旧版本日期时间问题

4.2 新版日期时间API介绍

4.2.1 LocalDate、LocalTime、LocalDateTime

4.2.2 日期时间的修改与比较

4.2.3 格式化和解析操作

4.2.4  Instant: 时间戳

4.2.5  Duration 与 Period——计算时间差

4.2.6 TemporalAdjuster—— 时间校正器

4.2.7 ZonedDateTime 时区讲解


一、实体类

   我们这个实体类中的两个时间类型的数据为LocalDateTime

package com.reggie_take_out.entity;

import com.baomidou.mybatisplus.annotation.FieldFill;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.Data;

import java.io.Serializable;
import java.time.LocalDateTime;

/**
 * 员工实体类
 */
@Data
@TableName("Employee")
public class Employee implements Serializable {
//  凡是一个类实现了Serializable接口,建议提供一个固定不变的序列化版本号,这样即使代码修改,java虚拟机也认为是同一个类
    private static final long serialVersionUID = 1L;


    @TableId("id")
    private Long id;

    @TableField("username")
    private String username;

    @TableField("name")
    private String name;

    @TableField("password")
    private String password;

    @TableField("phone")
    private String phone;

    @TableField("sex")
    private String sex;

    @TableField("id_number")
    private String idNumber;

    @TableField("status")
    private Integer status;

    @TableField("create_time")
    private LocalDateTime createTime;

    @TableField("update_time")
    private LocalDateTime updateTime;

    @TableField(value = "create_user",fill = FieldFill.INSERT)
    private Long createUser;

    @TableField(value = "update_user",fill = FieldFill.INSERT_UPDATE)
    private Long updateUser;

}

二、数据库

JDK8——新增时间类、有关时间数据的交互问题_第1张图片

 JDK8——新增时间类、有关时间数据的交互问题_第2张图片

三、数据交换 

LocalDateTime.now()  获取当前时间,格式为: - 月 - 日 - 时 - 分 - 秒

    @Override
    public R saveEmployee(HttpServletRequest request,Employee employee) {
//      首先判断是否存在这个username


//      1. 设置初始密码进行加密
        employee.setPassword(DigestUtils.md5DigestAsHex("123456".getBytes()));
//      2. 获取当前操作的用户ID
        Long empId = (Long) request.getSession().getAttribute("employee");
//        employee.setStatus(1);  入库默认1
        employee.setCreateTime(LocalDateTime.now());
        employee.setUpdateTime(LocalDateTime.now());
        employee.setCreateUser(empId);
        employee.setUpdateUser(empId);

        employeeMapper.insert(employee);

        return R.success("新增员工成功");
    }

四、关于LocalDateTime类型 (java 8)

与日期类进行对比

  JavaSE——java.util.Date日期类演示以及常用方法与操作_我爱布朗熊的博客-CSDN博客

 在前后端交互的时候,前端往往向后端传输字符串

4.1 旧版本日期时间问题

   旧版本中对日期的设计是非常差的

  •    第一条:设计不合理

          看下面的红框,Date类在java.util 与 java.sql中都有 

         java.util.Date同时包含日期和时间的,而java.sql.Date仅仅包含日期。

        此外用于格式化和解析的类在java,text包下

JDK8——新增时间类、有关时间数据的交互问题_第3张图片

  •  第二条:  日期格式化使用并不是很便捷
    @Test
    void test01() throws ParseException {
//      时间转换成字符串
        Date date = new Date();  //Sun Apr 09 14:03:41 CST 2023
        SimpleDateFormat sdf= new SimpleDateFormat("yyyy-MM-dd");
        String dateTime = sdf.format(date);
        System.out.println(dateTime);   //2023-04-09

//      字符串转换成时间
        Date parse = sdf.parse("2021-05-06");
        System.out.println(parse);  //Thu May 06 00:00:00 CST 2021

    }

  •  第三条: 数据安全问题——非线程安全 

         所有的日期类都是可变的,这是java日期类最大的问题之一

        在多线程的情况下,通过格式化对数据做操作的时候,会存在数据安全问题。

        时间格式化和解析操作是线程不安全的

JDK8——新增时间类、有关时间数据的交互问题_第4张图片

  •  第四条: 时区处理麻烦

       日期类并不提供国际化,没有时区支持

4.2 新版日期时间API介绍

此套API设计合理,是线程安全的。新的日期及时间API位于java.time包中,下面是一些关键类。

4.2.1 LocalDate、LocalTime、LocalDateTime

  •    LocalDate: 表示日期,包含年月日,格式为 2019-10-16
//      1. 获取指定日期
        LocalDate date = LocalDate.of(2021, 05, 06);
        System.out.println(date);             // 2021-05-06

//      2. 获取当前日期
        LocalDate now = LocalDate.now();
        System.out.println(now);  //2023-04-09

//      3.根据LocalDate对象获取对应信息
        System.out.println("年"+now.getYear());  //2023
        System.out.println("月"+now.getMonth()); //APRIL   这是一个枚举类型
        System.out.println("日"+now.getDayOfMonth()); //9
        System.out.println("星期"+now.getDayOfWeek()); //SUNDAY   这是一个枚举
//      枚举
        System.out.println("月"+now.getMonth().getValue()); //4    枚举值
        System.out.println("星期"+now.getDayOfWeek().getValue()); //7  枚举值

  •    LocalTime: 表示时间,包含时分秒,格式为 16:38:54.158549300
//        1.得到指定时间
        LocalTime time = LocalTime.of(5,23,33,123456);
        System.out.println(time); //05:23:33.000123456

//        2.获取当前时间
        LocalTime now = LocalTime.now();
        System.out.println(now); //分钟:45
        System.out.println("小时:"+now.getHour());   //小时:14
        System.out.println("分钟:"+now.getMinute()); //分钟:45
        System.out.println("秒:"+now.getSecond());   //秒:20
        System.out.println("纳秒:"+now.getNano());   //纳秒:698000000

  •    LocalDateTime: 表示日期时间,包含年月日,时分秒,格式为 2018-09-06T15:33:56.750。
//      1.获取指定的日期时间
        LocalDateTime time = LocalDateTime.of(2023, 04, 05, 12, 15, 30);
        System.out.println(time);

//      2. 获取当前的日期时间
        LocalDateTime now = LocalDateTime.now();
        System.out.println("年"+now.getYear());  //2023
        System.out.println("月"+now.getMonth()); //APRIL   这是一个枚举类型
        System.out.println("日"+now.getDayOfMonth()); //9
        System.out.println("星期"+now.getDayOfWeek()); //SUNDAY   这是一个枚举

        System.out.println("小时:"+now.getHour());   //小时:49
        System.out.println("分钟:"+now.getMinute()); //分钟:45
        System.out.println("秒:"+now.getSecond());   //秒:49
        System.out.println("纳秒:"+now.getNano());   //纳秒:667000000
        

4.2.2 日期时间的修改与比较

  日期的修改:

        LocalDateTime now = LocalDateTime.now();
        System.out.println("now=" + now);   //2023-04-09T14:57:07.994
//      1. 修改年份
//        注意!!
//         并不会修改原来的信息,而是创建一个新的对象
        LocalDateTime localDateTime = now.withYear(1998);
        System.out.println(localDateTime);  //1998-04-09T14:57:07.994


//      2. 在当前日期的基础上加上/减去指定的时间
        System.out.println(now.plusDays(2));  //两天后 2023-04-11T15:03:39.882
        System.out.println(now.plusYears(10));//十年后 2033-04-09T15:03:39.882

        System.out.println(now.minusMonths(6)); //半年后 2022-10-09T15:05:19.798
        System.out.println(now.minusDays(10)); //十天前  2023-03-30T15:05:19.798

日期的比较:

        LocalDate now =LocalDate.now();
        LocalDate date = LocalDate.of(2020,1,3);
//      时间比较
        System.out.println(now.isAfter(date));  //true
        System.out.println(now.isBefore(date)); //false
        System.out.println(now.isEqual(date));  //false

4.2.3 格式化和解析操作

  •    DateTimeFormatter: 日期时间格式化类
        LocalDateTime now = LocalDateTime.now();
//      指定格式
//      1.默认格式 DateTimeFormatter.ISO_LOCAL_DATE_TIME
        DateTimeFormatter isoLocalDateTime = DateTimeFormatter.ISO_LOCAL_DATE_TIME;
//      将日期时间转换为字符串
        String format = now.format(isoLocalDateTime);
        System.out.println(format); //默认格式 2023-04-09T15:30:56.136

//      2.ofPattern指定格式
        DateTimeFormatter dateTimeFormatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
        String format1 = now.format(dateTimeFormatter);
        System.out.println(format1);  //2023-04-09 15:33:01

//      3.将字符串解析为日期时间类型
        LocalDateTime parse = LocalDateTime.parse("1997-05-06 22:45:16", dateTimeFormatter);
        System.out.println(parse);   //1997-05-06T22:45:16

4.2.4  Instant: 时间戳

  •    Instant: 时间戳,表示一个特定的时间瞬间

      在jdk8中给我们新增一个Instant类(时间戳/时间线),内部保存了从1970年1月1日0时0分0秒以来的秒和纳秒(可以精确到纳秒)

        Instant now = Instant.now();
        System.out.println("now= "+now); //2023-04-09T07:40:59.610Z

        System.out.println(now.getNano()); //纳秒数据  610000000

4.2.5  Duration 与 Period——计算时间差

  •    Duration: 用于计算2个时间(LocalTime,时分秒)的距离。

               计算时,后面的数据减去前面的数据

        LocalTime now = LocalTime.now();
        LocalTime time = LocalTime.of(22,48);
//      计算时间差
        System.out.println(now);  //15:50:08.633
        Duration duration = Duration.between(now, time);
//      所差的天数
        System.out.println(duration.toDays());   //0
//      所差小时
        System.out.println(duration.toHours());  //6
//      所差分钟
        System.out.println(duration.toMinutes());//417
//      所差毫秒
        System.out.println(duration.toMillis()); //25071367

  •    Period:    用于计算2个日期(LocalDate,年月日)的距离
        LocalDate now = LocalDate.now();
        LocalDate time = LocalDate.of(1997,12,5);
//      计算时间差
        System.out.println(now);  //2023-04-09
        Period period = Period.between(now, time);
//      所差的年数
        System.out.println(period.getYears());   //-25
//      所差月份
        System.out.println(period.getMonths());  //-4
//      所差天数
        System.out.println(period.getDays());//-4

4.2.6 TemporalAdjuster—— 时间校正器

   有时候我们可以需要如下调整: 将日期调整到"下个月的第一天"等操作。当然我们也可以通过with进行修改,但是通过时间校正器更好。

   通过源码我们发现TemporalAdjuster是一个函数式接口,而且返回值类型和参数列表都是

Temporal类型

JDK8——新增时间类、有关时间数据的交互问题_第5张图片

        LocalDateTime now = LocalDateTime.now();
//      TemporalAdjuster 函数式接口
//      将当前日期调整到下个月一号
        TemporalAdjuster adjuster =(temporal -> {
//         这个能强制类型转换是因为LocalDateTime实现了Temporal接口
           LocalDateTime dateTIme = (LocalDateTime) temporal;
            LocalDateTime nextMonth = dateTIme.plusMonths(1) //下一个月
                    .withDayOfMonth(1);// 1号
            System.out.println("nextMonth="+nextMonth);  //nextMonth=2023-05-01T16:14:45.898
            return nextMonth;
        });

        LocalDateTime nextMonth = now.with(adjuster);
        System.out.println(nextMonth);  //2023-05-01T16:14:45.898

还有更简单的!!! 使用TemporalAdjusters工具类

JDK8——新增时间类、有关时间数据的交互问题_第6张图片

4.2.7 ZonedDateTime 时区讲解

     java8中加入了对时区的支持,localDate、LocalTime、LocalTime是不带时区的,带时区的日期时间类分别为:ZonedDate、ZonedTime、ZonedDateTime

   其中,每个时区都对应着ID,ID的格式为"区域/城市",例如:Asia/Shanghai等

    ZoneId:该类中包含了所有的时区信息

//     1.获取所有时区ID
        Set availableZoneIds = ZoneId.getAvailableZoneIds();
        for(String zone :availableZoneIds ){
            System.out.println(zone);
        }

JDK8——新增时间类、有关时间数据的交互问题_第7张图片

  •    ZonedDateTime: 包含时区的时间
//      2.获取标准时间 ZonedDateTime.now(Clock.systemUTC());
//         因为我们是东八区,比标准时间(本初子午线所在时区)快八个小时
        LocalDateTime localDateTime = LocalDateTime.now();
        System.out.println(localDateTime);  //2023-04-10T00:05:36.146
        ZonedDateTime bz = ZonedDateTime.now(Clock.systemUTC());
        System.out.println(bz);             //2023-04-09T16:05:36.146Z

//      3.使用计算机默认的时区创建日期时间
        ZonedDateTime now = ZonedDateTime.now();
        System.out.println(now);  //  2023-04-10T00:05:36.146+08:00[Asia/Shanghai]

//       4. 使用指定的时期创建日期时间
        ZonedDateTime now1 = ZonedDateTime.now(ZoneId.of("America/Marigot"));
        System.out.println(now1);//2023-04-09T12:05:36.147-04:00[America/Marigot]

        Java中使用的历法是ISO 8601日历系统,它是世界民用历法,也就是我们所说的公历。平年有365天,闺年是366天。此外Java 8还提供了4套其他历法,分别是:

  •    ThaiBuddhistDate: 泰国佛教历
  •    MinguoDate: 中华民国历
  •    JapaneseDate:日本历
  •     HiirahDate: 伊斯兰历

你可能感兴趣的:(springboot,java,jvm,servlet)