Barrera anti-explosión: estimar un join antes de pagarlo
El número de filas que producirá un join se puede calcular de antemano: la suma de los productos de las cardinalidades por clave. Un umbral convierte la estimación en una barrera que bloquea.
Requisitos
PySpark 3.x
Python
from pyspark.sql import functions as F
g = commandes.groupBy("ref").agg(F.count("*").alias("n_gauche"))
d = tarifs.groupBy("ref").agg(F.count("*").alias("n_droite"))
croise = g.join(d, "ref").withColumn(
"produit", F.col("n_gauche") * F.col("n_droite"))
estimation = croise.agg(F.sum("produit")).first()[0]
print(f"Jointure estimée : {estimation:,} lignes")
if estimation > 500_000_000:
croise.orderBy(F.desc("produit")).show(3)
raise RuntimeError("Explosion probable : cle 'ref' non unique des deux cotes")Resultado
Jointure estimée : 38,412,907,224 lignes +--------+--------+--------+--------------+ | ref|n_gauche|n_droite| produit| +--------+--------+--------+--------------+ |REF-MISC| 184,302| 208,114|38,355,826,428| |REF-0042| 1,204| 12| 14,448| |REF-1183| 880| 8| 7,040| +--------+--------+--------+--------------+ RuntimeError: Explosion probable : cle 'ref' non unique des deux cotes → REF-MISC est un fourre-tout présent 184 k × 208 k fois : 38 Md de lignes évitées
PySparkJointureCartésienGarde-fou