python - 如何调整此正则表达式以在我的数据框中检测正确的日期格式?
问题描述
如果我有这个数据框:
df:
name dob
will 05-2020
John 4-2020
James 07-1999
Rob 2-2001
kim 1-20202020
Jane 112-2020
我想在以下条件下检测 dob 列中的日期(mm-yyyy):
- 年份不能超过 4 个字符(当然必须是 int)
- 月份可以是一位数或两位数(例如:02、2、12、11、10、9、09:都可以),但如果是两位数,则第一个字符只能是 0-1 和第二个 0-9
到目前为止,我有这个正则表达式:
r'\d{2}[-/]\d{4}'
但我没有得到我想要的结果。在我的条件下,我不应该在我的数据框中检测到 kim 或 jane。
有任何想法吗?
解决方案
我建议使用自定义数字边界((?<!\d)
lookbehind 和(?!\d)
lookahead)来确保您只匹配您选择的数字并确保您匹配年份,而不仅仅是 4 位数字,例如9873
带有(?:19|20)\d{2}
交替运算符 + 任何两位数字的非捕获组。天数可以与Jan 的答案中的(?:0?[1-9]|1[0-2])
模式匹配。
使用 提取日期后str.extract
,您可以使用 将它们转换为日期时间pd.to_datetime
。
使用.fillna()
,您可以处理不匹配的条目(我在下面的代码中将它们保留为空)。
正则表达式是
(?<!\d)((?:0?[1-9]|1[0-2])-(?:19|20)\d{2})(?!\d)
请参阅正则表达式演示。细节:
(?<!\d)
- 如果紧靠当前位置的左侧有一个数字,则匹配失败的负向后查找((?:0?[1-9]|1[0-2])-(?:19|20)\d{2})
- 捕获组 1(需要str.extract
):(?:0?[1-9]|1[0-2])
- 一个可选0
的数字,从to1
或9
then1
或2 1 12`)0
1
(so, numbers from
to
-
- 一个连字符(?:19|20)\d{2}
-19
或20
,然后是任意 2 位数字
(?!\d)
- 如果在当前位置的右侧有一个数字,则匹配失败的负前瞻。
完整片段:
import pandas as pd
df = pd.DataFrame()
data = { 'dob': ['will\t05-2020', 'John\t4-2020', 'James\t07-1999', 'Rob\t2-2001','kim\t1-20202020','Jane\t112-2020']}
df = pd.DataFrame(data)
df['Date'] = df['dob'].str.extract(r'(?<!\d)((?:0?[1-9]|1[0-2])-(?:19|20)\d{2})(?!\d)').fillna("")
df['Date'] = pd.to_datetime(df['Date'], format='%m%Y', errors='ignore')
输出:
>>> df
dob Date
0 will\t05-2020 05-2020
1 John\t4-2020 4-2020
2 James\t07-1999 07-1999
3 Rob\t2-2001 2-2001
4 kim\t1-20202020
5 Jane\t112-2020
推荐阅读
- javascript - 反应引导手风琴加减指标问题
- python - 如何在 django 中覆盖管理列名“is_staff”和“is_superuser”?
- docker - Kubernetes 无法运行本地构建的 docker 镜像
- python - 在 python 中订阅 Redis 通道的意外功能
- .net - API 应用单端口多应用 IIS
- python - 在 Pandas 数据框中具有依赖性的条件累积和
- react-native - React Native 无法访问 4G 中的沙箱,但可以在 Wifi 中工作
- spring-boot - 在 JPA 存储库(Spring Data Jpa)中执行自定义查询
- python - Python项目设置损坏
- ceph - 如何配置 Ceph rgw sts 密钥