计算PySpark中数组的滚动和并另存为dict?

计算PySpark中数组的滚动和并另存为dict?,pyspark,Pyspark,给出如下输入: timestamp vars 2 [1,2,3] 2 [1,2,4] 3 [1,2] 4 [1,3] 5 [1,3] 我需要对每个指数进行滚动计数。尝试将数组扩展为一个热编码([1,2,3,5]->[0,1,1,1,0,1])并添加,但这可能会变得任意大(>100万),因此我希望将其作为一个dict进行维护。类似于下面的内容。任何指点都将不胜感激 t

给出如下输入:

timestamp     vars 
2             [1,2,3]
2             [1,2,4]
3             [1,2]
4             [1,3]
5             [1,3]
我需要对每个指数进行滚动计数。尝试将数组扩展为一个热编码([1,2,3,5]->[0,1,1,1,0,1])并添加,但这可能会变得任意大(>100万),因此我希望将其作为一个dict进行维护。类似于下面的内容。任何指点都将不胜感激

timestamp     vars 
2             {1:1, 2:1, 3:1}
2             {1:2, 2:2, 3:1, 4:1}
3             {1:3, 2:3, 3:1, 4:1}
4             {1:4, 2:3, 3:2, 4:1}
5             {1:5, 2:3, 3:3, 4:1}

谢谢

我建议
集合中的
计数器

In [1]: from collections import Counter                                                                                                                             

In [2]: count = Counter()                                                                                                                                           

In [3]: count.update([1,2,4])                                                                                                                                       

In [4]: count                                                                                                                                                       
Out[4]: Counter({1: 1, 2: 1, 4: 1})

In [5]: count.update([1,2,3])                                                                                                                                       

In [6]: count                                                                                                                                                       
Out[6]: Counter({1: 2, 2: 2, 4: 1, 3: 1})

In [7]: count.update([2,3,5])                                                                                                                                       

In [8]: count                                                                                                                                                       
Out[8]: Counter({1: 2, 2: 3, 4: 1, 3: 2, 5: 1})
示例数据帧:

+---+------------+
| ID|         arr|
+---+------------+
|  1|         [0]|
|  2|      [0, 1]|
|  3|   [0, 1, 2]|
|  4|[0, 1, 2, 3]|
|  1|         [0]|
|  1|         [0]|
|  3|   [0, 1, 2]|
|  0|          []|
+---+------------+
使用以下使用收集计数器的功能:

def arr_operation(arr):
   from collections import Counter
   return dict(Counter(arr))
按以下方式为
arr\u操作创建自定义项:

udf_dist_count =  udf(arr_operation,MapType(IntegerType(), IntegerType()))
并调用创建新列:

final_df = df.withColumn("Dict",udf_dist_count("arr"))
结果如下:

+---+------------+--------------------------------+
|ID |arr         |Dict                            |
+---+------------+--------------------------------+
|1  |[0]         |[0 -> 1]                        |
|2  |[0, 1]      |[0 -> 1, 1 -> 1]                |
|3  |[0, 1, 2]   |[0 -> 1, 1 -> 1, 2 -> 1]        |
|4  |[0, 1, 2, 3]|[0 -> 1, 1 -> 1, 2 -> 1, 3 -> 1]|
|1  |[0]         |[0 -> 1]                        |
|1  |[0]         |[0 -> 1]                        |
|3  |[0, 1, 2]   |[0 -> 1, 1 -> 1, 2 -> 1]        |
|0  |[]          |[]                              |
+---+------------+--------------------------------+

关于分布式环境中收集计数器速度慢的争论在回答这个问题时已经得到了很好的解释

我建议您维护一个hashmap,在那里增加计数,并在创建字典时获取它。这不适用于pyspark。@salt die,你们对PySpark有什么建议吗?我的建议是使用计数器。PySpark不包括python的标准库吗?@salt die是的,它有库,但它不会以分布式方式工作。您的建议将用于UDF,并且它们对于大数据任务来说非常慢。如果您不想弄乱可变对象,您可以通过添加计数来创建新计数器。