Disons que j'ai le dataframe suivant:
agentName|original_dt|parsed_dt| user|text|
+----------+-----------+---------+-------+----+
|qwertyuiop| 0| 0|16102.0| 0|
Je souhaite créer un nouveau cadre de données avec une colonne supplémentaire contenant la concaténation de tous les éléments de la ligne:
agentName|original_dt|parsed_dt| user|text| newCol
+----------+-----------+---------+-------+----+
|qwertyuiop| 0| 0|16102.0| 0| [qwertyuiop, 0,0, 16102, 0]
Note: Ceci est juste un exemple. Le nombre de colonnes et leurs noms ne sont pas connus. C'est dynamique.
Je pense que cela fonctionne parfaitement pour votre cas Voici un exemple
val spark =
SparkSession.builder().master("local").appName("test").getOrCreate()
import spark.implicits._
val data = spark.sparkContext.parallelize(
Seq(
("qwertyuiop", 0, 0, 16102.0, 0)
)
).toDF("agentName","original_dt","parsed_dt","user","text")
val result = data.withColumn("newCol", split(concat_ws(";", data.schema.fieldNames.map(c=> col(c)):_*), ";"))
result.show()
+----------+-----------+---------+-------+----+------------------------------+
|agentName |original_dt|parsed_dt|user |text|newCol |
+----------+-----------+---------+-------+----+------------------------------+
|qwertyuiop|0 |0 |16102.0|0 |[qwertyuiop, 0, 0, 16102.0, 0]|
+----------+-----------+---------+-------+----+------------------------------+
J'espère que cela a aidé!
TL; DR Utilisez la fonction struct
avec l'opérateur Dataset.columns
.
Citer le scaladoc de struct function:
struct (colName: String, colNames: String *): Column Crée une nouvelle colonne struct qui compose plusieurs colonnes en entrée.
Il existe deux variantes: les noms de colonne basés sur des chaînes ou l'utilisation d'expressions Column
(ce qui vous donne plus de flexibilité pour le calcul que vous souhaitez appliquer aux colonnes concaténées).
De Dataset.columns :
columns: Array [String] Retourne tous les noms de colonnes sous forme de tableau.
Votre cas se présenterait alors comme suit:
scala> df.withColumn("newCol",
struct(df.columns.head, df.columns.tail: _*)).
show(false)
+----------+-----------+---------+-------+----+--------------------------+
|agentName |original_dt|parsed_dt|user |text|newCol |
+----------+-----------+---------+-------+----+--------------------------+
|qwertyuiop|0 |0 |16102.0|0 |[qwertyuiop,0,0,16102.0,0]|
+----------+-----------+---------+-------+----+--------------------------+
En général, vous pouvez fusionner plusieurs colonnes dataframe en une seule en utilisant un tableau.
df.select($"*",array($"col1",$"col2").as("newCol")) \\$"*" will capture all existing columns
Voici la solution en une ligne pour votre cas:
df.select($"*",array($"agentName",$"original_dt",$"parsed_dt",$"user", $"text").as("newCol"))
Vous pouvez utiliser la fonction udf
pour concaténer tous les columns
en un. Tout ce que vous avez à faire est de définir une fonction udf
et de transmettre toutes les columns
que vous souhaitez concaténer à la fonction udf
et d'appeler la fonction udf
à l'aide de la fonction .withColumn
de dataframe
Ou
Vous pouvez utiliser la fonction concat_ws(Java.lang.String sep, Column... exprs)
disponible pour le cadre de données.
var df = Seq(("qwertyuiop",0,0,16102.0,0))
.toDF("agentName","original_dt","parsed_dt","user","text")
df.withColumn("newCol", concat_ws(",",$"agentName",$"original_dt",$"parsed_dt",$"user",$"text"))
df.show(false)
Vous donnera la sortie en tant que
+----------+-----------+---------+-------+----+------------------------+
|agentName |original_dt|parsed_dt|user |text|newCol |
+----------+-----------+---------+-------+----+------------------------+
|qwertyuiop|0 |0 |16102.0|0 |qwertyuiop,0,0,16102.0,0|
+----------+-----------+---------+-------+----+------------------------+
Cela vous donnera le résultat que vous voulez