列表推导式处理JSON日期数组的日期格式冲突解决问询
解决列表推导式中字符串与datetime.date的格式冲突及代码优化建议
核心问题解决
报错TypeError: '<' not supported between instances of 'str' and 'datetime.date'的本质是:title["date"]是字符串格式(如"2022-09-19"),而sdate/edate是datetime.date对象,两者无法直接比较。同时原代码的条件逻辑完全颠倒(找小于月初且大于月末的日期,不可能匹配到任何结果),需要同时修正格式和逻辑。
正确的列表推导式写法:
hols = [ event["title"] for event in ukHolidaysJSON if sdate <= datetime.strptime(event["date"], "%Y-%m-%d").date() <= edate ]
解释:
- 用
datetime.strptime(event["date"], "%Y-%m-%d")把字符串日期转成datetime对象,再调用.date()得到date类型,和sdate/edate类型统一后即可正常比较。 - 修正条件为
sdate <= ... <= edate,筛选出当月的公共假期。
代码优化建议
- 清理无用导入:去掉
import inspect、from turtle import title、from typing import Iterator、import print(print是Python内置函数,无需导入),减少冗余。 - 简化公共假期列表生成:原循环手动维护
eventIterator的写法可以用列表推导式一行完成:ukHolidayList = [event["date"] for event in ukHolidaysJSON] - 合并重复循环:原代码用两个独立循环遍历当月日期,可合并为一个循环减少重复计算:
numberOfWorkingDays = 0 numberOfHolidays = 0 for i in range(delta.days + 1): day = sdate + timedelta(days=i) day_str = str(day) is_holiday = day_str in ukHolidayList if is_holiday: numberOfHolidays += 1 elif np.is_busday([day]): print(f"- {day}") numberOfWorkingDays += 1 - 补全月份名称映射:原代码
months变量未定义,需提前定义月份字典:months = { "1": "January", "2": "February", "3": "March", "4": "April", "5": "May", "6": "June", "7": "July", "8": "August", "9": "September", "10": "October", "11": "November", "12": "December" } month = months[monthInput.lstrip('0')] - 改用生成器生成日期范围:用生成器表达式替代循环生成日期,代码更简洁:
date_range = (sdate + timedelta(days=i) for i in range(delta.days + 1)) for day in date_range: # 后续逻辑不变
优化后完整代码
from datetime import date, timedelta, datetime import numpy as np import json import requests from calendar import monthrange # 定义月份名称映射 months = { "1": "January", "2": "February", "3": "March", "4": "April", "5": "May", "6": "June", "7": "July", "8": "August", "9": "September", "10": "October", "11": "November", "12": "December" } # 测试用输入(可改为用户输入) monthInput = "09" yearInput = "2022" # 获取英格兰和威尔士公共假期数据 holidays_response = requests.get("https://www.gov.uk/bank-holidays.json") uk_holidays = json.loads(holidays_response.text)['england-and-wales']['events'] # 生成公共假期日期字符串列表 uk_holiday_dates = [event["date"] for event in uk_holidays] # 计算当月天数及起止日期 year = int(yearInput) month = int(monthInput) days_in_month = monthrange(year, month)[1] sdate = date(year, month, 1) edate = date(year, month, days_in_month) # 统计工作日与假期数 number_of_working_days = 0 number_of_holidays = 0 date_range = (sdate + timedelta(days=i) for i in range(days_in_month)) for day in date_range: day_str = str(day) is_holiday = day_str in uk_holiday_dates if is_holiday: number_of_holidays += 1 elif np.is_busday([day]): print(f"- {day}") number_of_working_days += 1 # 获取月份名称 month_name = months[monthInput.lstrip('0')] # 筛选当月公共假期名称 current_month_holidays = [ event["title"] for event in uk_holidays if sdate <= datetime.strptime(event["date"], "%Y-%m-%d").date() <= edate ] print(f"\n{month_name} {year} 工作日总数: {number_of_working_days}") print(f"{month_name} {year} 公共假期总数: {number_of_holidays}") print(f"{month_name} {year} 公共假期列表: {current_month_holidays}")
内容的提问来源于stack exchange,提问作者Steven Diffey
相关产品推荐
相关产品推荐

