计算 PySpark 中列中的非空值

问题描述 投票:0回答:4

我有一个包含空值的数据框:

from pyspark.sql import functions as F
df = spark.createDataFrame(
    [(125, '2012-10-10', 'tv'),
     (20, '2012-10-10', 'phone'),
     (40, '2012-10-10', 'tv'),
     (None, '2012-10-10', 'tv')],
    ["Sales", "date", "product"]
)

我需要计算“销售额”列中的非空值。

我尝试了3种方法。

我做对的第一个:

df.where(F.col("sales").isNotNull()).groupBy('product')\
  .agg((F.count(F.col("Sales")).alias("sales_count"))).show()

# product   | sales_count
# phone     |  1
# tv        |  2

第二个,不正确:

df.groupBy('product')\
  .agg((F.count(F.col("Sales").isNotNull()).alias("sales_count"))).show()

# product   | sales_count
# phone     |  1
# tv        |  3

第三个,我得到错误:

 df.groupBy('product')\
   .agg((F.col("Sales").isNotNull().count()).alias("sales_count")).show()

类型错误:“列”对象不可调用

第二种和第三种方法可能会出现什么错误?

apache-spark pyspark apache-spark-sql count null
4个回答
6
投票

您的第一次尝试是在进行聚合之前过滤掉

null
列中带有
Sales
的行。因此它会给你正确的结果。

但是使用第二个代码

df.groupBy('product') \
    .agg((F.count(F.col("Sales").isNotNull()).alias("sales_count"))).show()

您还没有

filtered
并在整个数据集上执行
aggregation
。如果您仔细分析,
F.col("Sales").isNotNull()
将为您提供boolean列,即
true
false
。因此
F.count(F.col("Sales").isNotNull())
只是计算分组数据集中的 boolean 值,如果您创建如下所示的新列,则这一点很明显

df.withColumn("isNotNull", F.col("Sales").isNotNull()).show()

这会给你

+-----+----------+-------+---------+
|Sales|      date|product|isNotNull|
+-----+----------+-------+---------+
|  125|2012-10-10|     tv|     true|
|   20|2012-10-10|  phone|     true|
|   40|2012-10-10|     tv|     true|
| null|2012-10-10|     tv|    false|
+-----+----------+-------+---------+

所以第二次尝试的计数是正确的。

对于您的第三次尝试,

.count()
是一个不能在聚合转换中使用的操作。 只有返回
Column
dataType 的函数才能在
.agg()
中使用,它们可以是内置函数、UDF 或您自己的函数。


6
投票

有一个更简单的方法:

>>> df.groupBy("product").agg({"Sales":"count"}).show()
+-------+------------+
|product|count(Sales)|
+-------+------------+
|  phone|           1|
|     tv|           2|
+-------+------------+

0
投票

计算非空值

  • 仅适用于每个字符串和数字列:

    df.summary("count").show()
    # +-------+-----+----+-------+
    # |summary|Sales|date|product|
    # +-------+-----+----+-------+
    # |  count|    3|   4|      4|
    # +-------+-----+----+-------+
    
  • 对于任何类型的每一列:

    df.agg(*[F.count(c).alias(c) for c in df.columns]).show()
    # +-----+----+-------+
    # |Sales|date|product|
    # +-----+----+-------+
    # |    3|   4|      4|
    # +-----+----+-------+
    

0
投票

查看 countIf() 函数。在函数内放置您的条件,例如:

df.select(count_if(col("销售").isNotNull()).show()

© www.soinside.com 2019 - 2024. All rights reserved.