从日期时间等距获取有冲突的信息

时间:2018-10-15 20:58:32

标签: python

我有一个列表,列出了给定年份的工作日(周一至周日为1-7)和星期数。我需要将该信息转换为给定日期。

因此,我编写了一个简单的脚本,该脚本包含三个参数: 1年 2.平日 3.周数

然后找出日期。

我的脚本基本上在给定年份的所有日期中进行迭代,并创建一个datetime对象,然后在其中提取isocalendar()[1]以将其与周数进行比较。

我发现如果输入2017 7 52,我将得到两个输出!

这是最基本的本质:

#!/Library/Frameworks/Python.framework/Versions/3.7/bin/python3

import datetime

def print_dt(year, month, day):
    dt = datetime.date(year, month, day)
    print("%d-%d-%d (%d) -> week# %d" % (year, month, day, dt.weekday(), dt.isocalendar()[1]))

print_dt(2017, 1, 1)
print_dt(2017, 12, 31)

与输出相同:

Anibals-iMac:RPEG anibal$ ./findDate-fixed-date.py
2017-1-1 (6) -> week# 52
2017-12-31 (6) -> week# 52

那怎么可能?这意味着2017年的第52周有两天的第六天,即两个不同的星期日。这种情况导致我的脚本出现问题。

关于如何解决这个问题的任何想法?

我最初的问题是,我在YYYYMMDD中给出了事件,因此我需要按年份将它们按年分组。因此,我可以说X的事件发生在2017年的第4周。在上面的情况下,直到第52周都不起作用,因为有一种以上的YYYYMMDD解决方案。

1 个答案:

答案 0 :(得分:0)

您正在混合使用ISO日历年和公历日历年。

日期2017-1-1是ISO日历中2016年第52周的第7天。

ISO日历将ISO日历年的第一周定义为包含相应格里高利历年的第一个星期四的周。 1月1日至7日可能在任何地方。由于ISO用星期一= 1到星期日= 7的天数,这意味着在每个新年前后最多三天,公历日期和ISO日历年不一致。

2015年1月1日是星期四,因此,尽管在2014年12月,星期一,星期二和星期三才具有2015年ISO日历年。类似地,2016年1月7日是星期四,星期五是1月1日至2016年1月3日星期日。尽管在2016年,但ISO日历年为2015。

您的脚本似乎在阳历中度过了一年,在整个阳历年中的所有日期中进行迭代,并寻找与星期几和ISO周号相匹配的日期。您发现的是,这三个值(格里高利年份,ISO周编号ISO周几)不能唯一地标识日期。您的脚本需要考虑以下事实:ISO日历年和公历日历年并不总是在ISO日历年而不是公历日历年上达成一致和匹配。一种方法是:

  • 在您搜索的日期范围内,包括上一个公历年的最后三天和下一个公历年的前三天,并且
  • 以及匹配ISO周号和ISO星期几,请确保ISO年也匹配。 ISO年份在dt.isocalendar()[0]中。

或者,您也可以完全避免使用ISO日历系统,而可以考虑以下内容:

def get_week_and_day(year, month, day):
    wday_of_jan_1 = datetime.date(year, 1, 1).timetuple().tm_wday
    daytuple = datetime.date(year, month, day).timetuple()
    wday = daytuple.tm_wday
    week = (daytuple.tm_yday - 1 + wday_of_jan_1) // 7 + 1
    return (week, wday)

鉴于每年,每月和每天,这将返回一年中的某周和一周中的某天,其中几周从星期一开始(根据time.struct_time),而第1周是一月的一周1个星期进入。星期通常最多增加53个星期,但是如果a年的12月31日是星期一(与2012年一样),则这一天将是第54周。

这可以通过使用date.timetuple()方法来获取日期中的工作日和日期,以及该年1月1日的星期几来实现。在week的计算中,我们:

  • 从给定日期的一年中的某天(daytuple.tm_yday减去1,因此1月1日为0,1月2日为1,依此类推。< / li>
  • 在此添加1月1日的星期几。我们这样做是因为1月1日的星期几也是一年中第一周丢失的天数到上一年。例如,如果1月1日是星期三,则wday_of_jan_1将是2,则从第1周开始的周一和周二将丢失,因此第一周将只有5天。
  • 到目前为止,计算得出的结果是给定日期与1月1日或之前的第一个星期一之间的天数。然后我们可以将其除以7,得到自本周一以来的整周数,最后加1,这样1月1日位于第1周,而不是第0周。

这种方法还避免了循环计算全年的日期并对其进行计算。