Java 8 java.time日期时间API完整使用指南与代码实例

2024-06-21 李腾 95 次阅读 0 次点赞
本文详细介绍了Java 8引入的java.time日期时间API,通过大量实用代码示例展示了LocalDate、LocalTime、LocalDateTime、ZonedDateTime等核心类的使用方法,包括日期创建、运算比较、时区转换、格式化解析等关键操作。内容涵盖Period和Duration时间段计算、DateTimeFormatter格式化处理以及Instant时间戳应用,并提供完整的综合示例,帮助开发者从旧版Date/Calendar平滑过渡到新版API,提升日期时间处理效率和代码质量。

java.time 是 Java 8 引入的日期和时间 API,它解决了旧的 java.util.Date 和 java.util.Calendar 类的诸多问题,提供了更直观、线程安全且功能丰富的日期时间处理能力。

主要特点

1、不可变性:所有核心类都是不可变的,线程安全

2、清晰的API设计:方法命名直观,易于理解

3、时区支持:完善的时区处理

4、格式化解析:强大的格式化功能

核心类概览

1. LocalDate - 日期(不含时间)

import java.time.LocalDate;
import java.time.DayOfWeek;
import java.time.format.DateTimeFormatter;
import java.time.temporal.ChronoUnit;

// 创建日期
LocalDate today = LocalDate.now();
LocalDate specificDate = LocalDate.of(2024, 5, 15);
LocalDate parsedDate = LocalDate.parse("2024-05-20");

System.out.println("今天: " + today);
System.out.println("特定日期: " + specificDate);
System.out.println("解析日期: " + parsedDate);

// 日期运算
LocalDate tomorrow = today.plusDays(1);
LocalDate nextWeek = today.plusWeeks(1);
LocalDate lastMonth = today.minusMonths(1);

System.out.println("明天: " + tomorrow);
System.out.println("下周: " + nextWeek);
System.out.println("上月: " + lastMonth);

// 日期比较
boolean isAfter = tomorrow.isAfter(today);
boolean isBefore = lastMonth.isBefore(today);
boolean isEqual = today.equals(LocalDate.now());

System.out.println("明天在今天之后: " + isAfter);
System.out.println("上月在今天之前: " + isBefore);

// 获取日期信息
DayOfWeek dayOfWeek = today.getDayOfWeek();
int dayOfMonth = today.getDayOfMonth();
int dayOfYear = today.getDayOfYear();

System.out.println("星期: " + dayOfWeek);
System.out.println("月中第几天: " + dayOfMonth);
System.out.println("年中第几天: " + dayOfYear);

// 格式化
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy/MM/dd");
String formatted = today.format(formatter);
System.out.println("格式化日期: " + formatted);

2. LocalTime - 时间(不含日期)

import java.time.LocalTime;
import java.time.format.DateTimeFormatter;

// 创建时间
LocalTime now = LocalTime.now();
LocalTime specificTime = LocalTime.of(14, 30, 15); // 14:30:15
LocalTime parsedTime = LocalTime.parse("09:45:00");

System.out.println("现在时间: " + now);
System.out.println("特定时间: " + specificTime);
System.out.println("解析时间: " + parsedTime);

// 时间运算
LocalTime inOneHour = now.plusHours(1);
LocalTime in30Minutes = now.plusMinutes(30);
LocalTime minus15Seconds = now.minusSeconds(15);

System.out.println("一小时后: " + inOneHour);
System.out.println("30分钟后: " + in30Minutes);

// 格式化时间
DateTimeFormatter timeFormatter = DateTimeFormatter.ofPattern("HH时mm分ss秒");
String formattedTime = now.format(timeFormatter);
System.out.println("格式化时间: " + formattedTime);

3. LocalDateTime - 日期时间

import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;

// 创建日期时间
LocalDateTime now = LocalDateTime.now();
LocalDateTime specificDateTime = LocalDateTime.of(2024, 5, 15, 14, 30, 0);

System.out.println("现在: " + now);
System.out.println("特定日期时间: " + specificDateTime);

// 组合日期和时间
LocalDate date = LocalDate.of(2024, 5, 15);
LocalTime time = LocalTime.of(14, 30);
LocalDateTime combined = LocalDateTime.of(date, time);

System.out.println("组合日期时间: " + combined);

// 格式化
DateTimeFormatter dtFormatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
String formatted = now.format(dtFormatter);
System.out.println("格式化日期时间: " + formatted);

4. ZonedDateTime - 带时区的日期时间

import java.time.ZonedDateTime;
import java.time.ZoneId;
import java.time.format.DateTimeFormatter;

// 创建带时区的日期时间
ZonedDateTime nowInShanghai = ZonedDateTime.now(ZoneId.of("Asia/Shanghai"));
ZonedDateTime nowInNewYork = ZonedDateTime.now(ZoneId.of("America/New_York"));

System.out.println("上海时间: " + nowInShanghai);
System.out.println("纽约时间: " + nowInNewYork);

// 时区转换
ZonedDateTime tokyoTime = nowInShanghai.withZoneSameInstant(ZoneId.of("Asia/Tokyo"));
System.out.println("对应的东京时间: " + tokyoTime);

// 获取所有可用时区
System.out.println("\n部分可用时区:");
ZoneId.getAvailableZoneIds().stream()
    .filter(zone -> zone.contains("Asia"))
    .limit(5)
    .forEach(System.out::println);

5. Period 和 Duration - 时间段

import java.time.LocalDate;
import java.time.LocalTime;
import java.time.Period;
import java.time.Duration;
import java.time.temporal.ChronoUnit;

