J'essaie de créer dynamiquement une ligne dans pySpark 1.6.1, puis de la construire dans une trame de données. L'idée générale est d'étendre les résultats de describe
pour inclure, par exemple, le biais et le kurtosis. Voici ce que je pensais que cela devrait fonctionner:
from pyspark.sql import Row
row_dict = {'C0': -1.1990072635132698,
'C3': 0.12605772684660232,
'C4': 0.5760856026559944,
'C5': 0.1951877800894315,
'C6': 24.72378589441825,
'summary': 'kurtosis'}
new_row = Row(row_dict)
Mais cela renvoie TypeError: sequence item 0: expected string, dict found
ce qui est une erreur assez claire. Ensuite, j'ai trouvé que si je définissais d'abord les champs Row, je pouvais utiliser un dict:
r = Row('summary', 'C0', 'C3', 'C4', 'C5', 'C6')
r(row_dict)
> Row(summary={'summary': 'kurtosis', 'C3': 0.12605772684660232, 'C0': -1.1990072635132698, 'C6': 24.72378589441825, 'C5': 0.1951877800894315, 'C4': 0.5760856026559944})
Ce serait une belle étape, sauf qu'il ne semble pas que je puisse spécifier dynamiquement les champs dans Row
. J'ai besoin que cela fonctionne pour un nombre inconnu de lignes avec des noms inconnus. Selon la documentation, vous pouvez réellement aller dans l'autre sens:
>>> Row(name="Alice", age=11).asDict() == {'name': 'Alice', 'age': 11}
True
Il semble donc que je devrais être en mesure de le faire. Il semble également que certaines fonctionnalités obsolètes d'anciennes versions le permettent, par exemple ici . Y a-t-il un équivalent plus actuel qui me manque?
Vous pouvez utiliser le déballage des arguments de mots clés comme suit:
Row(**row_dict)
## Row(C0=-1.1990072635132698, C3=0.12605772684660232, C4=0.5760856026559944,
## C5=0.1951877800894315, C6=24.72378589441825, summary='kurtosis')
Il est important de noter qu'il trie les données en interne par clé pour résoudre problèmes avec les anciennes Python .
Si le dict n'est pas aplati, vous pouvez le convertir récursivement en ligne.
def as_row(obj):
if isinstance(obj, dict):
dictionary = {k: as_row(v) for k, v in obj.items()}
return Row(**dictionary)
Elif isinstance(obj, list):
return [as_row(v) for v in obj]
else:
return obj