Bootstrap

【Java】Java 常用核心类篇 —— 时间-日期API(下)

其他常用类

在 Java 的 java.time 包中,除了 LocalDate、LocalTime、LocalDateTime、Instant、Duration 和 Period 类外,还有不少其他常用的日期时间处理类:

ZonedDateTime 类

ZonedDateTime 表示带有时区的日期和时间,它整合了日期、时间和时区信息,适用于处理跨时区的日期时间计算和显示。
常用方法示例

import java.time.ZoneId;
import java.time.ZonedDateTime;

public class ZonedDateTimeExample {
    public static void main(String[] args) {
        // 获取当前带时区的日期和时间
        ZonedDateTime now = ZonedDateTime.now();
        System.out.println("当前带时区的日期和时间: " + now);

        // 根据指定时区创建 ZonedDateTime
        ZoneId tokyoZone = ZoneId.of("Asia/Tokyo");
        ZonedDateTime tokyoDateTime = ZonedDateTime.now(tokyoZone);
        System.out.println("东京当前的日期和时间: " + tokyoDateTime);
    }
}

OffsetDateTime 类

OffsetDateTime 表示带有时区偏移量(相对于 UTC)的日期和时间,它不包含完整的时区规则信息,仅包含偏移量,适用于需要明确指定与 UTC 偏移的场景。
常用方法示例

import java.time.OffsetDateTime;
import java.time.ZoneOffset;

public class OffsetDateTimeExample {
    public static void main(String[] args) {
        // 获取当前带偏移量的日期和时间
        OffsetDateTime now = OffsetDateTime.now();
        System.out.println("当前带偏移量的日期和时间: " + now);

        // 创建指定偏移量的 OffsetDateTime
        ZoneOffset offset = ZoneOffset.of("+02:00");
        OffsetDateTime specificOffsetDateTime = OffsetDateTime.now(offset);
        System.out.println("指定偏移量的日期和时间: " + specificOffsetDateTime);
    }
}

OffsetTime 类

OffsetTime 表示带有时区偏移量的时间,不包含日期信息,适用于只关注时间且需要考虑时区偏移的场景。
常用方法示例

import java.time.OffsetTime;
import java.time.ZoneOffset;

public class OffsetTimeExample {
    public static void main(String[] args) {
        // 获取当前带偏移量的时间
        OffsetTime now = OffsetTime.now();
        System.out.println("当前带偏移量的时间: " + now);

        // 创建指定偏移量的 OffsetTime
        ZoneOffset offset = ZoneOffset.of("-05:00");
        OffsetTime specificOffsetTime = OffsetTime.now(offset);
        System.out.println("指定偏移量的时间: " + specificOffsetTime);
    }
}

Year 类

Year 类表示年份,提供了对年份的各种操作,如判断是否为闰年等。
常用方法示例

import java.time.Year;

public class YearExample {
    public static void main(String[] args) {
        // 获取当前年份
        Year currentYear = Year.now();
        System.out.println("当前年份: " + currentYear);

        // 判断指定年份是否为闰年
        Year specificYear = Year.of(2024);
        boolean isLeap = specificYear.isLeap();
        System.out.println(specificYear + " 是否为闰年: " + isLeap);
    }
}

YearMonth 类

YearMonth 表示年月,可用于处理与月份相关的统计和计算。
常用方法示例

import java.time.YearMonth;

public class YearMonthExample {
    public static void main(String[] args) {
        // 获取当前年月
        YearMonth currentYearMonth = YearMonth.now();
        System.out.println("当前年月: " + currentYearMonth);

        // 获取指定年月的天数
        YearMonth specificYearMonth = YearMonth.of(2024, 2);
        int lengthOfMonth = specificYearMonth.lengthOfMonth();
        System.out.println(specificYearMonth + " 的天数: " + lengthOfMonth);
    }
}

MonthDay 类

MonthDay 表示月和日,不包含年份信息,常用于处理每年固定日期的事件,如生日。
常用方法示例

import java.time.MonthDay;

public class MonthDayExample {
    public static void main(String[] args) {
        // 创建指定的月日
        MonthDay birthday = MonthDay.of(10, 15);
        System.out.println("生日: " + birthday);

        // 检查当前日期是否是指定的月日
        MonthDay currentMonthDay = MonthDay.now();
        boolean isBirthday = currentMonthDay.equals(birthday);
        System.out.println("今天是否是生日: " + isBirthday);
    }
}

ZoneId 类

ZoneId 用于表示时区标识符,可用于获取系统默认时区、根据 ID 创建特定时区等操作。
常用方法示例

import java.time.ZoneId;
import java.util.Set;

