在Pyspark中的RDD中添加两个词典

时间:2018-04-20 07:21:06

标签: python apache-spark optimization pyspark rdd

我创建了RDD,其中每个元素都是字典。 (这是一个样本。有30,000个键

rdd.take(2)

[{'actor': 'brad',
  'good': 1,
  'bad': 0,
  'average': 0,}
 {'actor': 'tom',
  'good': 0,
  'bad': 1,
  'average': 1,}]

我正在尝试对数据执行算术运算,即 '演员':' brad'和'演员'汤姆',我想添加具有相同键的其他值

我这样做了:

d1=rdd.filter(lambda x: x['actor']=='brad').first()
d2=rdd.filter(lambda x: x['actor']=='tom').first()

dc={key: d1[key] + d2[key] for key in d1.keys() if key not in {'actor'} }

但是因为大约有30,000个[键],这花费了我很多时间。我可以通过使用Spark的分布式操作执行添加来优化它。如果是这样的话?

预期产出:

 [{'actor': 'brad',
      'good': 1,
      'bad': 1,
      'average': 1,}]

1 个答案:

答案 0 :(得分:2)

如果您将RDD转换为Spark DF并使用键组合以总结值,这将是一个更快的解决方案:

from pyspark import SQLContext, SparkContext
sc = SparkContext()
sql = SQLContext(sc)

a = [{'actor': 'brad', 'good': 1, 'bad': 0, 'average': 0,}, {'actor': 'tom','good': 0, 'bad': 1, 'average': 1,}, {'actor': 'brad', 'good': 1, 'bad': 0, 'average': 0,}, {'actor': 'tom','good': 0, 'bad': 1, 'average': 1,}]

jsonRDD = sc.parallelize(a) # In your case this step might not be necessary
main_df = sql.read.json(jsonRDD)
main_df = main_df.groupby('actor').sum()

输出:

main_df.show()

+-----+------------+--------+---------+
|actor|sum(average)|sum(bad)|sum(good)|
+-----+------------+--------+---------+
| brad|           0|       0|        2|
|  tom|           2|       2|        0|
+-----+------------+--------+---------+

编辑2:     #如果需要,可以使用withColumnRenamed()

重命名列
main_json = main_df.toJSON()

编辑1:

>>> main_df.rdd.map(lambda x: {x[0]: (x[1], x[2], x[3])}).collect()
[{u'brad': (0, 0, 2)}, {u'tom': (2, 2, 0)}]