【问题标题】:Reduce key, value pair based on similarity of their value in PySpark根据 PySpark 中值的相似性减少键值对
【发布时间】:2021-02-13 20:38:31
【问题描述】:

我是 PySpark 的初学者。

我想找到值中具有相同数字的字母对,然后找出哪对字母出现的频率更高。

这是我的数据

data = sc.parallelize([('a', 1), ('b', 4), ('c', 10), ('d', 4), ('e', 4), ('f', 1), ('b', 5), ('d', 5)])
data.collect()
[('a', 1), ('b', 4), ('c', 10), ('d', 4), ('e', 4), ('f', 1), ('b', 5), ('d', 5)]

我想要的结果是这样的:

1: a,f
4: b, d
4: b, e
4: d, e
10: c
5: b, d

我尝试了以下方法:

data1= data.map(lambda y: (y[1], y[0]))
data1.collect()
[(1, 'a'), (4, 'b'), (10, 'c'), (4, 'd'), (4, 'e'), (1, 'f'), ('b', 5), ('d', 5)]

data1.groupByKey().mapValues(list).collect()
[(10, ['c']), (4, ['b', 'd', 'e']), (1, ['a', 'f']), (5, ['b', 'd'])]

正如我所说,我对 PySpark 非常陌生,并试图搜索该命令但没有成功。谁能帮我解决这个问题?

【问题讨论】:

    标签: apache-spark pyspark rdd key-value


    【解决方案1】:

    您可以使用 flatMap 和 python itertools.combinations 从分组值中获取 2 的组合。另外,更喜欢使用reduceByKey 而不是groupByKey

    from itertools import combinations
    
    result = data.map(lambda x: (x[1], [x[0]])) \
        .reduceByKey(lambda a, b: a + b) \
        .flatMap(lambda x: [(x[0], p) for p in combinations(x[1], 2 if (len(x[1]) > 1) else 1)])
    
    result.collect()
    
    #[(1, ('a', 'f')), (10, ('c',)), (4, ('b', 'd')), (4, ('b', 'e')), (4, ('d', 'e')), (5, ('b', 'd'))]
    

    如果你想在元组只有一个元素时得到 None,你可以这样:

    .flatMap(lambda x: [(x[0], p) for p in combinations(x[1] if len(x[1]) > 1 else x[1] + [None], 2)])
    

    【讨论】:

    • 非常感谢!另外,如果只有一个值(10,('c',None)而不是(10,('c',),我想添加None。我将如何更改?我试图更改代码,但它不起作用。
    • @user14913431 你可以改用这个.flatMap(lambda x: [(x[0], p) for p in combinations(x[1] if len(x[1]) > 1 else x[1] + [None], 2)])。更新了我的答案。
    猜你喜欢
    • 2020-08-09
    • 2018-04-15
    • 2020-03-25
    • 2014-06-07
    • 1970-01-01
    • 2020-10-29
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多