计算给定年份的滴答声(数学方法)

时间:2018-07-26 20:18:17

标签: c# .net-core

我一直在尝试使用以下公式将给定的日期转换为刻度,由于我刚刚开始编写此函数,因此我尚未考虑monthday的值:

public static long DateToTicks(int year, int month, int day) {
     var leapYears = (year - 1) / 4;
     var result = ((year - 1) * 365 * OneDay.Ticks) + (leapYears * OneDay.Ticks);
     return result;
}

OneDay.Ticks是一个常量,其值为3600 * 24 * 1000 * 10000

我所面临的问题是,当我从零天(即0001-01-01、0002-01-01)开始计算滴答声时,它可以正常工作,直到我到达101年,再获得一天!我将结果与DateTime.Net Core结构返回的值进行比较。例如:

var myResult = DateToTicks(100, 01, 01);
var dateTimeResult = new DateTime(100,01,01).Ticks;

在此日期之前,myResult == dateTimeResult始终为真,但是当我进入下一个世纪时,我看到DateTime struct返回的结果落后一天,而当我进入下一个世纪时,该值将翻倍。

但是,我知道在101年中,有25个leap年,这意味着我必须将75年乘以365,其余的乘以366,然后将它们相加,我不明白为什么我的结果与点网的DateTime结果不同。

我的方法有什么问题?鉴于该日期和日期并不重要(始终设置为01)。

3 个答案:

答案 0 :(得分:2)

因为您似乎不想看C#代码。我在那儿找你-花了我1分钟时间

    private static long DateToTicks(int year, int month, int day) {     
        if (year >= 1 && year <= 9999 && month >= 1 && month <= 12) {
            int[] days = IsLeapYear(year)? DaysToMonth366: DaysToMonth365;
            if (day >= 1 && day <= days[month] - days[month - 1]) {
                int y = year - 1;
                int n = y * 365 + y / 4 - y / 100 + y / 400 + days[month - 1] + day - 1;
                return n * TicksPerDay;
            }
        }
        throw new ArgumentOutOfRangeException(null, Environment.GetResourceString("ArgumentOutOfRange_BadYearMonthDay"));
    }

   public static bool IsLeapYear(int year) {
        if (year < 1 || year > 9999) {
            throw new ArgumentOutOfRangeException("year", Environment.GetResourceString("ArgumentOutOfRange_Year"));
        }
        Contract.EndContractBlock();
        return year % 4 == 0 && (year % 100 != 0 || year % 400 == 0);
    }

这是直接链接

https://referencesource.microsoft.com/#mscorlib/system/datetime.cs,891f8af5025ab2f3

答案 1 :(得分:0)

将您的leap年计算逻辑更改为此,即可正常工作:

var leapYears = ((year - 1) / 4) - (year / 400 > 0 ? ((year) / 100) - (((year) / 400)) : ((year - 1) / 100)) + (year % 100 == 0 && year % 400 != 0 ? 1 : 0) + (year == 100 || year == 200 || year == 300 ? -1 : 0);

答案 2 :(得分:-1)

简单地除以4并不是确定a年的正确方法。

这是测试for年的一种方法:

  

年份可以平均除以4;

     

如果年份可以除以100,则不是NOT年,除非;

     

该年份也可以平均除以400。然后是a年。

因此,1900年不是a年,而2000年是a年。