ZetCode

Java HijrahDate 类

最后修改时间:2025 年 4 月 16 日

java.time.chrono.HijrahDate 类表示伊斯兰希吉里历法中的日期。该历法在许多穆斯林国家用于宗教目的。它是一种阴历,一年有 12 个月。

HijrahDate 是不可变的且线程安全的。它实现了 ChronoLocalDate 接口。该类支持与 ISO 日期的转换。希吉里历的年比公历年短大约 11 天。

HijrahDate 类概述

HijrahDate 提供了创建、操作和格式化伊斯兰日期的方法。它支持日期算术和比较操作。该类默认使用 Umm al-Qura 版本的希吉里历。

public final class HijrahDate implements ChronoLocalDate, Serializable {
    public static HijrahDate now();
    public static HijrahDate of(int prolepticYear, int month, int dayOfMonth);
    public static HijrahDate from(TemporalAccessor temporal);
    public static HijrahDate now(ZoneId zone);
    public int lengthOfMonth();
    public int lengthOfYear();
    public HijrahDate plus(long amountToAdd, TemporalUnit unit);
    public HijrahDate minus(long amountToSubtract, TemporalUnit unit);
    public long until(Temporal endExclusive, TemporalUnit unit);
}

上面的代码展示了 HijrahDate 的关键方法。这些方法允许创建、比较和操作伊斯兰日期。该类提供了在希吉里历和其他历法系统之间的转换。

创建 HijrahDate 对象

HijrahDate 对象可以通过多种方式创建。最常用的方法是使用 now 获取当前日期,以及使用工厂方法创建特定日期。也支持从其他日期类型的转换。

Main.java
package com.zetcode;

import java.time.chrono.HijrahDate;
import java.time.LocalDate;
import java.time.ZoneId;

public class Main {

    public static void main(String[] args) {
        
        // Current Hijri date
        HijrahDate now = HijrahDate.now();
        System.out.println("Current Hijri date: " + now);
        
        // Specific Hijri date
        HijrahDate date1 = HijrahDate.of(1445, 9, 1);
        System.out.println("Specific Hijri date: " + date1);
        
        // From LocalDate
        HijrahDate date2 = HijrahDate.from(LocalDate.now());
        System.out.println("From LocalDate: " + date2);
        
        // With timezone
        HijrahDate date3 = HijrahDate.now(ZoneId.of("Asia/Riyadh"));
        System.out.println("With timezone: " + date3);
    }
}

此示例演示了创建 HijrahDate 对象的不同方法。输出显示了带有希吉里纪元的类似 ISO 的格式的日期。now 方法使用系统默认时区。

获取日期组件

一个 HijrahDate 可以分解为它的年、月和日组件。这些值表示伊斯兰日期。这些方法对于以自定义格式显示日期很有用。

Main.java
package com.zetcode;

import java.time.chrono.HijrahDate;
import java.time.temporal.ChronoField;

public class Main {

    public static void main(String[] args) {

        HijrahDate hijrahDate = HijrahDate.now();
        
        // Get year
        int year = hijrahDate.get(ChronoField.YEAR);
        System.out.println("Hijri year: " + year);
        
        // Get month
        int month = hijrahDate.get(ChronoField.MONTH_OF_YEAR);
        System.out.println("Hijri month: " + month);
        
        // Get day
        int day = hijrahDate.get(ChronoField.DAY_OF_MONTH);
        System.out.println("Hijri day: " + day);
        
        // Get era
        String era = hijrahDate.getEra().toString();
        System.out.println("Era: " + era);
    }
}

此示例演示了如何从 HijrahDate 中提取组件。ChronoField 常量用于访问日期部分。在希吉里历中,纪元始终是 AH (Anno Hegirae)。

比较 HijrahDates

可以比较 HijrahDates 以确定时间顺序。该类提供了 isBeforeisAftercompareTo 方法。这些比较与其他日期类型的操作方式相同。

Main.java
package com.zetcode;

import java.time.chrono.HijrahDate;
import java.time.temporal.ChronoUnit;

public class Main {

    public static void main(String[] args) {

        HijrahDate today = HijrahDate.now();
        HijrahDate tomorrow = today.plus(1, ChronoUnit.DAYS);
        HijrahDate yesterday = today.minus(1, ChronoUnit.DAYS);
        
        System.out.println("Today is before tomorrow: " + today.isBefore(tomorrow));
        System.out.println("Today is after yesterday: " + today.isAfter(yesterday));
        System.out.println("Comparison result: " + today.compareTo(tomorrow));
        
        // Equality check
        HijrahDate sameDate = HijrahDate.of(today.get(ChronoField.YEAR),
                                         today.get(ChronoField.MONTH_OF_YEAR),
                                         today.get(ChronoField.DAY_OF_MONTH));
        System.out.println("Today equals sameDate: " + today.equals(sameDate));
    }
}

