python pandas以字符串模式为条件替换列值并使用split()

时间:2015-05-01 14:54:18

标签: regex pandas

很长一段时间潜伏 - 我终于坚持了一个涉及熊猫的项目,而且比以往任何时候都需要你的帮助。

我有一个如下的数据帧。每行描述一个退休公式,该公式可能有多个标准(因此e1)

index    e0     e1 
1    62/10   NaN
2    age 55  NaN
3    67/10   age 70

我想制作描述最低年龄的专栏年龄。我已经定义了如何描述每个标准的模式。例如,

 pattern1=r'.*/.*'

 pattern7=r'age.[0-9].*'

我有pattern1-pattern7。

我使用以下代码将e0的年龄部分提取到新的年龄段:

 df['age']=df['e0'][(df['e0'].str.match(pattern1)==1)].apply(lambda x: str(x).split('/')[0])

给了我

index    e0     e1    age
1    62/10   NaN      62
2    age 55  NaN      NaN
3    67/10   age 70   67

我想解决其他格式,例如“55岁”(在这种情况下提取55),但我不确定如何去做。如果我做

  df['age']=df['e0'][(df['e0'].str.match(pattern7)==1)].apply(lambda x: str(x).split(' ')[1])

然后它显然是错误的,因为我会覆盖已经存在的年龄而且我得到了

index    e0     e1    age
1    62/10   NaN      NaN
2    age 55  NaN      55
3    67/10   age 70   NaN

我已尝试过其他变体,只要语法允许我,但无济于事。 我是Stata用户,在Stata中,我会在regexm上使用replace命令。我正在努力学习Python,这是一段艰难的旅程!我对此表示感谢。

我还有另一个(希望)快速问题:我使用了以下两行来消除e0和e1中的空白区域。

 option['e0']=option['e0'].str.strip()
 option['e1']=option['e1'].str.strip()

有没有办法在一行中解决它们?

提前多多感谢。

2 个答案:

答案 0 :(得分:0)

有趣的问题,我在这里传递一个删除NaN值的函数,然后调用sum来连接数据行。

然后,我们可以使用正则表达式str调用矢量化findall方法\d+,该方法将所有数字作为列表返回。

然后我们将另一个函数应用于此,将str数转换为int,将它们放在一个列表中并返回最小值:

In [37]:

def func(x):
    return x.dropna().sum()
​
def lowest(x):
    return min(list(map(int,x)))
​
df['min'] = df[['e0','e1']].apply(lambda x: func(x), axis=1).str.findall(r'\d+').apply(lowest)
df
Out[37]:
   index      e0      e1  min
0      1   62/10     NaN   10
1      2  age 55     NaN   55
2      3   67/10  age 70   10

打破上面所以你可以看到发生了什么:

In [38]:

df[['e0','e1']].apply(lambda x: func(x), axis=1)
Out[38]:
0          62/10
1         age 55
2    67/10age 70
dtype: object
In [39]:

df[['e0','e1']].apply(lambda x: func(x), axis=1).str.findall(r'\d+')
Out[39]:
0        [62, 10]
1            [55]
2    [67, 10, 70]
dtype: object

答案 1 :(得分:0)

这是对你的第二个问题的回答(你应该坚持每个帖子一个问题)。

df.loc[:, ['e0', 'e1']].apply(lambda x: x.str.strip())

我不确定您为什么要调用DataFrame'选项'当它之前被称为“df'”时,我坚持使用后者。