反转Django的自然时间的结果
Reversing the result of Django's naturaltime
Django 的 humanize
模块非常适合将 datetime
对象变成对我们人类更有意义的东西,它具有 naturaltime
功能 (docs)。我想做的是相反,采用任何一种 naturaltime
格式并将其转换回 datetime
(接受明显的精度损失)。
是否有任何现有的库可以执行此操作,或者我是否必须编写自己的 datetime.strptime
模式?
我知道这是一个有点 "find me a tool/library" 的问题,但我在谷歌上搜索了很多但没有结果。
对于任何未来的搜索者,我最终写了 dehumanize
来处理这个问题。在 github here.
from datetime import datetime, timedelta
import re
def naturaltime(text, now=None):
"""Convert a django naturaltime string to a datetime object."""
if not now:
now = datetime.now()
if text == 'now':
return now
if "ago" in text:
multiplier = -1
elif "from now" in text:
multiplier = 1
else:
raise ValueError("%s is not a valid naturaltime" % text)
text = text.replace('an ', '1 ')
text = text.replace('a ', '1 ')
days = get_first(r'(\d*) day', text)
hours = get_first(r'(\d*) hour', text)
minutes = get_first(r'(\d*) minute', text)
seconds = get_first(r'(\d*) second', text)
delta = timedelta(days=days, hours=hours, minutes=minutes, seconds=seconds)
delta *= multiplier
return now + delta
def get_first(pattern, text):
"""Return either a matched number or 0."""
matches = re.findall(pattern, text)
if matches:
return int(matches[0])
else:
return 0
Django 的 humanize
模块非常适合将 datetime
对象变成对我们人类更有意义的东西,它具有 naturaltime
功能 (docs)。我想做的是相反,采用任何一种 naturaltime
格式并将其转换回 datetime
(接受明显的精度损失)。
是否有任何现有的库可以执行此操作,或者我是否必须编写自己的 datetime.strptime
模式?
我知道这是一个有点 "find me a tool/library" 的问题,但我在谷歌上搜索了很多但没有结果。
对于任何未来的搜索者,我最终写了 dehumanize
来处理这个问题。在 github here.
from datetime import datetime, timedelta
import re
def naturaltime(text, now=None):
"""Convert a django naturaltime string to a datetime object."""
if not now:
now = datetime.now()
if text == 'now':
return now
if "ago" in text:
multiplier = -1
elif "from now" in text:
multiplier = 1
else:
raise ValueError("%s is not a valid naturaltime" % text)
text = text.replace('an ', '1 ')
text = text.replace('a ', '1 ')
days = get_first(r'(\d*) day', text)
hours = get_first(r'(\d*) hour', text)
minutes = get_first(r'(\d*) minute', text)
seconds = get_first(r'(\d*) second', text)
delta = timedelta(days=days, hours=hours, minutes=minutes, seconds=seconds)
delta *= multiplier
return now + delta
def get_first(pattern, text):
"""Return either a matched number or 0."""
matches = re.findall(pattern, text)
if matches:
return int(matches[0])
else:
return 0