我的日期格式如下:
"1###-##-##" here # denote uncertainty. e.g.
"1###-##-##" denotes (1000-00-00 to 1999-12-31)
"-138 - ## - ##" denotes (0138-01-01 BC, 0138-12-31 BC)
"18##-##-##" denotes (1800-01-01, 1899-12-31)
"1713-##-##" denotes (1713-01-01, 1713-12-31)
"####-##-##" denotes (0001-01-01, 9999-12-31)
我试图通过使用特定的开关案例来实现这种转换,但结果并不高效。在python中是否还有其他一些方法可以实现这一目标?
以下零值转换为BC
编辑:我想要的输出给出一个类似“1 ### - ## - ##”的模式,找出最小和最大范围
答案 0 :(得分:4)
鉴于
dateranges = [
"1***-**-**",
"-138 - ## - ##",
"18##-##-##",
"1713-##-##",
"####-##-##"
]
你最好的解析器可能是re
,假设你不想这样做:
import re
matcher = re.compile("(-?[\d*#]+)\s*-\s*([\d*#][\d*#])\s*-\s*([\d*#][\d*#])")
datetuples = [matcher.match(daterange).groups() for daterange in dateranges]
然后你可以通过元组,
for year, month, day in datetuples:
将每个未知数转换为数字和上限。
minyear = int(year.replace("*", "0").replace("#", "0"))
minmonth = max(1, int(month.replace("*", "0").replace("#", "0")))
minday = max(1, int(day.replace("*", "0").replace("#", "0")))
mindate = (minyear, minmonth, minday)
maxyear = int(year.replace("*", "9").replace("#", "9"))
maxmonth = min(12, int(month.replace("*", "9").replace("#", "9")))
### WARNING! MAXIMUM DAY NUMBER DEPENDS ON BOTH MONTH AND YEAR
maxday = min(31, int(day.replace("*", "9").replace("#", "9")))
maxdate = (maxyear, maxmonth, maxday)
print(mindate, maxdate)
#>>> (1000, 1, 1) (1999, 12, 31)
#>>> (-138, 1, 1) (-138, 12, 31)
#>>> (1800, 1, 1) (1899, 12, 31)
#>>> (1713, 1, 1) (1713, 12, 31)
#>>> (0, 1, 1) (9999, 12, 31)
请记住,这会因为上限而接受误报,并牢记大胆的警告。
答案 1 :(得分:0)
如果我理解正确,您希望*表示从0到最大值的范围,而#表示从1到最大值的范围。此外,以破折号开头的日期位于BC。
这比你原来的方法更好吗?
def getdaterange(inputdate):
inputdate = inputdate.replace(' ', '')
maxdate = '9999-12-31'
zerodate = '0000-00-00'
onedate = '0001-01-01'
lowdate = list(inputdate)
highdate = list(inputdate)
for i, ch in enumerate(inputdate):
if ch == '*' or ch == '#':
highdate[i] = maxdate[i]
if ch == '*':
lowdate[i] = zerodate[i]
elif ch == '#':
lowdate[i] = onedate[i]
if inputdate[0] == '-':
lowdate[0], highdate[0] = '0', '0'
lowdate.append(' BC')
highdate.append(' BC')
return (''.join(lowdate), ''.join(highdate))
testins = ('1***-**-**', '-138 - ## - ##', '18##-##-##',
'1713-##-##', '####-##-##')
for i in testins:
print(getdaterange(i))
输出看起来正确。
('1000-00-00', '1999-12-31')
('0138-01-01 BC', '0138-12-31 BC')
('1801-01-01', '1899-12-31')
('1713-01-01', '1713-12-31')
('0001-01-01', '9999-12-31')
当然它不验证函数的输入。可能值得在开头添加一些正则表达式来验证输入是否是正确的形式。