Как преобразовать григорианскую дату в исламскую (хиджра) без времени? - PullRequest
3 голосов
/ 21 апреля 2019

См. SO 15728744 и SO 51058875 .

Как может быть правильным следующее:

LocalDate gregorianDate = LocalDate.parse(gregorianString, dateFormatter);
HijrahDate islamicDate = HijrahDate.from(gregorianDate);

Я думал, что день хиджры заканчивается в закат , а не * полночь , поэтому должен был потребоваться gregorianDateTime.

Ответы [ 2 ]

2 голосов
/ 26 мая 2019

Вы правы, что календарь хиджр начинается в дни заката в предыдущий западный день.Вы также правы, говоря, что стандартная Java не поддерживает его.

Почему?

Я искал в старых архивах Threeten, но ничего не нашел.Тем не менее, главный разработчик и архитектор java.time -API однажды заявил в документации предка Joda-Time следующее предложение:

Эта реализация определяет день как полночьдо полуночи точно в соответствии с хронологией ISO.Это правильное начало дня на закате предыдущего дня, однако это не может быть легко смоделировано и было проигнорировано.

Мое предположение: та же мотивация также была ответственной, почему java.time не принимаетучитывать время суток в конверсиях в или из исламского календаря.Это трудно реализовать в основном потому, что для этого требуются астрономические вычисления.

Как справиться с этим недостатком?

В рамках стандартной Java пользователям рекомендуется игнорировать времядня как можно больше.Поэтому имейте в виду, что такие преобразования являются абстракциями без времени.Конечно, если вы хотите определить ТЕКУЩИЙ день (который косвенно включает время дня и гражданский часовой пояс), то такие преобразования более или менее ошибочны!

Если вы не хотите игнорироватьsunset как начало дня ...

... тогда вы можете использовать мою библиотеку Time4J (и я не знаю других библиотек, которые могут обрабатывать sunset как началодень).Следите за документацией класса HijriCalendar .Пример для общего преобразования от момента / момента к календарной дате хиджры:

// the geographic location
SolarTime meccaTime = SolarTime.ofLocation(21.4225, 39.826111); 
// or even simple: meccaTime = SolarTime.ofMecca()

// the moment to be converted
Moment now = SystemClock.currentTime();
// alternative using an explicit gregorian date:
//   now = PlainDate.of(2019, 5, 26).atTime(18, 45).inStdTimezone();
// alternative using modern Java: 
//   now = Moment.from(Instant.now());
// alternative using outdated old API: 
//   java.util.Date instant = new java.util.Date();
//   now = TemporalType.JAVA_UTIL_DATE.translate(instant);

// the conversion
HijriCalendar hcal = now.toGeneralTimestamp(
  HijriCalendar.family(),
  HijriCalendar.VARIANT_UMALQURA, // attention: there is no single islamic calendar
  Timezone.ofSystem().getID(), // or use something like: ()-> "Europe/London"
  StartOfDay.definedBy(meccaTime.sunset()));

Time4J также содержит механизм форматирования, который способен анализировать либо григорианские даты, либо дату календаря хиджры.раз во многих отношениях.Начало дня на закате можно также учитывать при форматировании и разборе на основе ChronoFormatter .

Также поддерживается обратное преобразование календарной даты Хиджры в момент.Пример:

HijriCalendar hcal = ...;
Moment m = 
  hcal.atTime(18, 45).in(Timezone.ofSystem(), StartOfDay.definedBy(meccaTime.sunset()));
0 голосов
/ 21 апреля 2019

В документации Java упоминается, что класс LocalDate не учитывает время.

См .: https://docs.oracle.com/javase/8/docs/api/java/time/LocalDate.html

Этот класс не хранит и не представляет время или часовой пояс.,Вместо этого это описание даты, используемое для дней рождения.

Рассмотрите возможность использования LocalDateTime для вашего требования.

...