熊猫DataFrame字符串替换,然后分割并设置交集

时间:2019-04-20 23:01:48

标签: python python-3.x pandas

我关注了0 low 1 high 2 high 3 high 4 low pandas

DataFrame

我有整数列表

data = ['18#38#123#23=>21', '18#38#23#55=>35']
d = pd.DataFrame(data, columns = ['rule'])

,并且如果列表r = [18, 55] 中的所有整数也都存在于规则中,我想从DataFrame上方过滤规则。我尝试了以下代码,但失败了

r

如何使用d[d['rule'].str.replace('=>','#').split('#').astype(set).issuperset(set(r))]

实现所需的过滤

4 个答案:

答案 0 :(得分:2)

您的发展方向正确,只需使用apply函数即可:

d[d['rule'].str.replace('=>','#').str.split('#').apply(lambda x: set(x).issuperset(set(map(str,r))))]

答案 1 :(得分:1)

我最初的直觉是使用list理解:

df = pd.DataFrame(['18#38#123#23=>21', '188#38#123#23=>21', '#18#38#23#55=>35'], columns = ['rule'])

def wrap(n):
    return r'(?<=[^|^\d]){}(?=[^\d])'.format(n)

patterns = [18, 55]
pd.concat([df['rule'].str.contains(wrap(pattern)) for pattern in patterns], axis=1).all(axis=1)

输出:

0    False
1    False
2     True

答案 2 :(得分:1)

使用str.get_dummies

d.rule.str.replace('=>','#').str.get_dummies(sep='#').loc[:, map(str, r)].all(1)

输出

0    False
1     True
dtype: bool

详细信息:

get_dummies + loc返回

    18  55
0   1   0
1   1   1

答案 3 :(得分:-1)

我的方法类似于@RafaelC的答案,但是将所有string转换为int

new_df = d.rule.str.replace('=>','#').str.get_dummies(sep='#')
new_df.columns = new_df.columns.astype(int)
has_all = new_df[r].all(1)

# then you can assign new column for initial data frame
d['new_col'] = 10
d.loc[has_all, 'new_col'] = 100

输出:

+-------+-------------------+------------+
|       |    rule           |   new_col  |
+-------+-------------------+------------+
|    0  | 18#38#123#23=>21  |      10    |
|    1  | 188#38#23#55=>35  |      10    |
|    2  | 18#38#23#55=>35   |     100    |
+-------+-------------------+------------+