给定一个字符串的Series,我试图计算一个新的Series,它包含原始字符串中最高的连续辅音计数,忽略空格。
例如,给定df['names'],我想确定df['max_consonants'],如下所示:
In [1]: df
Out[1]:
names max_consonants
0 will hunting 2
1 sean maguire 1
2 gerald lambeau 2
3 chuckie sullivan 2
4 mike krzyzewski 5在pandas之外,我可以使用re模块完成此操作,如下所示:
In [2]: def max_consonants(s):
return max(len(i) for i in re.findall(r'[^aeiou ]+', s))
In [3]: max_consonants('mike krzyzewski')
Out[3]: 5我知道可以使用pd.Series.apply在Series上使用max_consonants函数,但它不是矢量化的。我正在处理包含2-3 am行/名称的数据,因此我正在寻找最有效的解决方案。
对于pandas,有没有一种更优雅的解决方案可以让我利用矢量化?
发布于 2019-08-27 06:48:24
你可以试试这个,由于\W的缘故,它应该也适用于特殊字符。但请注意,\W也捕获数字,因此如果您还想拆分这些数字,则需要将0-9添加到split使用的正则表达式中:
df['names'].str.split(r'[AaEeIiOoUu\W]', expand=True).fillna('').applymap(len).max(axis='columns')使用测试数据:
raw="""idx names max_consonants
0 will hunting 2
1 sean maguire 1
2 gerald lambeau 2
3 chuckie sullivan 2
4 mike krzyzewski 5
5 mike krzyzewski12345678 5
"""
df= pd.read_csv(io.StringIO(raw), sep='\s{2,}', index_col=[0])其计算结果为:
idx
0 2
1 1
2 2
3 2
4 5
5 8
dtype: int64applymap之前的中间结果看起来像这样:
Out[89]:
0 1 2 3 4 5 6 7
idx
0 w ll h nt ng
1 s n m g r
2 g r ld l mb
3 ch ck s ll v n
4 m k krzyz wsk
5 m k krzyz wsk 12345678 关于性能的注意事项:我希望.mapapply(len)能够转换为高效的C++操作,但无法使用我的数据进行验证。如果您在此解决方案中遇到性能问题,您可以尝试一种变体,在该变体中,您可以执行直到applymap的所有操作,将applymap替换为列上的循环,然后执行.str.len()。大致如下所示:
df_consonant_strings= df['names'].str.split(r'[AaEeIiOoUu\W]', expand=True).fillna('')
ser_max= None
for col in df_consonant_strings.columns:
ser_col= df_consonant_strings[col].str.len()
if ser_max is None:
ser_max= ser_col
else:
ser_max= ser_max.where(ser_max>ser_col, ser_col)
# now ser_max contains the desired maximum length of consonant substringshttps://stackoverflow.com/questions/57665493
复制相似问题