如何更改日期字符串格式(2052年10月20日-> 2052-10-20)

时间:2019-01-22 13:16:45

标签: python date

  

Blockquote

我有一个日期字符串,格式为Day Month Year,例如1984年3月1日,1973年4月4日,2006年5月22日,其中:

日期位于{“ 1st”,“ 2nd”,“ 3rd”,...,'“ 30th”,“ 31st”}的集合中

月份在集合{“ Jan”,“ Feb”,“ Mar”,...,“ Dec”}中

年份在[1900,2100]范围内

我必须将日期字符串转换为YYYY-MM-DD格式,例如: 1984年3月1日-> 1984-03-01 1973年4月4日-> 1973-04-04

(函数ReformatDate具有以下参数: date [dates [0],...,dates [n-1]]是日期字符串数组,格式为Day Month Year)

样本输入 4 2052年10月20日 1933年6月6日 1960年5月26日 1958年9月20日

示例输出 2052-10-20 1933-06-06 1960-05-26 1958-09-20

enter code here
    def reformatDate(dates):
    # write your code here
    if __name__ == '__main__':
        fptr = open(os.environ['OUTPUT_PATH'], 'w')
        dates_count = int(input().strip())
        dates = []
        for _ in range(dates_count):
            dates.item = input()
            dates.append(dates_item)       
        result = reformatDate(dates)
        fptr.write('\n'.join(result))
        fptr.write('\n')
        fptr.close

5 个答案:

答案 0 :(得分:0)

这是一种针对您的案例的临时解决方案。您可以通过将自己的月份名称传递给数字映射来避免使用日历包。不过,可能还有更多通用和pythonic解决方案。

import calendar 

def reformatDate(dates):
    output_dates = []
    for date in output_dates:
        fields = date.split()
        day = fields[0][:-2]
        month = str(list(calendar.month_abbr).index(fields[1]))
        year = fields[2]
        output_date = year + "-" + month + "-" + day
        output_dates.append(output_date)
    return output_dates

答案 1 :(得分:0)

这是使用datetime模块的一种方法。

例如:

import datetime
import re    

lst = ["20th Oct 2052", "6th Jun 1933", "26th May 1960", "20th Sep 1958"]
for i in lst:
    print(datetime.datetime.strptime(re.sub(r"(st|th|rd)", "", i), "%d %b %Y").strftime("%Y-%m-%d"))

输出:

2052-10-20
1933-06-06
1960-05-26
1958-09-20

注意:re.sub(r"(st|th|rd)", "", i)从日期中删除st,th,rd。

答案 2 :(得分:0)

您可以将lambda用于列表理解:

import re
lst = ["20th Oct 2052", "6th Jun 1933", "26th May 1960", "20th Sep 1958"]
m = ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec']
new_data = [(lambda x:f'{x[-1]}-{m.index(x[1])+1}-{x[0]}')(re.findall('\d+|\w{3,}', c)) for c in lst]

输出:

['2052-10-20', '1933-6-6', '1960-5-26', '1958-9-20']

答案 3 :(得分:0)

由于所有以前的答案都使用输出模块(redatetimecalendar在标准Python库中,但仍然需要以这种方式导入),我写了一个内置python函数的解决方案。请毫不犹豫地提出改进建议:

#your input
d = ["20th Oct 2052", "6th Jun 1933", "26th May 1960", "20th Sep 1958"]
#first split the data
ds=[l.strip().split(" ") for l in d]
#then create a dictionary for month
month_dict={'Jan':'01', 'Feb':'02', 'Mar':'03', 'Apr':'04', 'May':'05', 'Jun':'06', 'Jul':'07', 'Aug':'08', 'Sep':'09', 'Oct':'10', 'Nov':'11', 'Dec':'12'}

#function to filter digits from a string.
#a strong advantage of filtering digits is that it doesn't matter whether or not days are written with st, nd or rd
def digit_from_string(x):
    s = ''.join(filter(str.isdigit, x))
    #in case only one digit was extracted (e.g., 2), add a 0 in front (e.g., 02)
    if len(s) == 1:
        s='0'+s
    return s

#iterates on the splitted data; v[0] corresponds to the day, v[1] the month and v[2] the year
ds=[{'day': digit_from_string(v[0]),
    'month': digit_from_string(month_dict[v[1]]),
    'year': digit_from_string(v[2])}
   for v in ds]

#format the output
output=['{0}-{1}-{2}'.format(x['year'],x['month'],x['day']) for x in ds]

输出:

['2052-10-20', '1933-06-06', '1960-05-26', '1958-09-20']

答案 4 :(得分:0)

您写道:

  

如果可能,我宁愿不使用外部模块

在注释中,但是datetimecalendar是标准库的一部分,而不是外部模块!也就是说:这些模块是Python语言的一部分,就像整数,循环,函数和类一样。 (嗯……差不多:请参见Is the Python standard library really standard?Which parts of the python standard library are guaranteed to be available?。)记住这一点:

  

Python具有“包括电池”的理念。 ( Guido van Rossum https://docs.python.org/3/tutorial/stdlib.html#batteries-included

您不应尝试避免使用标准库,而应学习如何使用它。

如果您仍然希望自己尝试进行此操作,则可以使用通常的单线:

>>> date_strings = ["20th Oct 2052", "6th Jun 1933", "26th May 1960", "20th Sep 1958"]
>>> month_names = ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec']
>>> ["{:0>4}-{:0>2}-{:0>2}".format(y, month_names.index(m)+1, d.rstrip("stnrdh")) for d,m,y in map(str.split, date_strings)]
['2052-10-20', '1933-06-06', '1960-05-26', '1958-09-20']

说明:

  • 格式{:0>4}表示:数字和字符串的宽度应为4,右对齐(>),并用0 s填充(请参阅:{{3 }}。
  • month_names.index(m)+1是该月份的数字(如果未知月份则失败)
  • d.rstrip("stnrdh")仅清除日期数字的后缀(“ st”,“ nd”,“ rd”,“ th”)
  • map(str.split, date_strings)将日期分为三部分(天,月,年)。

请注意,如果输入无效,此代码将失败。换句话说,除非输入经过验证,否则我不会依赖此代码。