// Period - 基于日期的时段(年、月、日)
LocalDate startDate = LocalDate.of(2020, 1, 1);
LocalDate endDate = LocalDate.of(2024, 5, 15);
Period period = Period.between(startDate, endDate);

System.out.println("时间段: " + period.getYears() + "年 " + 
                  period.getMonths() + "月 " + 
                  period.getDays() + "天");

// Duration - 基于时间的时段(小时、分钟、秒)
LocalTime startTime = LocalTime.of(9, 0);
LocalTime endTime = LocalTime.of(17, 30);
Duration duration = Duration.between(startTime, endTime);

System.out.println("工作时间: " + duration.toHours() + "小时 " + 
                  (duration.toMinutes() % 60) + "分钟");

// 使用 ChronoUnit 计算
long daysBetween = ChronoUnit.DAYS.between(startDate, endDate);
long hoursBetween = ChronoUnit.HOURS.between(startTime, endTime);

System.out.println("总天数: " + daysBetween);
System.out.println("总小时数: " + hoursBetween);

6. DateTimeFormatter - 格式化

import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.Locale;

LocalDateTime now = LocalDateTime.now();

// 预定义的格式化器
System.out.println("ISO格式: " + now.format(DateTimeFormatter.ISO_DATE_TIME));
System.out.println("基本ISO格式: " + now.format(DateTimeFormatter.BASIC_ISO_DATE));

// 自定义格式化器
DateTimeFormatter customFormatter = DateTimeFormatter.ofPattern("yyyy年MM月dd日 HH时mm分ss秒");
System.out.println("中文格式: " + now.format(customFormatter));

// 本地化格式化
DateTimeFormatter germanFormatter = DateTimeFormatter.ofPattern("dd. MMMM yyyy", Locale.GERMAN);
System.out.println("德语格式: " + now.format(germanFormatter));

// 解析字符串为日期时间
String dateString = "2024-05-15 14:30:00";
DateTimeFormatter parser = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
LocalDateTime parsedDateTime = LocalDateTime.parse(dateString, parser);
System.out.println("解析结果: " + parsedDateTime);

7. Instant - 时间戳

import java.time.Instant;
import java.time.LocalDateTime;
import java.time.ZoneId;

// 获取当前时间戳
Instant now = Instant.now();
System.out.println("当前时间戳: " + now);

// 时间戳运算
Instant inOneHour = now.plusSeconds(3600);
System.out.println("一小时后: " + inOneHour);

// 与 LocalDateTime 转换
LocalDateTime localDateTime = LocalDateTime.ofInstant(now, ZoneId.systemDefault());
Instant backToInstant = localDateTime.atZone(ZoneId.systemDefault()).toInstant();

System.out.println("转换为LocalDateTime: " + localDateTime);
System.out.println("转换回Instant: " + backToInstant);

完整示例

import java.time.*;
import java.time.format.DateTimeFormatter;
import java.time.temporal.ChronoUnit;

public class DateTimeExample {
    public static void main(String[] args) {
        // 1. 生日计算
        LocalDate birthday = LocalDate.of(1990, 8, 15);
        LocalDate today = LocalDate.now();
        
        Period age = Period.between(birthday, today);
        System.out.printf("年龄: %d岁%d个月%d天%n", 
            age.getYears(), age.getMonths(), age.getDays());
        
        // 2. 会议安排
        LocalDateTime meetingStart = LocalDateTime.of(2024, 5, 20, 14, 0);
        Duration meetingDuration = Duration.ofHours(2).plusMinutes(30);
        LocalDateTime meetingEnd = meetingStart.plus(meetingDuration);
        
        DateTimeFormatter formatter = DateTimeFormatter.ofPattern("MM月dd日 HH:mm");
        System.out.printf("会议时间: %s - %s%n", 
            meetingStart.format(formatter), meetingEnd.format(formatter));
        
        // 3. 国际会议时区转换
        ZonedDateTime nyMeeting = ZonedDateTime.of(
            LocalDateTime.of(2024, 5, 20, 9, 0), 
            ZoneId.of("America/New_York")
        );
        
        ZonedDateTime shMeeting = nyMeeting.withZoneSameInstant(ZoneId.of("Asia/Shanghai"));
        System.out.printf("纽约时间: %s%n", nyMeeting);
        System.out.printf("上海时间: %s%n", shMeeting);
        
        // 4. 日期比较
        LocalDate deadline = LocalDate.of(2024, 6, 1);
        long daysUntilDeadline = ChronoUnit.DAYS.between(today, deadline);
        System.out.printf("距离截止日期还有 %d 天%n", daysUntilDeadline);
    }
}

总结

java.time 包提供了:

1、清晰的类型分离:日期、时间、日期时间、时区等都有专门的类

2、不可变性和线程安全

3、流畅的API:方法链式调用

4、强大的时区支持

5、丰富的格式化选项

这些特性使得日期时间处理变得更加简单、安全和直观。

最后更新于3月前
本文由人工编写,AI优化,转载请注明原文地址: Java 8时间日期处理:java.time使用详解与实战代码示例

评论 (3)

发表评论

昵称:加载中...
马小玲2025-12-04 12:06:46
文章讲得很清楚,示例代码也很实用!终于搞懂了LocalDate的用法,比老Date类好用太多了。感谢作者分享!
温柔一刀2025-11-12 19:47:29
感谢分享!java.time确实比Date好用太多了,代码示例很实用,特别是日期比较和格式化部分。请问在跨时区业务场景中,ZonedDateTime和Instant该如何选择?
晨曦微露2025-11-10 18:23:19
之前一直用老Date类各种坑,这个java.time教程太及时了!正好用LocalDate重构了项目的报表模块,代码清爽多了,再也不用担心线程安全问题了。