繁体   English   中英

使用pandas替换字符串中字符中最后一次出现的所有字符

[英]Replace all but last occurrences of a character in a string with pandas

使用Pandas删除字符串中的所有但最后一个句点,如下所示:

s = pd.Series(['1.234.5','123.5','2.345.6','678.9'])
counts = s.str.count('\.')
target = counts==2
target
0     True
1    False
2     True
3    False
dtype: bool

s = s[target].str.replace('\.','',1)
s
0    1234.5
2    2345.6
dtype: object

然而,我想要的输出是:

0    1234.5
1    123.5
2    2345.6
3    678.9
dtype: object

替换命令以及掩码目标似乎正在删除未替换的值,我无法看到如何解决这个问题。

基于正则表达式的str.replace

这个带有str.replace正则表达式模式应该很好。

s.str.replace(r'\.(?=.*?\.)', '')

0    1234.5
1     123.5
2    2345.6
3     678.9
dtype: object

这个想法是,只要有更多的字符要替换,继续更换。 这是使用的正则表达式的细分。

\.     # '.'
(?=    # positive lookahead
.*?    # match anything
\.     # look for '.'
)

有趣的np.vectorize

如果你想用count来做这件事,这并非不可能,但这是一个挑战。 您可以使用np.vectorize使这更容易。 首先,定义一个函数,

def foo(r, c):
    return r.replace('.', '', c)

矢量化,

v = np.vectorize(foo)

现在,调用函数v ,传递s和计数以替换。

pd.Series(v(s, s.str.count(r'\.') - 1))

0    1234.5
1     123.5
2    2345.6
3     678.9
dtype: object

请记住,这基本上是一个美化的循环。


Loopy / List理解

python相当于vectorize

r = []
for x, y in zip(s, s.str.count(r'\.') - 1):
    r.append(x.replace('.', '', y))

pd.Series(r)

0    1234.5
1     123.5
2    2345.6
3     678.9
dtype: object

或者,使用列表理解:

pd.Series([x.replace('.', '', y) for x, y in zip(s, s.str.count(r'\.') - 1)])

0    1234.5
1     123.5
2    2345.6
3     678.9
dtype: object

您想要替换蒙面项目并保持其余部分保持不变。 这正是Series.where所做的,除了它取代了未屏蔽的值,所以你需要否定掩码。

s.where(~target, s.str.replace('\.','',1))

或者您可以通过分配屏蔽值来进行就地更改,这可能更便宜但具有破坏性。

s[target] = s[target].str.replace('\.','',1)

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM