我在Spark领域还很陌生,我对数据框有疑问。我需要对两列(estado,producto)中的唯一分类变量进行分组,然后对第二列(producto)的唯一值进行计数和排序(asc)。我可以在Pandas中做到这一点,但不能在Spark中复制它。
我的原始数据框是
+--------------------+--------------------+
| estado| producto|
+--------------------+--------------------+
| MÉXICO|TINTE PARA EL CAB...|
| MÉXICO| TELEVISORES|
| MÉXICO| ACELGA|
| MÉXICO| QUESO. COTIJA|
| DISTRITO FEDERAL| AZUCAR|
| MÉXICO| DESENFRIOL-ITO|
| JALISCO| ARROZ|
| OAXACA|PEDIALYTE. ELECTR...|
| TLAXCALA| AGUA SIN GAS|
|VERACRUZ DE IGNAC...| TOMATE|
| MICHOACÁN DE OCAMPO| PAN DE CAJA|
| YUCATÁN| FLAGENASE 400|
| MICHOACÁN DE OCAMPO| ECTIVA|
| YUCATÁN| SALSA CATSUP|
| YUCATÁN| CLAVULIN|
| YUCATÁN| CAPOTENA|
| JALISCO| FLAGENASE 400|
| HIDALGO| VERMOX|
| OAXACA| MAIZ POZOLERO|
| OAXACA| AJO|
+--------------------+--------------------+
only showing top 20 rows
和我的虚拟尝试:
df.groupBy('estado','producto').agg({'producto':'count'}).show()
+--------------------+--------------------+---------------+
| estado| producto|count(producto)|
+--------------------+--------------------+---------------+
| MÉXICO|TINTE PARA EL CAB...| 44007|
| MÉXICO| TELEVISORES| 29702|
| MÉXICO| ACELGA| 7691|
| MÉXICO| QUESO. COTIJA| 4414|
| DISTRITO FEDERAL| AZUCAR| 18078|
| MÉXICO| DESENFRIOL-ITO| 642|
| JALISCO| ARROZ| 11735|
| OAXACA|PEDIALYTE. ELECTR...| 302|
| TLAXCALA| AGUA SIN GAS| 14505|
|VERACRUZ DE IGNAC...| TOMATE| 652|
| MICHOACÁN DE OCAMPO| PAN DE CAJA| 13003|
| YUCATÁN| FLAGENASE 400| 313|
| MICHOACÁN DE OCAMPO| ECTIVA| 39|
| YUCATÁN| SALSA CATSUP| 6549|
| YUCATÁN| CLAVULIN| 183|
| YUCATÁN| CAPOTENA| 271|
| JALISCO| FLAGENASE 400| 699|
| HIDALGO| VERMOX| 121|
| OAXACA| MAIZ POZOLERO| 1387|
| OAXACA| AJO| 783|
+--------------------+--------------------+---------------+
但我需要与
类似的输出+--------------------+--------------------+---------------+
| estado| producto|count(producto)|
+--------------------+--------------------+---------------+
| DISTRITO FEDERAL| AZUCAR| 18078|
| HIDALGO| VERMOX| 121|
| JALISCO| ARROZ| 11735|
| JALISCO| FLAGENASE 400| 699|
| MÉXICO|TINTE PARA EL CAB...| 44007|
| MÉXICO| TELEVISORES| 29702|
| MÉXICO| ACELGA| 7691|
| MÉXICO| QUESO. COTIJA| 4414|
| MÉXICO| DESENFRIOL-ITO| 642|
| MICHOACÁN DE OCAMPO| PAN DE CAJA| 13003|
| MICHOACÁN DE OCAMPO| ECTIVA| 39|
| OAXACA| MAIZ POZOLERO| 1387|
| OAXACA| AJO| 783|
| OAXACA|PEDIALYTE. ELECTR...| 302|
| TLAXCALA| AGUA SIN GAS| 14505|
|VERACRUZ DE IGNAC...| TOMATE| 652|
| YUCATÁN| SALSA CATSUP| 6549|
| YUCATÁN| FLAGENASE 400| 313|
| YUCATÁN| CLAVULIN| 183|
| YUCATÁN| CAPOTENA| 271|
+--------------------+--------------------+---------------+
甚至更好,显示第一列的每个唯一变量的第二列的唯一分类变量
+--------------------+--------------------+---------------+
| estado| producto|count(producto)|
+--------------------+--------------------+---------------+
| DISTRITO FEDERAL| AZUCAR| 18078|
| HIDALGO| VERMOX| 121|
| JALISCO| ARROZ| 11735|
| | FLAGENASE 400| 699|
| MÉXICO|TINTE PARA EL CAB...| 44007|
| | TELEVISORES| 29702|
| | ACELGA| 7691|
| | QUESO. COTIJA| 4414|
| | DESENFRIOL-ITO| 642|
| MICHOACÁN DE OCAMPO| PAN DE CAJA| 13003|
| | ECTIVA| 39|
| OAXACA| MAIZ POZOLERO| 1387|
| | AJO| 783|
| |PEDIALYTE. ELECTR...| 302|
| TLAXCALA| AGUA SIN GAS| 14505|
|VERACRUZ DE IGNAC...| TOMATE| 652|
| YUCATÁN| SALSA CATSUP| 6549|
| | FLAGENASE 400| 313|
| | CLAVULIN| 183|
| | CAPOTENA| 271|
+--------------------+--------------------+---------------+
我希望我对我的问题很清楚,对我的英语不好对不起。谢谢
更新:我忘了说第三列(count(producto))仅显示前n个最大值,也就是说,前三个最大,类似于Pandas中的nlargest()函数。
我想使用这样的东西
df.groupBy('estado','producto').count().filter("'count'>=3").sort(asc("count"))
但是我还没有尝试过。
更新2
我已尝试使用此代码在注释中提出建议
df.groupBy("estado","producto").count()\
.withColumn("row_num",F.row_number()\
.over(Window.partitionBy("estado","producto")\
.orderBy(F.col("count").desc())))\
.filter(F.col("row_num") < 3)\
.drop("row_num")\
.orderBy(F.col("estado"), F.col("producto").desc(),F.col("count")\
.desc()).show()
但输出不是所需的
+------+-------------+-----+
|estado| producto|count|
+------+-------------+-----+
| null|ZWAN. PREMIUM| 55|
| null| ZWAN| 55|
| null| ZUCARITAS| 20|
| null| ZOFILIP| 9|
| null| ZINTREPID| 9|
| null| ZINNAT| 9|
| null| ZANAHORIA| 14|
| null| ZACTOS| 9|
| null| YOGHURT| 203|
| null| YASMIN 24/4| 9|
| null| YASMIN| 9|
| null| XATRAL-OD| 8|
| null|VYTORIN 10/20| 8|
| null| VINO DE MESA| 7|
| null| VINAGRE| 66|
| null| VIDEOJUEGOS| 7|
| null| VIDEOCAMARAS| 1|
| null| VICK VAPORUB| 16|
| null| VIAGRA| 17|
| null| VERMOX PLUS| 9|
+------+-------------+-----+
only showing top 20 rows
我尝试稍微修改一下代码,但我明白了
+----------------+--------------------+------+
| estado| producto| count|
+----------------+--------------------+------+
|DISTRITO FEDERAL| REFRESCO|287463|
|DISTRITO FEDERAL| FUD|207569|
| MÉXICO| REFRESCO|194939|
|DISTRITO FEDERAL|LECHE ULTRAPASTEU...|175640|
|DISTRITO FEDERAL| DETERGENTE P/ROPA|173452|
| MÉXICO| FUD|149141|
|DISTRITO FEDERAL| YOGHURT|136720|
|DISTRITO FEDERAL| CERVEZA|136686|
| MÉXICO| DETERGENTE P/ROPA|132862|
|DISTRITO FEDERAL| MAYONESA|131103|
|DISTRITO FEDERAL| CHILES EN LATA|130598|
|DISTRITO FEDERAL| JABON DE TOCADOR|129889|
|DISTRITO FEDERAL| SHAMPOO|125603|
|DISTRITO FEDERAL| LECHE EN POLVO|116827|
| MÉXICO|LECHE ULTRAPASTEU...|116522|
|DISTRITO FEDERAL| DESODORANTE|113779|
|DISTRITO FEDERAL| HUEVO|111412|
|DISTRITO FEDERAL| TOALLA FEMENINA|102356|
|DISTRITO FEDERAL| MARGARINA| 98235|
| MÉXICO| JABON DE TOCADOR| 97330|
+----------------+--------------------+------+
only showing top 20 rows
答案 0 :(得分:0)
You are counting properly. You just need to use row_number window to select the top 3 and order the results properly. Have look at the code below.
df.groupBy("estado","producto").count()
.withColumn("row_num",row_number().over(Window.partitionBy("estado","producto").orderBy(col("count").desc)))
.filter(col("row_num") <= 3)
.drop("row_num")
.orderBy(col("estado"), col("producto"), col("count").desc)
Check this link中已保存的.html文件中的所有链接,以正确使用Pyspark中的row_number。 Spark SQL Row_number() PartitionBy Sort Desc