public class ZoneIdExample {
    public static void main(String[] args) {
        // 获取系统默认时区
        ZoneId defaultZone = ZoneId.systemDefault();
        System.out.println("系统默认时区: " + defaultZone);

        // 获取所有可用的时区 ID
        Set<String> allZoneIds = ZoneId.getAvailableZoneIds();
        System.out.println("所有可用的时区 ID 数量: " + allZoneIds.size());
    }
}

ZoneOffset 类

ZoneOffset 表示相对于 UTC 的时区偏移量,是 OffsetDateTime 和 OffsetTime 中使用的时区偏移信息。
常用方法示例

import java.time.ZoneOffset;

public class ZoneOffsetExample {
    public static void main(String[] args) {
        // 创建指定偏移量
        ZoneOffset offset = ZoneOffset.of("+03:00");
        System.out.println("指定的时区偏移量: " + offset);

        // 获取当前系统的时区偏移量
        ZoneOffset systemOffset = ZoneOffset.systemDefault().getRules().getOffset(java.time.Instant.now());
        System.out.println("当前系统的时区偏移量: " + systemOffset);
    }
}

日期时间解析和格式化

时态数据解析

在 Java 里,java.time 包中的各个日期时间类的 parse 方法和时态数据解析密切相关。时态数据解析本质上就是利用这些 parse 方法,把各种格式的字符串转换为对应的日期时间对象。下面结合不同类型的时态数据和 parse 方法进行详细介绍,并给出示例代码。

解析 LocalDate 类型的时态数据

LocalDate 表示不包含时间和时区信息的日期,使用 parse 方法可以将日期字符串解析为 LocalDate 对象。

import java.time.LocalDate;
import java.time.format.DateTimeFormatter;
import java.time.format.DateTimeParseException;

public class LocalDateParsing {
    public static void main(String[] args) {
        // 预定义格式(ISO_LOCAL_DATE)解析
        String isoDateStr = "2024-10-15";
        try {
            LocalDate isoParsedDate = LocalDate.parse(isoDateStr);
            System.out.println("ISO 格式解析后的日期: " + isoParsedDate);
        } catch (DateTimeParseException e) {
            System.out.println("ISO 格式解析失败: " + e.getMessage());
        }

        // 自定义格式解析
        String customDateStr = "15/10/2024";
        DateTimeFormatter customFormatter = DateTimeFormatter.ofPattern("dd/MM/yyyy");
        try {
            LocalDate customParsedDate = LocalDate.parse(customDateStr, customFormatter);
            System.out.println("自定义格式解析后的日期: " + customParsedDate);
        } catch (DateTimeParseException e) {
            System.out.println("自定义格式解析失败: " + e.getMessage());
        }
    }
}

解析 LocalTime 类型的时态数据

LocalTime 表示不包含日期和时区信息的时间,通过 parse 方法能将时间字符串解析为 LocalTime 对象。

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

public class LocalTimeParsing {
    public static void main(String[] args) {
        // 预定义格式(ISO_LOCAL_TIME)解析
        String isoTimeStr = "14:30:00";
        try {
            LocalTime isoParsedTime = LocalTime.parse(isoTimeStr);
            System.out.println("ISO 格式解析后的时间: " + isoParsedTime);
        } catch (DateTimeParseException e) {
            System.out.println("ISO 格式解析失败: " + e.getMessage());
        }

        // 自定义格式解析
        String customTimeStr = "2:30 PM";
        DateTimeFormatter customFormatter = DateTimeFormatter.ofPattern("h:mm a");
        try {
            LocalTime customParsedTime = LocalTime.parse(customTimeStr, customFormatter);
            System.out.println("自定义格式解析后的时间: " + customParsedTime);
        } catch (DateTimeParseException e) {
            System.out.println("自定义格式解析失败: " + e.getMessage());
        }
    }
}

解析 LocalDateTime 类型的时态数据

LocalDateTime 是日期和时间的组合,不包含时区信息,使用 parse 方法可将日期时间字符串解析为 LocalDateTime 对象。

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

public class LocalDateTimeParsing {
    public static void main(String[] args) {
        // 预定义格式(ISO_LOCAL_DATE_TIME)解析
        String isoDateTimeStr = "2024-10-15T14:30:00";
        try {
            LocalDateTime isoParsedDateTime = LocalDateTime.parse(isoDateTimeStr);
            System.out.println("ISO 格式解析后的日期时间: " + isoParsedDateTime);
        } catch (DateTimeParseException e) {
            System.out.println("ISO 格式解析失败: " + e.getMessage());
        }

        // 自定义格式解析
        String customDateTimeStr = "15/10/2024 2:30 PM";
        DateTimeFormatter customFormatter = DateTimeFormatter.ofPattern("dd/MM/yyyy h:mm a");
        try {
            LocalDateTime customParsedDateTime = LocalDateTime.parse(customDateTimeStr, customFormatter);
            System.out.println("自定义格式解析后的日期时间: " + customParsedDateTime);
        } catch (DateTimeParseException e) {
            System.out.println("自定义格式解析失败: " + e.getMessage());
        }
    }
}

