Python Groupby类和统计要素中缺少的值

Python Groupby类和统计要素中缺少的值,python,pandas,dataframe,group-by,pandas-groupby,Python,Pandas,Dataframe,Group By,Pandas Groupby,我有一个问题,我无法在网络或文档中找到任何解决方案,即使我认为这是非常琐碎的 我想做什么 我有一个这样的数据帧 CLASS FEATURE1 FEATURE2 FEATURE3 X A NaN NaN X NaN A NaN B A A A 我想按标签(CLASS)分组,并显示每个特征中计数的NaN值的数量,使其看起来像这样。这样做的目的是了解缺失值在不同类中的分布情况 CLASS

我有一个问题,我无法在网络或文档中找到任何解决方案,即使我认为这是非常琐碎的

我想做什么

我有一个这样的数据帧

CLASS FEATURE1 FEATURE2 FEATURE3
  X      A       NaN      NaN
  X     NaN       A       NaN
  B      A        A        A
我想按标签(CLASS)分组,并显示每个特征中计数的NaN值的数量,使其看起来像这样。这样做的目的是了解缺失值在不同类中的分布情况

CLASS FEATURE1 FEATURE2 FEATURE3
  X      1        1        2
  B      0        0        0
我知道如何接收非空值的数量-
df.groupby['CLASS'].count()

NaN值是否存在类似的情况


我试图从size()中减去count(),但它返回了一个未格式化的输出,其中填充了值NaN

使用isna计算掩码,然后分组并找到总和:

df.drop('CLASS', 1).isna().groupby(df.CLASS, sort=False).sum().reset_index()

  CLASS  FEATURE1  FEATURE2  FEATURE3
0     X       1.0       1.0       2.0
1     B       0.0       0.0       0.0

另一个选项是使用
rsub
沿第0轴使用
size
count
中减去
size,以进行索引对齐减法:

df.groupby('CLASS').count().rsub(df.groupby('CLASS').size(), axis=0)
或者


有很多很好的答案,这里有一些
timeits
供您阅读:

df_ = df
df = pd.concat([df_] * 10000)

%timeit df.drop('CLASS', 1).isna().groupby(df.CLASS, sort=False).sum()
%timeit df.set_index('CLASS').isna().sum(level=0)    
%%timeit
g = df.groupby('CLASS')
g.count().rsub(g.size(), axis=0)

11.8 ms ± 108 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)
9.47 ms ± 379 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)
6.54 ms ± 81.6 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)

实际性能取决于您的数据和设置,因此您的里程数可能会有所不同。

您可以使用
set\u index
sum

df.set_index('CLASS').isna().sum(level=0)
输出:

       FEATURE1  FEATURE2  FEATURE3
CLASS                              
X           1.0       1.0       2.0
B           0.0       0.0       0.0

使用
计数
大小

g=df.groupby('CLASS')

-g.count().sub(g.size(),0)

          FEATURE1  FEATURE2  FEATURE3
CLASS                              
B             0         0         0
X             1         1         2
我们可以将这个问题转化为一个更一般的问题,即如何使用for循环计算数据帧中的
NaN

pd.DataFrame({x: y.isna().sum()for x , y in g }).T.drop('CLASS',1)
Out[468]: 
   FEATURE1  FEATURE2  FEATURE3
B         0         0         0
X         1         1         2

我想更好地理解第一个代码。你能解释一下df.drop('CLASS',1)在这种情况下的作用吗?非常感谢。
g=df.groupby('CLASS')

-g.count().sub(g.size(),0)

          FEATURE1  FEATURE2  FEATURE3
CLASS                              
B             0         0         0
X             1         1         2
pd.DataFrame({x: y.isna().sum()for x , y in g }).T.drop('CLASS',1)
Out[468]: 
   FEATURE1  FEATURE2  FEATURE3
B         0         0         0
X         1         1         2