web-dev-qa-db-fra.com

Comment changer une position de colonne dans un dataframe spark?

Je me demandais s'il était possible de changer la position d'une colonne dans un cadre de données, en réalité pour changer le schéma?

Justement si j'ai un dataframe comme [field1, field2, field3], et j'aimerais avoir [field1, field3, field2].

Je ne peux mettre aucun morceau de code. Imaginons que nous travaillions avec un cadre de données de cent colonnes, après quelques jointures et transformations, certaines de ces colonnes sont mal placées en ce qui concerne le schéma de la table de destination.

Comment déplacer une ou plusieurs colonnes, à savoir: comment changer le schéma?

27
obiwan kenobi

Vous pouvez obtenir les noms de colonne, les réorganiser comme vous le souhaitez, puis utiliser select sur le DataFrame d'origine pour en obtenir un nouveau avec cette nouvelle commande:

val columns: Array[String] = dataFrame.columns
val reorderedColumnNames: Array[String] = ??? // do the reordering you want
val result: DataFrame = dataFrame.select(reorderedColumnNames.head, reorderedColumnNames.tail: _*)
50
Tzach Zohar

La bibliothèque spark-daria a une méthode reorderColumns qui facilite la réorganisation des colonnes dans un DataFrame.

import com.github.mrpowers.spark.daria.sql.DataFrameExt._

val actualDF = sourceDF.reorderColumns(
  Seq("field1", "field3", "field2")
)

La méthode reorderColumns utilise la solution de @Rockie Yang sous le capot.

Si vous voulez obtenir l'ordre des colonnes de df1 pour égaler le classement des colonnes de df2, quelque chose comme ceci devrait fonctionner mieux que de coder en dur toutes les colonnes:

df1.reorderColumns(df2.columns)

La bibliothèque spark-daria définit également une transformation sortColumns pour trier les colonnes par ordre croissant ou décroissant (si vous ne souhaitez pas spécifier toute la colonne d'une séquence).

import com.github.mrpowers.spark.daria.sql.transformations._

df.transform(sortColumns("asc"))
5
Powers

Comme d'autres l'ont commenté, je suis curieux de savoir pourquoi vous le feriez, car l'ordre n'est pas pertinent lorsque vous pouvez interroger les colonnes par leur nom.

Quoi qu'il en soit, l'utilisation de select devrait donner l'impression que les colonnes ont été déplacées dans la description du schéma:

val data = Seq(
  ("a",       "hello", 1),
  ("b",       "spark", 2)
)
.toDF("field1", "field2", "field3")

data
 .show()

data
 .select("field3", "field2", "field1")
 .show()
5
Raphaël Brugier

Une toute petite version comparée à @Tzach Zohar

val cols = df.columns.map(df(_)).reverse
val reversedColDF = df.select(cols:_*)
5
Rockie Yang