【问题标题】:Pandas replace full word string熊猫替换完整的单词字符串
【发布时间】:2016-05-29 01:21:36
【问题描述】:

我有一个数据框:

df = pd.DataFrame({'id' : ['abarth 1.4 a','abarth 1 a','land rover 1.3 r','land rover 2',
                           'land rover 5 g','mazda 4.55 bl'], 
                   'series': ['a','a','r','','g', 'bl'] })

我想从对应的id中删除'series'字符串,所以最终结果应该是:

'id': ['abarth 1.4','abarth 1','land rover 1.3','land rover 2','land rover 5', 'mazda 4.55']

目前我正在使用 df.apply:

df.id = df.apply(lambda x: x['id'].replace(x['series'], ''), axis =1)

但这会删除字符串的所有实例,换句话说,就像这样: 'id': ['brth 1.4','brth 1','land ove 1.3','land rover 2','land rover 5', 'mazda 4.55']

我是否应该像这样将正则表达式与 df.apply 中的变量混合匹配?

df.id = df.apply(lambda x: x['id'].replace(r'\b' + x['series'], ''), axis =1)

【问题讨论】:

    标签: python pandas


    【解决方案1】:

    使用re,如果你想指定series字符串:

    df.apply(lambda x: re.sub('\s*{}$'.format(x['series']), '', x['id']), axis=1)
    

    如果series 字符串始终是可预测的模式(即[a-z]),您也可以尝试:

    df['id'].apply(lambda x: re.sub('\s*[a-z]+$', '', x))
    

    无论哪种方式,输出都是您要寻找的:

    0        abarth 1.4
    1          abarth 1
    2    land rover 1.3
    3      land rover 2
    4      land rover 5
    5        mazda 4.55
    

    【讨论】:

      【解决方案2】:

      您可以使用str.rpartitionids 拆分到最后一个空格。

      In [169]: parts = df['id'].str.rpartition(' ')[[0,2]]; parts
      Out[169]: 
                      0   2
      0      abarth 1.4   a
      1        abarth 1   a
      2  land rover 1.3   r
      3      land rover   2
      4    land rover 5   g
      5      mazda 4.55  bl
      

      然后您可以使用==parts[2]df['series'] 进行比较:

      In [170]: mask = (parts[2] == df['series']); mask
      Out[170]: 
      0     True
      1     True
      2     True
      3    False
      4     True
      5     True
      dtype: bool
      

      最后,使用df['id'].wheredf['id] 替换为parts[0],其中mask 为True:

      import pandas as pd
      df = pd.DataFrame(
          {'id' : ['abarth 1.4 a','abarth 1 a','land rover 1.3 r','land rover 2',
                   'land rover 5 g','mazda 4.55 bl'], 
           'series': ['a','a','r','','g', 'bl'] })
      parts = df['id'].str.rpartition(' ')[[0,2]]
      mask = (parts[2] == df['series'])
      df['id'] = df['id'].where(~mask, parts[0], axis=0)
      print(df)
      

      产量

                     id series
      0      abarth 1.4      a
      1        abarth 1      a
      2  land rover 1.3      r
      3    land rover 2       
      4    land rover 5      g
      5      mazda 4.55     bl
      

      或者,您可以使用

      import re
      def remove_series(x):
          pat = r'{}$'.format(x['series'])
          return re.sub(pat, '', x['id'])
      df['id'] = df.apply(remove_series, axis=1)
      

      但是使用自定义函数调用 df.apply 往往比使用内置矢量化方法(例如第一种方法中使用的方法)要慢得多。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2017-03-12
        • 2019-06-03
        • 2019-11-23
        • 2019-02-06
        • 1970-01-01
        • 1970-01-01
        • 2017-12-28
        • 2017-02-07
        相关资源
        最近更新 更多