解析带时区的时态数据

解析 ZonedDateTime

ZonedDateTime 表示带有时区信息的日期时间,使用 parse 方法可将包含时区信息的字符串解析为 ZonedDateTime 对象。

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

public class ZonedDateTimeParsing {
    public static void main(String[] args) {
        // 预定义格式(ISO_ZONED_DATE_TIME)解析
        String isoZonedDateTimeStr = "2024-10-15T14:30:00+08:00[Asia/Shanghai]";
        try {
            ZonedDateTime isoParsedZonedDateTime = ZonedDateTime.parse(isoZonedDateTimeStr);
            System.out.println("ISO 格式解析后的带时区日期时间: " + isoParsedZonedDateTime);
        } catch (DateTimeParseException e) {
            System.out.println("ISO 格式解析失败: " + e.getMessage());
        }

        // 自定义格式解析
        String customZonedDateTimeStr = "15/10/2024 2:30 PM +08:00[Asia/Shanghai]";
        DateTimeFormatter customFormatter = DateTimeFormatter.ofPattern("dd/MM/yyyy h:mm a ZZZZ[VV]");
        try {
            ZonedDateTime customParsedZonedDateTime = ZonedDateTime.parse(customZonedDateTimeStr, customFormatter);
            System.out.println("自定义格式解析后的带时区日期时间: " + customParsedZonedDateTime);
        } catch (DateTimeParseException e) {
            System.out.println("自定义格式解析失败: " + e.getMessage());
        }
    }
}
解析 OffsetDateTime

OffsetDateTime 表示带有时区偏移量的日期时间,同样可以使用 parse 方法进行解析。

import java.time.OffsetDateTime;
import java.time.format.DateTimeFormatter;
import java.time.format.DateTimeParseException;

public class OffsetDateTimeParsing {
    public static void main(String[] args) {
        // 预定义格式(ISO_OFFSET_DATE_TIME)解析
        String isoOffsetDateTimeStr = "2024-10-15T14:30:00+08:00";
        try {
            OffsetDateTime isoParsedOffsetDateTime = OffsetDateTime.parse(isoOffsetDateTimeStr);
            System.out.println("ISO 格式解析后的带偏移量日期时间: " + isoParsedOffsetDateTime);
        } catch (DateTimeParseException e) {
            System.out.println("ISO 格式解析失败: " + e.getMessage());
        }

        // 自定义格式解析
        String customOffsetDateTimeStr = "15/10/2024 2:30 PM +08:00";
        DateTimeFormatter customFormatter = DateTimeFormatter.ofPattern("dd/MM/yyyy h:mm a ZZZZ");
        try {
            OffsetDateTime customParsedOffsetDateTime = OffsetDateTime.parse(customOffsetDateTimeStr, customFormatter);
            System.out.println("自定义格式解析后的带偏移量日期时间: " + customParsedOffsetDateTime);
        } catch (DateTimeParseException e) {
            System.out.println("自定义格式解析失败: " + e.getMessage());
        }
    }
}

解析 Instant 类型的时态数据

Instant 表示时间线上的一个瞬时点,使用 parse 方法可将符合 ISO-8601 格式的字符串解析为 Instant 对象。

import java.time.Instant;
import java.time.format.DateTimeParseException;

public class InstantParsing {
    public static void main(String[] args) {
        String instantStr = "2024-10-15T14:30:00Z";
        try {
            Instant parsedInstant = Instant.parse(instantStr);
            System.out.println("解析后的 Instant 对象: " + parsedInstant);
        } catch (DateTimeParseException e) {
            System.out.println("解析失败: " + e.getMessage());
        }
    }
}

总结

  • 不同的日期时间类(如 LocalDate、LocalTime、LocalDateTime、ZonedDateTime、OffsetDateTime 和 Instant)都提供了 parse 方法用于时态数据解析。
  • 可以使用预定义的格式(如 ISO_LOCAL_DATE、ISO_LOCAL_TIME 等)或自定义的 DateTimeFormatter 来解析字符串。
  • 在实际应用中,要对可能出现的 DateTimeParseException 异常进行处理,以确保程序的健壮性。

时态数据格式化

在 Java 里,时态数据格式化主要是把 java.time 包中的日期、时间或日期时间对象,利用 format 方法和 DateTimeFormatter 类转化成特定格式的字符串。下面将详细介绍不同类型时态数据如何运用 format 方法进行格式化。

格式化 LocalDate

