CollectionExpr représente un ensemble de données bidimensionnel dans l'API PyODPS DataFrame, équivalent à une table MaxCompute ou à une feuille de calcul. Les objets DataFrame sont également des objets CollectionExpr. CollectionExpr prend en charge les opérations sur les colonnes, le filtrage des données et la transformation des données.
Prérequis
Avant de commencer, assurez-vous d'avoir :
Une table nommée
pyodps_iris. Pour plus d'informations, consultez la section « Traitement des données DataFrame » de la rubrique Prise en mainUn objet DataFrame. Pour plus d'informations, consultez la section « Créer un objet DataFrame à partir d'une table MaxCompute » de la rubrique Créer un objet DataFrame
Récupérer les types de colonnes
Utilisez l'attribut dtypes pour obtenir les types de toutes les colonnes d'un CollectionExpr. Il renvoie un type Schema.
print(iris.dtypes)
Sortie :
odps.Schema {
sepallength float64
sepalwidth float64
petallength float64
petalwidth float64
name string
}
Sélectionner, ajouter et supprimer des colonnes
Le tableau suivant indique la syntaxe à utiliser en fonction de votre objectif :
| Objectif | Syntaxe recommandée | Version PyODPS |
|---|---|---|
| Sélectionner des colonnes spécifiques | expr[col1, col2] |
Toutes les versions |
| Exclure des colonnes | exclude(col1, col2) |
Toutes les versions |
| Ajouter une colonne calculée | iris['new_col'] = expr |
0.7.2+ |
| Écraser une colonne existante | iris['col'] = new_expr |
0.7.2+ |
| Supprimer une colonne | del iris['col'] |
0.7.2+ |
| Mise à jour conditionnelle d'une colonne | iris[condition, 'col'] = expr |
0.7.2+ |
| Ajouter une colonne constante | iris['col'] = value |
0.7.12+ |
| Renommer lors de la sélection | select(col, new_name=expr) |
Toutes les versions |
Sélectionner des colonnes
Utilisez expr[columns] pour sélectionner des colonnes spécifiques d'un CollectionExpr.
print(iris['name', 'sepallength'].head(5))
Sortie :
name sepallength
0 Iris-setosa 4.9
1 Iris-setosa 4.7
2 Iris-setosa 4.6
3 Iris-setosa 5.0
4 Iris-setosa 5.4
Pour sélectionner une seule colonne et renvoyer une Collection (et non une Sequence), ajoutez une virgule finale ou utilisez des doubles crochets :iris[iris.sepallength,]ouiris[[iris.sepallength]]. Sans ces éléments, un objet Sequence est renvoyé à la place.
Supprimer des colonnes
Utilisation de exclude (toutes les versions de PyODPS) :
print(iris.exclude('sepallength', 'petallength')[:5].head(5))
Sortie :
sepalwidth petalwidth name
0 3.0 0.2 Iris-setosa
1 3.2 0.2 Iris-setosa
2 3.1 0.2 Iris-setosa
3 3.6 0.2 Iris-setosa
4 3.9 0.4 Iris-setosa
Utilisation de del (PyODPS 0.7.2+) :
del iris['sepallength']
del iris['petallength']
print(iris[:5].head(5))
Sortie :
sepalwidth petalwidth name
0 3.0 0.2 Iris-setosa
1 3.2 0.2 Iris-setosa
2 3.1 0.2 Iris-setosa
3 3.6 0.2 Iris-setosa
4 3.9 0.4 Iris-setosa
Ajouter des colonnes
Utilisation de la syntaxe d'affectation (PyODPS 0.7.2+, recommandé) :
iris['sepalwidthplus1'] = iris.sepalwidth + 1
print(iris.head(5))
Sortie :
sepallength sepalwidth petallength petalwidth name \
0 4.9 3.0 1.4 0.2 Iris-setosa
1 4.7 3.2 1.3 0.2 Iris-setosa
2 4.6 3.1 1.5 0.2 Iris-setosa
3 5.0 3.6 1.4 0.2 Iris-setosa
4 5.4 3.9 1.7 0.4 Iris-setosa
sepalwidthplus1
0 4.0
1 4.2
2 4.1
3 4.6
4 4.9
Utilisation de expr[expr, new_sequence] (toutes les versions) : Crée une nouvelle Collection avec la colonne supplémentaire ajoutée à la fin. Si la nouvelle colonne porte le même nom qu'une colonne existante, renommez-la pour éviter les conflits.
print(iris[iris, (iris.sepalwidth + 1).rename('sepalwidthplus1')].head(5))
Sortie :
sepallength sepalwidth petallength petalwidth name \
0 4.9 3.0 1.4 0.2 Iris-setosa
1 4.7 3.2 1.3 0.2 Iris-setosa
2 4.6 3.1 1.5 0.2 Iris-setosa
3 5.0 3.6 1.4 0.2 Iris-setosa
4 5.4 3.9 1.7 0.4 Iris-setosa
sepalwidthplus1
0 4.0
1 4.2
2 4.1
3 4.6
4 4.9
Ajouter et supprimer des colonnes simultanément
Écraser une colonne existante (PyODPS 0.7.2+) :
iris['sepalwidth'] = iris.sepalwidth * 2
print(iris.head(5))
Sortie :
sepallength sepalwidth petallength petalwidth name
0 4.9 6.0 1.4 0.2 Iris-setosa
1 4.7 6.4 1.3 0.2 Iris-setosa
2 4.6 6.2 1.5 0.2 Iris-setosa
3 5.0 7.2 1.4 0.2 Iris-setosa
4 5.4 7.8 1.7 0.4 Iris-setosa
Utilisation de exclude avec une nouvelle colonne (toutes les versions) : Exclut la colonne d'origine et ajoute la version transformée, ce qui évite tout besoin de renommage.
print(iris[iris.exclude('sepalwidth'), iris.sepalwidth * 2].head(5))
Sortie :
sepallength petallength petalwidth name sepalwidth
0 4.9 1.4 0.2 Iris-setosa 6.0
1 4.7 1.3 0.2 Iris-setosa 6.4
2 4.6 1.5 0.2 Iris-setosa 6.2
3 5.0 1.4 0.2 Iris-setosa 7.2
4 5.4 1.7 0.4 Iris-setosa 7.8
Utilisation de select (toutes les versions) : Similaire à exclude avec une nouvelle colonne, mais permet de renommer le résultat en une seule étape à l'aide d'arguments par mot-clé.
print(iris.select('name', sepalwidthminus1=iris.sepalwidth - 1).head(5))
Sortie :
name sepalwidthminus1
0 Iris-setosa 2.0
1 Iris-setosa 2.2
2 Iris-setosa 2.1
3 Iris-setosa 2.6
4 Iris-setosa 2.9
Utilisation d'une expression lambda : Transmettez une fonction lambda qui prend le résultat de l'opération précédente comme paramètre. PyODPS évalue la fonction lambda et substitue les colonnes valides de cette Collection.
print(iris['name', 'petallength'][[lambda x: x.name]].head(5))
Sortie :
name
0 Iris-setosa
1 Iris-setosa
2 Iris-setosa
3 Iris-setosa
4 Iris-setosa
Mise à jour conditionnelle d'une colonne (PyODPS 0.7.2+) : Mettez à jour une colonne uniquement pour les lignes correspondant à une condition.
iris[iris.sepallength > 5.0, 'sepalwidth'] = iris.sepalwidth * 2
print(iris.head(5))
Sortie :
sepallength sepalwidth petallength petalwidth name
0 4.9 3.0 1.4 0.2 Iris-setosa
1 4.7 3.2 1.3 0.2 Iris-setosa
2 4.6 3.1 1.5 0.2 Iris-setosa
3 5.0 3.6 1.4 0.2 Iris-setosa
4 5.4 7.8 1.7 0.4 Iris-setosa
Introduire des constantes et des nombres aléatoires
Ajouter une colonne constante
Syntaxe simple (PyODPS 0.7.12+, recommandé) : Affectez directement une valeur littérale à une nouvelle colonne.
iris['id'] = 1
print(iris.head(5))
Sortie :
sepallength sepalwidth petallength petalwidth name id
0 4.9 3.0 1.4 0.2 Iris-setosa 1
1 4.7 3.2 1.3 0.2 Iris-setosa 1
2 4.6 3.1 1.5 0.2 Iris-setosa 1
3 5.0 3.6 1.4 0.2 Iris-setosa 1
4 5.4 3.9 1.7 0.4 Iris-setosa 1
La syntaxe simple ne peut pas déduire automatiquement le type des valeurs nulles. Pour ajouter une colonne nulle, utilisez NullScalar avec un type explicite.
from odps.df import NullScalar
iris['null_col'] = NullScalar('float')
print(iris.head(5))
Sortie :
sepallength sepalwidth petallength petalwidth name null_col
0 4.9 3.0 1.4 0.2 Iris-setosa None
1 4.7 3.2 1.3 0.2 Iris-setosa None
2 4.6 3.1 1.5 0.2 Iris-setosa None
3 5.0 3.6 1.4 0.2 Iris-setosa None
4 5.4 3.9 1.7 0.4 Iris-setosa None
Utilisation de Scalar (toutes les versions) : Encapsulez une constante avec Scalar et spécifiez manuellement le nom de la colonne.
from odps.df import Scalar
print(iris[iris, Scalar(1).rename('id')][:5].head(5))
Sortie :
sepallength sepalwidth petallength petalwidth name id
0 4.9 3.0 1.4 0.2 Iris-setosa 1
1 4.7 3.2 1.3 0.2 Iris-setosa 1
2 4.6 3.1 1.5 0.2 Iris-setosa 1
3 5.0 3.6 1.4 0.2 Iris-setosa 1
4 5.4 3.9 1.7 0.4 Iris-setosa 1
Pour ajouter une colonne nulle avec un type explicite :
from odps.df import NullScalar
print(iris[iris, NullScalar('float').rename('fid')][:5].head(5))
Sortie :
sepallength sepalwidth petallength petalwidth name fid
0 4.9 3.0 1.4 0.2 Iris-setosa None
1 4.7 3.2 1.3 0.2 Iris-setosa None
2 4.6 3.1 1.5 0.2 Iris-setosa None
3 5.0 3.6 1.4 0.2 Iris-setosa None
4 5.4 3.9 1.7 0.4 Iris-setosa None
Ajouter une colonne de nombres aléatoires
Utilisez RandomScalar pour ajouter une colonne de valeurs FLOAT aléatoires comprises entre 0 et 1, avec une valeur unique par ligne. Le paramètre facultatif est une graine aléatoire.
from odps.df import RandomScalar
iris[iris, RandomScalar().rename('rand_val')][:5]
Sortie :
sepallength sepalwidth petallength petalwidth name rand_val
0 4.9 3.0 1.4 0.2 Iris-setosa 0.000471
1 4.7 3.2 1.3 0.2 Iris-setosa 0.799520
2 4.6 3.1 1.5 0.2 Iris-setosa 0.834609
3 5.0 3.6 1.4 0.2 Iris-setosa 0.106921
4 5.4 3.9 1.7 0.4 Iris-setosa 0.763442
Filtrer les données
Filtrez les lignes à l'aide d'opérateurs standard, de la méthode filter, de la méthode query ou d'expressions lambda.
Dans les expressions de filtre standard, utilisez&pour ET|pour OU — les mots-clés Pythonandetorne sont pas pris en charge. La méthodequeryaccepte les deux.
Filtrer par condition :
print(iris[iris.sepallength > 5].head(5))
Sortie :
sepallength sepalwidth petallength petalwidth name
0 5.4 3.9 1.7 0.4 Iris-setosa
1 5.4 3.7 1.5 0.2 Iris-setosa
2 5.8 4.0 1.2 0.2 Iris-setosa
3 5.7 4.4 1.5 0.4 Iris-setosa
4 5.4 3.9 1.3 0.4 Iris-setosa
ET (&) :
print(iris[(iris.sepallength < 5) & (iris['petallength'] > 1.5)].head(5))
Sortie :
sepallength sepalwidth petallength petalwidth name
0 4.8 3.4 1.6 0.2 Iris-setosa
1 4.8 3.4 1.9 0.2 Iris-setosa
2 4.7 3.2 1.6 0.2 Iris-setosa
3 4.8 3.1 1.6 0.2 Iris-setosa
4 4.9 2.4 3.3 1.0 Iris-versicolor
OU (|) :
print(iris[(iris.sepalwidth < 2.5) | (iris.sepalwidth > 4)].head(5))
Sortie :
sepallength sepalwidth petallength petalwidth name
0 5.7 4.4 1.5 0.4 Iris-setosa
1 5.2 4.1 1.5 0.1 Iris-setosa
2 5.5 4.2 1.4 0.2 Iris-setosa
3 4.5 2.3 1.3 0.3 Iris-setosa
4 5.5 2.3 4.0 1.3 Iris-versicolor
NON (~) :
print(iris[~(iris.sepalwidth > 3)].head(5))
Sortie :
sepallength sepalwidth petallength petalwidth name
0 4.9 3.0 1.4 0.2 Iris-setosa
1 4.4 2.9 1.4 0.2 Iris-setosa
2 4.8 3.0 1.4 0.1 Iris-setosa
3 4.3 3.0 1.1 0.1 Iris-setosa
4 5.0 3.0 1.6 0.2 Iris-setosa
Méthode filter avec plusieurs conditions : Le passage de plusieurs arguments à filter équivaut à les combiner avec &.
print(iris.filter(iris.sepalwidth > 3.5, iris.sepalwidth < 4).head(5))
Sortie :
sepallength sepalwidth petallength petalwidth name
0 5.0 3.6 1.4 0.2 Iris-setosa
1 5.4 3.9 1.7 0.4 Iris-setosa
2 5.4 3.7 1.5 0.2 Iris-setosa
3 5.4 3.9 1.3 0.4 Iris-setosa
4 5.7 3.8 1.7 0.3 Iris-setosa
Expression lambda pour les opérations chaînées :
print(iris[iris.sepalwidth > 3.8]['name', lambda x: x.sepallength + 1].head(5))
Sortie :
name sepallength
0 Iris-setosa 6.4
1 Iris-setosa 6.8
2 Iris-setosa 6.7
3 Iris-setosa 6.4
4 Iris-setosa 6.2
Colonne BOOLEAN comme filtre : Lorsqu'une Collection contient une colonne BOOLEAN, utilisez cette colonne directement comme condition de filtre.
# Check the schema
print(df.dtypes)
# odps.Schema {
# a boolean
# b int64
# }
# Filter using the boolean column
print(df[df.a])
# a b
# 0 True 1
# 1 True 3
Les exemples suivants montrent la différence entre la récupération d'une seule colonne et son utilisation comme filtre :
df[df.a, ] # Retrieve a one-column Collection
df[[df.a]] # Retrieve a one-column Collection
df.select(df.a) # Retrieve a one-column Collection explicitly
df[df.a] # Use column a (BOOLEAN) as a filter condition
df.a # Retrieve a column from a Collection
df['a'] # Retrieve a column from a Collection
Filtrer avec query
La méthode query accepte les conditions de filtre sous forme d'expression de chaîne, de manière similaire à Pandas. Référencez directement les noms de colonnes dans la chaîne ; préfixez les variables locales par @.
print(iris.query("(sepallength < 5) and (petallength > 1.5)").head(5))
Sortie :
sepallength sepalwidth petallength petalwidth name
0 4.8 3.4 1.6 0.2 Iris-setosa
1 4.8 3.4 1.9 0.2 Iris-setosa
2 4.7 3.2 1.6 0.2 Iris-setosa
3 4.8 3.1 1.6 0.2 Iris-setosa
4 4.9 2.4 3.3 1.0 Iris-versicolor
Utilisez @ pour référencer une variable locale dans une chaîne de requête :
var = 4
print(iris.query("(sepalwidth < 2.5) | (sepalwidth > @var)").head(5))
Sortie :
sepallength sepalwidth petallength petalwidth name
0 5.7 4.4 1.5 0.4 Iris-setosa
1 5.2 4.1 1.5 0.1 Iris-setosa
2 5.5 4.2 1.4 0.2 Iris-setosa
3 4.5 2.3 1.3 0.3 Iris-setosa
4 5.5 2.3 4.0 1.3 Iris-versicolor
La méthode query prend en charge la syntaxe suivante :
| Syntaxe | Description | |
|---|---|---|
| name | Noms de colonnes (sans préfixe @). Utilisez @variable pour référencer une variable Python locale. |
|
| operator | +, -, *, /, //, %, **, ==, !=, <, <=, >, >=, in, not in |
|
| bool | ET : & ou and. OU : ` |
or ou`. |
| attribute | Attributs d'objet | |
| index, slice, subscript | Opérations de découpage |
Convertir une colonne en lignes
Utilisez explode pour développer une colonne LIST ou MAP en plusieurs lignes. Vous pouvez également utiliser la méthode apply pour une sortie multiligne. Vous pouvez éclater une ou plusieurs colonnes simultanément. Si une ligne d'entrée ne produit aucune sortie (par exemple, une liste vide), la ligne est exclue par défaut. Définissez keep_nulls=True pour conserver ces lignes avec des valeurs nulles.
Pour plus d'informations sur l'utilisation de explode pour une sortie multiligne, consultez la section « Opérations liées aux collections » de la rubrique Opérations sur les colonnes.
Données d'exemple :
print(df)
# id a b
# 0 1 [a1, b1] [a2, b2, c2]
# 1 2 [c1] [d2, e2]
Éclater une colonne, conserver l'autre telle quelle :
print(df[df.id, df.a.explode(), df.b])
Sortie :
id a b
0 1 a1 [a2, b2, c2]
1 1 b1 [a2, b2, c2]
2 2 c1 [d2, e2]
Éclater deux colonnes simultanément :
print(df[df.id, df.a.explode(), df.b.explode()])
Sortie :
id a b
0 1 a1 a2
1 1 a1 b2
2 1 a1 c2
3 1 b1 a2
4 1 b1 b2
5 1 b1 c2
6 2 c1 d2
7 2 c1 e2
keep_nulls=True — conserver les lignes avec une entrée vide :
print(df)
# id a
# 0 1 [a1, b1]
# 1 2 []
# Without keep_nulls: row 2 is dropped
print(df[df.id, df.a.explode()])
# id a
# 0 1 a1
# 1 1 b1
# With keep_nulls=True: row 2 is retained with a null value
print(df[df.id, df.a.explode(keep_nulls=True)])
# id a
# 0 1 a1
# 1 1 b1
# 2 2 None
Limites de sortie
Limitez le nombre de lignes renvoyées à l'aide de la syntaxe de découpage ou de la méthode limit.
Syntaxe de découpage :
print(iris[:3].execute())
Sortie :
sepallength sepalwidth petallength petalwidth name
0 4.9 3.0 1.4 0.2 Iris-setosa
1 4.7 3.2 1.3 0.2 Iris-setosa
2 4.6 3.1 1.5 0.2 Iris-setosa
Méthode limit :
print(iris.limit(3).execute())
Sortie :
sepallength sepalwidth petallength petalwidth name
0 4.9 3.0 1.4 0.2 Iris-setosa
1 4.7 3.2 1.3 0.2 Iris-setosa
2 4.6 3.1 1.5 0.2 Iris-setosa
Dans le backend SQL MaxCompute, les opérations de découpage ne prennent pas en chargestartnistep— seulelimitest prise en charge. Les opérations de découpage s'appliquent uniquement aux objets Collection, pas aux objets Sequence.