此示例演示了各种比较 HijrahDate 对象的方法。比较方法考虑了完整的日期。请注意,相等性要求所有日期组件完全匹配。

添加和减去时间

HijrahDate 通过 plusminus 方法支持时间算术。这些操作考虑了伊斯兰历中月份长度的变化。该类处理月和年的边界。

Main.java
package com.zetcode;

import java.time.chrono.HijrahDate;
import java.time.temporal.ChronoUnit;

public class Main {

    public static void main(String[] args) {

        HijrahDate today = HijrahDate.now();
        
        // Add days
        HijrahDate in10Days = today.plus(10, ChronoUnit.DAYS);
        System.out.println("In 10 days: " + in10Days);
        
        // Add months
        HijrahDate in2Months = today.plus(2, ChronoUnit.MONTHS);
        System.out.println("In 2 months: " + in2Months);
        
        // Add years
        HijrahDate nextYear = today.plus(1, ChronoUnit.YEARS);
        System.out.println("Next year: " + nextYear);
        
        // Subtract weeks
        HijrahDate twoWeeksAgo = today.minus(2, ChronoUnit.WEEKS);
        System.out.println("Two weeks ago: " + twoWeeksAgo);
    }
}

此示例展示了使用 HijrahDate 执行日期算术的各种方法。操作考虑了伊斯兰历的特点。在希吉里历中,月份长度在 29 到 30 天之间变化。

在日历系统之间转换

HijrahDate 可以转换为其他历法系统,如公历,也可以从其他历法系统转换而来。当使用多个历法系统时,这些转换是必不可少的。

Main.java
package com.zetcode;

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

public class Main {

    public static void main(String[] args) {

        HijrahDate hijrahDate = HijrahDate.now();
        
        // Convert to LocalDate
        LocalDate gregorianDate = LocalDate.from(hijrahDate);
        System.out.println("Gregorian date: " + gregorianDate);
        
        // Convert back to HijrahDate
        HijrahDate backToHijri = HijrahDate.from(gregorianDate);
        System.out.println("Back to Hijri: " + backToHijri);
        
        // Formatting
        DateTimeFormatter formatter = DateTimeFormatter.ofPattern("dd MMMM yyyy G");
        String formatted = hijrahDate.format(formatter);
        System.out.println("Formatted: " + formatted);
    }
}

此示例演示了 HijrahDate 和 LocalDate 之间的转换。格式化示例显示了如何以自定义模式显示日期。所有转换都保持在同一时间点。

处理月份长度

希吉里历的月份长度各不相同。lengthOfMonthlengthOfYear 方法有助于处理这些变化。

Main.java
package com.zetcode;

import java.time.chrono.HijrahDate;

public class Main {

    public static void main(String[] args) {

        HijrahDate date1 = HijrahDate.of(1445, 1, 1);
        System.out.println("Month length for 1445-1: " + date1.lengthOfMonth());
        
        HijrahDate date2 = HijrahDate.of(1445, 2, 1);
        System.out.println("Month length for 1445-2: " + date2.lengthOfMonth());
        
        HijrahDate date3 = HijrahDate.of(1445, 12, 1);
        System.out.println("Month length for 1445-12: " + date3.lengthOfMonth());
        
        System.out.println("Year length for 1445: " + date1.lengthOfYear());
        
        // Check if year is leap (Hijri calendar doesn't have leap years)
        System.out.println("Is leap year: " + date1.isLeapYear());
    }
}

此示例展示了如何在希吉里历中处理月和年的长度。与公历不同,伊斯兰历没有闰年。月份长度由月相周期决定。

来源

Java HijrahDate 类文档

在本文中,我们介绍了 Java HijrahDate 类的基本方法和功能。理解这些概念对于在 Java 应用程序中使用伊斯兰日期至关重要。

作者

我的名字是 Jan Bodnar,是一位经验丰富的程序员,在这个领域拥有多年的经验。我从 2007 年开始撰写编程文章,至今已撰写了 1400 多篇文章和 8 本电子书。凭借超过八年的教学经验,我致力于分享我的知识并帮助他人掌握编程概念。

列出所有Java教程