iT邦幫忙

1

【小馬的LeetCode練功坊】曆法問題- 1154. Day of the Year, 1185. Day of the Week

今天分享在LeetCode上的歷法問題,
其實這類問題邏輯都不是很難,
只是因為每個月的天數不同,
加上有閏年的關係,
程式往往會不小心寫很長,
這邊分享自己研究精簡程式的寫法

1154. Day of the Year

參考題目: leetcode- 1154. Day of the Year
題意: 給你一組日期,判斷是一年之中的第幾天
範例:

Input: date = "2019-01-09"
Output: 9
說明: 1月9日是2019年的第9天

這題的技巧便是用一個陣列把每個月有幾天的資訊存下來,省下一堆if-else的判斷,
需注意若超過2月的狀況下,閏年需要再加1天,程式如下:

mdays = [0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31]

# 判斷閏年
def isLeap(n):
    return (n%4==0 and n%100!=0) or n%400==0

def dayOfYearII(year, month, day):
    return sum(mdays[:month])+day + (month>2 and isLeap(year))

class Solution:
    def dayOfYear(self, date: str) -> int:
        year, month, day = map(int, date.split('-'))
        return dayOfYearII(year, month, day)

1185. Day of the Week

參考題目: leetcode- 1185. Day of the Week
題意: 給你一組日期,判斷那天是星期幾
範例:

Input: day = 31, month = 8, year = 2019
Output: "Saturday

我的策略是這樣,首先我查到「西元1年1月1日是星期一」,
如果我能計算出這個日期距離西元1年1月1日過了幾天,
便可以把過去的天數除以7看餘數判斷是星期幾,程式如下:

mdays = [0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31]

def isLeap(n):
    return (n%4==0 and n%100!=0) or n%400==0

# 計算日期是從元年元月元日算起的幾幾天
def daysFromZeroYear(year, month, day):
    leaps = year//4-year//100+year//400 - (month<=2 and isLeap(year))
    return 365*(year-1) + sum(mdays[:month])+day + leaps

class Solution:
    def dayOfTheWeek(self, day: int, month: int, year: int) -> str:
        weekdays= ["Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"]
        return weekdays[daysFromZeroYear(year, month, day)%7]

補題: zerojudge- a263: 日期差幾天

參考題目: zerojudge- a263: 日期差幾天
這一題在zerojudge據說是難題,
題意: 給你兩組日期,判斷它們差幾天,
年份可能會跨很多年

不過我們做完leetcode的1185.題之後,
可以把想法拿來用,
直接算兩組日期的差距太難了,
但是把它拿去跟西元1年1月1日算差距是比較容易的,
把兩組日期各自去算跟西元1年1月1日差幾天,
再把兩個數字相減即可

mdays = [0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31]

def isLeap(n):
    return (n%4==0 and n%100!=0) or n%400==0

# 計算日期是從元年元月元日算起的幾幾天
def daysFromZeroYear(year, month, day):
    leaps = year//4-year//100+year//400 - (month<=2 and isLeap(year))
    return 365*(year-1) + sum(mdays[:month])+day + leaps

while True:
    try:
        y1, m1, d1 = map(int,input().split())
        y2, m2, d2 = map(int,input().split())
        print(abs(daysFromZeroYear(y1, m1, d1)-daysFromZeroYear(y2, m2, d2)))
    except: 
        break

尚未有邦友留言

立即登入留言