回历日期到公历日期是否有任何正确的转换器

Rez*_*dar 11 c# hijri

我参与了许多带有日期转换的项目。例如,我研究太阳历以及如何将它们转换为公历日期,反之亦然。太阳历(波斯历)在一年中的天数方面几乎与公历相似[闰与否]。
但我最近在做一个关于农历的项目。当我研究农历时,我意识到没有任何单一的逻辑方法可以将月球系统转换为太阳系(至少据我所知)。
以下是我研究过的一些参考链接:

  1. 无法从回历日期转换为公历日期 (c#)
  2. 将日期从回历转换为公历,反之亦然
  3. 回历日期到 gregorian 使用 DateTime.Parse
  4. 将回历日期转换为公历日期

当我按照上述链接进行训练和测试时,人们提出了算法,我注意到它们都不是绝对正确的。

可以这么说,只需将"1441/02/30" [Safar 30th]您想尝试的每种方法转换为公历日期即可。

下图对上述示例很有帮助。 在此处输入图片说明

我把我的一些测试代码放在这里,但失败了:

CultureInfo arSA = new CultureInfo("ar-SA");
arSA.DateTimeFormat.Calendar = new HijriCalendar();
var dateValue = DateTime.ParseExact("1441/02/30", "yyyy/MM/dd", arSA);
return dateValue.ToString();
Run Code Online (Sandbox Code Playgroud)

上述代码的错误:

日历 System.Globalization.HijriCalendar 不支持字符串表示的 DateTime。

HijriCalendar hc = new HijriCalendar();
DateTime date = new DateTime(1441, 2, 30, hc);
return date.ToString();
Run Code Online (Sandbox Code Playgroud)

上述代码的错误:

“第 2 个月的日必须介于 1 到 29 之间。”

string hijri = "1441/2/30";
HijriCalendar hc = new HijriCalendar();
int year = int.Parse(hijri.Substring(0, 4));
string rem = hijri.Remove(0, 5);
int end = rem.IndexOf('/', 0);
int month = int.Parse(rem.Substring(0, end));
rem = rem.Remove(0, end + 1);
int day = int.Parse(rem);
DateTime date = new DateTime(year, month, day, hc);
return date.ToShortDateString();
Run Code Online (Sandbox Code Playgroud)

上述代码的错误:

“第 2 个月的日必须介于 1 到 29 之间。”

在那之后,我试图了解是否有任何算法可以将回历日期转换为公历日期?
所以我测试了一些伊斯兰在线日期转换器,我很惊讶!
只需尝试"1441/2/30"在两个日期转换器上输入即可。
第一个返回October 30, 2019
第二个返回29 October 2019
Hijri gregorian-converter
伊斯兰日期转换器 - Gregorian Calendar Converter

所以我不知道是否有任何真正的算法可以将 Hijri 日期转换为 Gregorian 。
在此先感谢您的时间。

有关更多信息, 请访问 https://www.wikiwand.com/simple/Islamic_calendar


更新:我知道没有任何正确的库可供了解。但是如果有人对回历日历(所有界面)有知识或详细信息,请在此处描述我真的想为所有人部署回历日历。

Ali*_*idi 1

您可以使用类似此代码的代码将回历日历字符串转换并解析为公历日期时间。

//assuming current culture is like en-us or something with gregorian calendar
string hijri = "1441/2/30";
HijriCalendar hc = new HijriCalendar();
var dateParts = hijri.Split('/');
DateTime? gregorianDate=null;
if (dateParts.Length == 3 && int.TryParse(dateParts[0], out int year) &&
     int.TryParse(dateParts[1], out int month) && int.TryParse(dateParts[2], out int day))
{
      if(month == 2 && day==30)
      {
         var temp = hc.ToDateTime(year, month, 29, 0, 0, 0, 0);
         gregorianDate = temp.AddDays(1);
      }
      else
      {
         gregorianDate = hc.ToDateTime(year, month, day, 0, 0, 0, 0);
      }

}
Run Code Online (Sandbox Code Playgroud)