1185. 一周中的第几天

1185. 一周中的第几天

给你一个日期,请你设计一个算法来判断它是对应一周中的哪一天。

输入为三个整数:day、month 和 year,分别表示日、月、年。

您返回的结果必须是这几个值中的一个 {“Sunday”, “Monday”, “Tuesday”, “Wednesday”, “Thursday”, “Friday”, “Saturday”}。

示例 1:

输入:day = 31, month = 8, year = 2019
输出:"Saturday"

示例 2:

输入:day = 18, month = 7, year = 1999
输出:"Sunday"

示例 3:

输入:day = 15, month = 8, year = 1993
输出:"Sunday"

提示:

  • 给出的日期一定是在 1971 到 2100 年之间的有效日期。

解题思路:
leetcode连续三天模拟题,这题模拟获取输入天数到1971年1月1日的天数即可计算出星期几了。
代码:

char * dayOfTheWeek(int day, int month, int year){
    char* weeks[7] = {"Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"};
    int days = 0;
    int month_day[12] = {31,28,31,30,31,30,31,31,30,31,30,31};
    for(int i = 1971; i < year; i++)
    {
        if(isleapyear(i))
            days += 366;
        else
            days += 365;
    }
    for(int i = 0; i < month - 1; i++)
    {
        if(i == 1 && isleapyear(year))  days++;
        days += month_day[i];
    }
    days += day;
    return weeks[(3 + days)%7];

}

int isleapyear(int year)
{
    if((year %4 == 0 && year % 100 != 0) || year % 400 ==0) return 1;
    return 0;
}

时间复杂度: O(year + month + 1)
空间复杂度: O( C )
解题方式2:
蔡勒公式
公式中的符号含义如下:
w = ( y + [ y 4 ] + [ c 4 ] − 2 c + [ 26 ( m + 1 ) 10 ] + d − 1 )   m o d   7 {\displaystyle w=\left(y+\left[{\frac {y}{4}}\right]+\left[{\frac {c}{4}}\right]-2c+\left[{\frac {26(m+1)}{10}}\right]+d-1\right){\bmod {7}}} w=(y+[4y]+[4c]2c+[1026(m+1)]+d1)mod7
or
w = ( y + [ y 4 ] + [ c 4 ] − 2 c + 2 m + [ 3 ( m + 1 ) 5 ] + d + 1 )   m o d   7 {\displaystyle w=\left(y+\left[{\frac {y}{4}}\right]+\left[{\frac {c}{4}}\right]-2c+2m+\left[{\frac {3(m+1)}{5}}\right]+d+1\right){\bmod {7}}} w=(y+[4y]+[4c]2c+2m+[53(m+1)]+d+1)mod7

w:星期(计算所得的数值对应的星期:0-星期日;1-星期一;2-星期二;3-星期三;4-星期四;5-星期五;6-星期六)[注 1]
c:年份前两位数
y:年份后两位数
m:月(m的取值范围为3至14,即在蔡勒公式中,某年的1、2月要看作上一年的13、14月来计算,比如2003年1月1日要看作2002年的13月1日来计算)
d:日
[ ]:称作高斯符号,代表向下取整,即,取不大于原数的最大整数。
mod:同余(这里代表括号里的答案除以7后的余数)
因为
( y + [ y 4 ] + [ c 4 ] − 2 c + [ 26 ( m + 1 ) 10 ] + d − 1 ) {\displaystyle \left(y+[{\frac {y}{4}}]+[{\frac {c}{4}}]-2c+[{\frac {26(m+1)}{10}}]+d-1\right)} (y+[4y]+[4c]2c+[1026(m+1)]+d1)
可能为负数,所以当出现负数的情况下不能直接mod 7。编写成代码的时候如果两个操作数中只有一个负数,求模的结果取决于机器,也就是说某些情况下w在一些机器上为负数,但是在某一些机器上w不一定为负数(例如:21%-5的结果取决于机器,可能得到1或-4),对于产生负数这种情况可将原来公式分为两步:
w = ( y + [ y 4 ] + [ c 4 ] − 2 c + [ 26 ( m + 1 ) 10 ] + d − 1 ) {\displaystyle w=\left(y+[{\frac {y}{4}}]+[{\frac {c}{4}}]-2c+[{\frac {26(m+1)}{10}}]+d-1\right)} w=(y+[4y]+[4c]2c+[1026(m+1)]+d1)
w = ( w % 7 + 7 ) % 7 {\displaystyle w=(w\%7+7)\%7} w=(w%7+7)%7
若为一月二月,则看作为去年的13月和14月输入,同时在年份上减一。以上各式中的“%”符号表示取余运算。
摘自维基百科
代码实现:

char * dayOfTheWeek(int day, int month, int year){
    char* a[7] = {"Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"};
    if (month == 1) {
        month = 13;
        year--;
    }
    if (month == 2) {
        month = 14;
        year--;
    }
    int y = year % 100;
    int c = year / 100;
    int week = (y + y/4 + c/4 - 2*c + 26*(month+1)/10 + day - 1) % 7;
    week = (week%7 + 7) % 7;
    return a[week];
}

时间复杂度: O(1)
空间复杂度: O(1)

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值