如何基于多列数据从Pandas数据框中删除行?

3
我知道如何根据简单条件删除行,例如在这个stack overflow问题中,但是,我需要使用更复杂的条件删除行。

我的情况是:我有一些数据行,每行都有四个包含数字代码的列。 我需要删除所有没有至少一个以小于5的前导数字开头的代码的行。 我目前已经有一个函数,可以用于dataframe.apply,并创建一个名为“keep”的新列,并将其用1填充,如果它是要保留的行。 然后,我再使用该简单的“keep”列进行第二遍处理,以删除不需要的行。 我正在寻找一种方法,在不必创建新列的情况下完成此操作。

示例数据:

   a | b | c | d
0 145|567|999|876
1 999|876|543|543

在这些数据中,我希望保留第一行,因为在列“a”中,最高位数字小于5。第二行没有任何以小于5为首位数字的列,所以需要删除该行。


1
所以数据是整数还是字符串? - EdChum
这些代码是字符串。我还应该补充一些代码中也包含字母,例如“5K”,但它们都以数字开头。 - Gregory Arenius
1个回答

4
这应该可以正常工作:
In [31]:
df[(df.apply(lambda x: x.str[0].astype(int))).lt(5).any(axis=1)]

Out[31]:
     a    b    c    d
0  145  567  999  876

基本上,这个方法使用向量化的str方法获取每列的第一个字符,将其转换为int,然后调用lt方法在行级别上生成布尔值df,然后在df的行上调用any方法以生成布尔掩码,并对索引应用该掩码以屏蔽df。因此,可以将上述过程分解为以下步骤:
In [34]:
df.apply(lambda x: x.str[0].astype(int))

Out[34]:
   a  b  c  d
0  1  5  9  8
1  9  8  5  5

In [35]:    
df.apply(lambda x: x.str[0].astype(int)).lt(5)

Out[35]:
       a      b      c      d
0   True  False  False  False
1  False  False  False  False

In [37]:    
df.apply(lambda x: x.str[0].astype(int)).lt(5).any(axis=1)

Out[37]:
0     True
1    False
dtype: bool

编辑

为了处理NaN值,您需要调用dropna函数:

In [39]:
t="""a,b,c,d
0,145,567,999,876
1,999,876,543,543
2,,324,344"""
df = pd.read_csv(io.StringIO(t),dtype=str)
df

Out[39]:
     a    b    c    d
0  145  567  999  876
1  999  876  543  543
2  NaN  324  344  NaN

In [44]:
df[(df.apply(lambda x: x.dropna().str[0].astype(int))).lt(5,axis=0).any(axis=1)]

Out[44]:
     a    b    c    d
0  145  567  999  876
2  NaN  324  344  NaN

太棒了。我以前从未使用过这种方法来制作掩码。这对我在其他几个地方也会有所帮助。是否有一种方法可以处理缺失数据?它无法处理NaN。 - Gregory Arenius
1
我会更新,基本上你在 lambda 函数中调用 dropna - EdChum
不,它不会看到我的编辑,当你在系列上调用dropna()(这就是我们在df上调用apply时所做的)时,它会删除系列中的一个条目而不是整个行。 - EdChum
当然,你是正确的。我在你更新之前回答了。这个答案完美地解决了问题。谢谢你的解释。 - Gregory Arenius
更新后加入dropna的函数对大多数情况都有效,但当四个列都是NaN时会失败。原因是返回的Series的索引与原始数据框不匹配。为了解决这个问题,我在代码行中添加了reindex:df[(df.apply(lambda x: x.dropna().str[0].astype(int))).lt(5,axis = 0).any(axis = 1).reindex(index=df.index, fill_value=False)]。 - Gregory Arenius

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接