我有一个pandas数据框,文字属性为
loc_id text
1 'Monday: 8:30 AM \x96 5:30 PM,Tuesday: 8:30 AM \x96 5:30 PM,Wednesday: 8:30 AM \x96 5:30 PM,Thursday: 8:30 AM \x96 5:30 PM,Friday: 8:30 AM \x96 5:30 PM,Saturday: Closed,Sunday: Closed'
2 ''
3 'Monday: Open 24 hours,Tuesday: Open 24 hours,Wednesday: Open 24 hours,Thursday: Open 24 hours,Friday: Open 24 hours,Saturday: Open 24 hours,Sunday: Open 24 hours
它是一个文本数据,我想计算它打开时的总开放时间
loc_id openingHours
1 45
2 NAN
3 168
我是文本挖掘的新手,所以不知道如何解析和转换它。文本只提到了这两种格式。
答案 0 :(得分:1)
我认为您需要一些自然语言日期解析器,例如dateparser:
dateparser提供了几乎可以轻松解析本地化日期的模块 网页上常见的任何字符串格式。
- 以英语,西班牙语,荷兰语,俄语和20多种其他语言对日期进行通用解析,以及与语言无关的多种格式 方式。
- 相关日期的通用解析,例如:'1分钟前','2周前','3个月,1周和1天前','2天','明天'。
- 具有时区缩写或UTC偏移的日期的一般解析,例如:'2015年8月14日美国东部时间','2013年7月4日太平洋标准时间',2013年7月21日 晚上10:15 +0500'。
- 支持非公历日历系统。请参阅支持的日历。
- 广泛的测试覆盖率。
如果你需要解析它,那么就像@asongtoruin所提议的那样,你必须使用正则表达式:
import re
opened_str = 'Monday: 8:30 AM \x96 5:30 PM,Tuesday: 8:30 AM \x96 5:30 PM,Wednesday: 8:30 AM \x96 5:30 PM,Thursday: 8:30 AM \x96 5:30 PM,Friday: 8:30 AM \x96 5:30 PM,Saturday: Closed,Sunday: Closed'
PARSE_RE = re.compile(r'(?P<DAY>Monday|Tuesday|Wednesday|Thursday|Friday|Saturday|Sunday): (?P<WORKHOURS>(?P<OPEN>\d+:\d+ (:?AM|PM)) \x96 (?P<CLOSE>\d+:\d+ (:?AM|PM))|Closed|Open 24 hours)')
for item in PARSE_RE.findall(opened_str):
print(item)
将打印:
('Monday', '8:30 AM \x96 5:30 PM', '8:30 AM', 'AM', '5:30 PM', 'PM')
('Tuesday', '8:30 AM \x96 5:30 PM', '8:30 AM', 'AM', '5:30 PM', 'PM')
('Wednesday', '8:30 AM \x96 5:30 PM', '8:30 AM', 'AM', '5:30 PM', 'PM')
('Thursday', '8:30 AM \x96 5:30 PM', '8:30 AM', 'AM', '5:30 PM', 'PM')
('Friday', '8:30 AM \x96 5:30 PM', '8:30 AM', 'AM', '5:30 PM', 'PM')
('Saturday', 'Closed', '', '', '', '')
('Sunday', 'Closed', '', '', '', '')
因此,您可以检查每个元组的第二和第三索引的开启/关闭时间,或者 1st ,如果它已关闭。之后,您可以根据自己的喜好解析这些日期。
答案 1 :(得分:1)
这是针对您的问题的工作解决方案!
下面给出的解释。
import re
from datetime import datetime
sumtime = 0
sumlist=[]
list_of_strings = ['''Monday: 8:30 AM \x96 5:30 PM,Tuesday: 8:30 AM \x96 5:30 PM,Wednesday: 8:30 AM \x96 5:30 PM,Thursday: 8:30 AM
\x96 5:30 PM,Friday: 8:30 AM \x96 5:30 PM,Saturday: Closed,Sunday: Closed''','''Monday: Open 24 hours,Tuesday: Open 24 hours,Wednesday: Open
24 hours,Thursday: Open 24 hours,Friday: Open 24 hours,Saturday: Open 24 hours,Sunday: Open 24 hours''']
for s in list_of_strings: #Text for each loc_id
if 'Open' not in s:
#If the word 'Open' isn't present in the text then do below
times = [line[0] for line in re.findall(r'\b((1[0-2]|0?[1-9]):([0-5][0-9]) ([AaPp][Mm]))',s)]
times = [[i,j] for i,j in zip(times[0::2], times[1::2])]
fmt = '%I:%M %p'
time_objects = [datetime.strptime(b,fmt)-datetime.strptime(a,fmt)
for a,b in times]
finaltime = [td.seconds//3600 for td in time_objects]
sumtime=sum(finaltime)
sumlist.append(sumtime)
else:
#If Open is present in the text
open_times = [int(st) for st in s.split() if st.isdigit()]
sumlist.append(sum(open_times))
print(sumlist)
1) re.findall 返回字符串中找到的每个匹配项。它的输出将是这样的
[('8:30 AM', '8', '30', 'AM'),('5:30 PM', '5', '30', 'PM'), ('8:30 AM', '8', '30', 'AM')]
因此,行[0]将从元组中给出第一个。即'8:30 AM',我们需要
[line[0] for line in re.findall(r'\b((1[0-2]|0?[1-9]):([0-5][0-9]) ([AaPp][Mm]))',s)]
2)以上的输出将是
['8:30 AM', '5:30 PM', '8:30 AM', '5:30 PM', '8:30 AM', '5:30 PM', '8:30 AM', '5:30 PM', '8:30 AM', '5:30 PM']
3)现在列表中的每个偶数元素(0,2,4,...)将与奇数元素(1,3,5,...)配对。注意时间[0 :: 2]这里给出了一个元素列表,从索引0 开始,每个索引递增 2 。同样从索引1 开始 递增 2 。将它们压缩在一起。你明白了,
[['8:30 AM', '5:30 PM'], ['8:30 AM', '5:30 PM'],...and so on]
times = [[i,j] for i,j in zip(times[0::2], times[1::2])]
4)fmt是格式 fmt = '%I:%M %p'
。请注意,它将是%H:%M,但因为我们使用的是%p
文件明确规定,在这种情况下,我们应该%I而不是%H。否则%H就好了。在我们的a,b [8:30 AM', '5:30 PM']
上使用 datetime.strptime 来获取日期时间对象。减去它们以获得 timedelta 对象。使用timdelta_object.seconds
将其转换为秒。
[datetime.strptime(b,fmt)-datetime.strptime(a,fmt) for a,b in times]
然后,您可以使用td.days
获取日期,td//3600
获取时间
5)使用sum(your_list)
查找此列表的总和,以获得您的案例中 45 的总和。将其附加到列表中。
6)如果文字中有 Open 这个词,
然后从文本中单独获取数字作为int并找到它们的总和。
7)最后输出列表将是
[45, 168]
这是解决您手头问题的有效方法。假设您以这种格式获得文本
'Monday: 8:30 AM \x96 5:30 PM,Tuesday: 8:30 AM \x96 5:30 PM,Wednesday: 8:30 AM \x96 5:30 PM,Thursday: 8:30 AM \x96 5:30 PM,Friday: 8:30 AM \x96 5:30 PM,Saturday: Closed,Sunday: Closed'
或此格式
'Monday: Open 24 hours,Tuesday: Open 24 hours,Wednesday: Open 24 hours,Thursday: Open 24 hours,Friday: Open 24 hours,Saturday: Open 24 hours,Sunday: Open 24 hours'
同时请务必查看dateparser