Comme tout le monde connaît les partitionneurs en Spark ont un impact énorme sur les performances de toutes les opérations "larges", il est donc généralement personnalisé dans les opérations. J'expérimentais avec le code suivant:
val rdd1 =
sc.parallelize(1 to 50).keyBy(_ % 10)
.partitionBy(new HashPartitioner(10))
val rdd2 =
sc.parallelize(200 to 230).keyBy(_ % 13)
val cogrouped = rdd1.cogroup(rdd2)
println("cogrouped: " + cogrouped.partitioner)
val unioned = rdd1.union(rdd2)
println("union: " + unioned.partitioner)
Je vois que par défaut cogroup()
donne toujours un RDD avec le partitionneur personnalisé, mais union()
ne le fait pas, il reviendra toujours à défaut. Ceci est contre-intuitif car nous supposons généralement qu'un PairRDD devrait utiliser son premier élément comme clé de partition. Existe-t-il un moyen de "forcer" Spark pour fusionner 2 PairRDD pour utiliser la même clé de partition?
union
est une opération très efficace, car elle ne déplace aucune donnée. Si rdd1
A 10 partitions et rdd2
A 20 partitions alors rdd1.union(rdd2)
aura 30 partitions: les partitions des deux RDD mises l'une après l'autre. Ce n'est qu'un changement de comptabilité, il n'y a pas de remaniement.
Mais il rejette nécessairement le partitionneur. Un partitionneur est construit pour un nombre donné de partitions. Le RDD résultant a un certain nombre de partitions différentes de rdd1
Et rdd2
.
Après avoir pris l'union, vous pouvez exécuter repartition
pour mélanger les données et les organiser par clé.
Il y a une exception à ce qui précède. Si rdd1
Et rdd2
Ont le même partitionneur (avec le même nombre de partitions), union
se comporte différemment. Il joindra les partitions des deux RDD par paire, ce qui lui donnera le même nombre de partitions que chacune des entrées. Cela peut impliquer le déplacement de données (si les partitions n'étaient pas colocalisées) mais n'impliquera pas de lecture aléatoire. Dans ce cas, le partitionneur est conservé. (Le code pour cela est dans PartitionerAwareUnionRDD.scala .)
Ce n'est plus vrai. Si deux RDD ont exactement le même partitionneur et le même nombre de partitions, le RDD union
ed aura également ces mêmes partitions. Cela a été introduit dans https://github.com/Apache/spark/pull/4629 et incorporé dans Spark 1.3.