LocalDate 代表不含时间和时区信息的日期,可使用 format 方法搭配不同的 DateTimeFormatter 进行格式化。

import java.time.LocalDate;
import java.time.format.DateTimeFormatter;

public class LocalDateFormatting {
    public static void main(String[] args) {
        // 获取当前日期
        LocalDate currentDate = LocalDate.now();

        // 使用预定义的 ISO 格式
        String isoFormattedDate = currentDate.format(DateTimeFormatter.ISO_LOCAL_DATE);
        System.out.println("ISO 格式的日期: " + isoFormattedDate);

        // 使用自定义格式
        DateTimeFormatter customFormatter = DateTimeFormatter.ofPattern("dd/MM/yyyy");
        String customFormattedDate = currentDate.format(customFormatter);
        System.out.println("自定义格式的日期: " + customFormattedDate);
    }
}

格式化 LocalTime

LocalTime 表示不含日期和时区信息的时间,同样可以借助 format 方法和 DateTimeFormatter 来格式化。

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

public class LocalTimeFormatting {
    public static void main(String[] args) {
        // 获取当前时间
        LocalTime currentTime = LocalTime.now();

        // 使用预定义的 ISO 格式
        String isoFormattedTime = currentTime.format(DateTimeFormatter.ISO_LOCAL_TIME);
        System.out.println("ISO 格式的时间: " + isoFormattedTime);

        // 使用自定义格式
        DateTimeFormatter customFormatter = DateTimeFormatter.ofPattern("hh:mm:ss a");
        String customFormattedTime = currentTime.format(customFormatter);
        System.out.println("自定义格式的时间: " + customFormattedTime);
    }
}

格式化 LocalDateTime

LocalDateTime 是日期和时间的组合,不包含时区信息,可通过 format 方法按指定格式输出。

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

public class LocalDateTimeFormatting {
    public static void main(String[] args) {
        // 获取当前日期时间
        LocalDateTime currentDateTime = LocalDateTime.now();

        // 使用预定义的 ISO 格式
        String isoFormattedDateTime = currentDateTime.format(DateTimeFormatter.ISO_LOCAL_DATE_TIME);
        System.out.println("ISO 格式的日期时间: " + isoFormattedDateTime);

        // 使用自定义格式
        DateTimeFormatter customFormatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
        String customFormattedDateTime = currentDateTime.format(customFormatter);
        System.out.println("自定义格式的日期时间: " + customFormattedDateTime);
    }
}

格式化带时区的时态数据

格式化 ZonedDateTime

ZonedDateTime 表示带有时区信息的日期时间,格式化时可包含时区相关信息。

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

public class ZonedDateTimeFormatting {
    public static void main(String[] args) {
        // 获取当前带时区的日期时间
        ZonedDateTime currentZonedDateTime = ZonedDateTime.now();

        // 使用预定义的 ISO 格式
        String isoFormattedZonedDateTime = currentZonedDateTime.format(DateTimeFormatter.ISO_ZONED_DATE_TIME);
        System.out.println("ISO 格式的带时区日期时间: " + isoFormattedZonedDateTime);

        // 使用自定义格式,包含时区信息
        DateTimeFormatter customFormatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss zzz VV");
        String customFormattedZonedDateTime = currentZonedDateTime.format(customFormatter);
        System.out.println("自定义格式的带时区日期时间: " + customFormattedZonedDateTime);
    }
}
格式化 OffsetDateTime

OffsetDateTime 表示带有时区偏移量的日期时间,格式化方式类似。

import java.time.OffsetDateTime;
import java.time.format.DateTimeFormatter;

public class OffsetDateTimeFormatting {
    public static void main(String[] args) {
        // 获取当前带偏移量的日期时间
        OffsetDateTime currentOffsetDateTime = OffsetDateTime.now();

        // 使用预定义的 ISO 格式
        String isoFormattedOffsetDateTime = currentOffsetDateTime.format(DateTimeFormatter.ISO_OFFSET_DATE_TIME);
        System.out.println("ISO 格式的带偏移量日期时间: " + isoFormattedOffsetDateTime);

        // 使用自定义格式,包含偏移量信息
        DateTimeFormatter customFormatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss Z");
        String customFormattedOffsetDateTime = currentOffsetDateTime.format(customFormatter);
        System.out.println("自定义格式的带偏移量日期时间: " + customFormattedOffsetDateTime);
    }
}

总结

  • format 方法是 java.time 包中日期时间类用于格式化的核心方法,需要和 DateTimeFormatter 搭配使用。
  • DateTimeFormatter 提供了预定义的格式,也支持自定义格式,能满足不同的业务需求。
  • 格式化带时区的时态数据时,要确保自定义格式中包含时区或偏移量相关的占位符,以正确显示时区信息。
;