Python 正则表达式将地址分成三个不同的系列[第1部分]
我正在用一个包含客户信息的数据集来试验/学习Python 数据帧结构如下(这些是由记录组成的): 我对Python 正则表达式将地址分成三个不同的系列[第1部分],python,regex,pandas,dataframe,Python,Regex,Pandas,Dataframe,我正在用一个包含客户信息的数据集来试验/学习Python 数据帧结构如下(这些是由记录组成的): 我对地址系列特别感兴趣。具体来说,我的目标是将街道、编号和方框的信息“拆分”为三个不同的系列 例如,在转换之后,第一个和第七个记录/行应该如下所示: | cus_name | street | number | box | postal_code | |----------|--------------|--------|-----|-------------| | James |
地址
系列特别感兴趣。具体来说,我的目标是将街道、编号和方框的信息“拆分”为三个不同的系列
例如,在转换之后,第一个和第七个记录/行应该如下所示:
| cus_name | street | number | box | postal_code |
|----------|--------------|--------|-----|-------------|
| James | Main St | 59 | NaN | 1410 |
| Maria | Mc-Kenzie Av | 40P | 1 | 1190.0 |
起初,我不知道如何解决这个问题。在这里做了一些研究之后,我发现了一些有趣的使用正则表达式的相关帖子
由于我不是Python(也不是正则表达式)方面的专家,我想我可以从识别address
系列中的模式开始。事实上,每个地址都有以下模式:
- 位于字符串开头的街道部分。它由一个或多个由空格字符或破折号分隔的单词组成(例如,
)Mc Kenzie Av
- 位于字符串末端的框部分。它总是紧跟在
字符之后,由一个包含字母数字字符的单词和一些特殊字符(例如b.
,A/b
)组成F1
100-102
,7d
)
我正在寻求帮助,以使用正则表达式实现我想要的目标(如果正则表达式是解决方案的话) 您可以尝试以下模式:
pattern = "^(?P<street>.+)\s+(?P<number>[\d\w]+)\s+b\.(?P<box>.*)$"
df['address'].str.extract(pattern)
pattern = "^(?P<street>[\D]+)\s+(?P<number>[\w\s]+)\s+b\.(?P<box>.*)$"
有关说明,请粘贴图案
如果您要求街道严格无编号,例如上面的第8行,请使用以下模式:
pattern = "^(?P<street>.+)\s+(?P<number>[\d\w]+)\s+b\.(?P<box>.*)$"
df['address'].str.extract(pattern)
pattern = "^(?P<street>[\D]+)\s+(?P<number>[\w\s]+)\s+b\.(?P<box>.*)$"
您可以尝试以下模式:
pattern = "^(?P<street>.+)\s+(?P<number>[\d\w]+)\s+b\.(?P<box>.*)$"
df['address'].str.extract(pattern)
pattern = "^(?P<street>[\D]+)\s+(?P<number>[\w\s]+)\s+b\.(?P<box>.*)$"
有关说明,请粘贴图案
如果您要求街道严格无编号,例如上面的第8行,请使用以下模式:
pattern = "^(?P<street>.+)\s+(?P<number>[\d\w]+)\s+b\.(?P<box>.*)$"
df['address'].str.extract(pattern)
pattern = "^(?P<street>[\D]+)\s+(?P<number>[\w\s]+)\s+b\.(?P<box>.*)$"
另一种正则表达式方法:
In [913]: df[['street', 'number', 'box']] = df.address.str.extract(r'(\D+)\s+(\d+[\s-]?(?!b)\w*)(?:\s+b\.)?(\S+)?', expand=True)
In [914]: df
Out[914]:
cus_name address postal_code street number box
0 James Main St 59 1410.0 Main St 59 NaN
1 Mary Yellow Av 11 b.F1 1210.0 Yellow Av 11 F1
2 David Terrazzo Way 100-102 1020.0 Terrazzo Way 100-102 NaN
3 Linda NaN NaN NaN NaN NaN
4 George Hamilton St 159 b.A/B 1310.0 Hamilton St 159 A/B
5 Jennifer NaN NaN NaN NaN NaN
6 John Henry St 7 D 1080.0 Henry St 7 D NaN
7 Maria Mc-Kenzie Av 40P b.1 1190.0 Mc-Kenzie Av 40P 1
8 Charles Neptune Av 14 15 b.G 1040.0 Neptune Av 14 15 G
9 Helen NaN NaN NaN NaN NaN
另一种正则表达式方法:
In [913]: df[['street', 'number', 'box']] = df.address.str.extract(r'(\D+)\s+(\d+[\s-]?(?!b)\w*)(?:\s+b\.)?(\S+)?', expand=True)
In [914]: df
Out[914]:
cus_name address postal_code street number box
0 James Main St 59 1410.0 Main St 59 NaN
1 Mary Yellow Av 11 b.F1 1210.0 Yellow Av 11 F1
2 David Terrazzo Way 100-102 1020.0 Terrazzo Way 100-102 NaN
3 Linda NaN NaN NaN NaN NaN
4 George Hamilton St 159 b.A/B 1310.0 Hamilton St 159 A/B
5 Jennifer NaN NaN NaN NaN NaN
6 John Henry St 7 D 1080.0 Henry St 7 D NaN
7 Maria Mc-Kenzie Av 40P b.1 1190.0 Mc-Kenzie Av 40P 1
8 Charles Neptune Av 14 15 b.G 1040.0 Neptune Av 14 15 G
9 Helen NaN NaN NaN NaN NaN
[\d\w]
=\w
和b.
必须是b\.
,因为
是原始数据中的一个点。@Quanghaang谢谢,非常感谢。你的解决方案几乎就是我想要的。是否有一种简单的方法来修改代码,以便在框信息丢失时,模式仍然捕获街道和数字部分?我在我原来的帖子中添加了一个明确的例子。与另一个答案类似,你可以将模式更改为pattern=“^(?P.+)\s+(?P[\w-]+)?[\s+b\]?(?P.*)”
[\d\w]
=\w
,并且必须是b\
,因为/code>是原始数据中的一个点。@QuangHoang谢谢你,非常感谢。你的解决方案几乎就是我想要的。是否有一种简单的方法来修改代码,以便在框信息丢失时,模式仍然捕获街道和数字部分?我在原来的帖子中添加了一个明确的例子。与另一个答案类似,您可以将模式更改为pattern=“^(?P.+)\s+(?P[\w-]+)?[\s+b\.]?(?P.*)$”
。