Problème de filtrage de ma trame de données de résultat avec une or
condition Je veux que mon résultat df
extrait toutes les var
valeurs de colonne supérieures à 0,25 et inférieures à -0,25.
Cette logique ci-dessous me donne une valeur de vérité ambiguë mais elle fonctionne lorsque je divise ce filtrage en deux opérations distinctes. Que se passe-t-il ici? Je ne sais pas où utiliser le suggéré a.empty(), a.bool(), a.item(),a.any() or a.all()
.
result = result[(result['var']>0.25) or (result['var']<-0.25)]
|
au lieu deor
abs(result['var'])>0.25
Réponses:
Les instructions
or
etand
python nécessitenttruth
-values. Pourpandas
ceux-ci sont considérés comme ambigus, vous devez donc utiliser les opérations "au niveau du bit"|
(ou) ou&
(et):Ceux-ci sont surchargés pour ce type de infrastructures de données pour produire l'élément
or
(ouand
).Juste pour ajouter quelques explications à cette déclaration:
L'exception est levée lorsque vous voulez obtenir l'
bool
unpandas.Series
:Ce que vous avez touché était un endroit où l'opérateur a implicitement converti les opérandes
bool
(vous l'avez utiliséor
mais cela arrive aussi pourand
,if
etwhile
):En plus de ces 4 déclarations il y a plusieurs fonctions de python qui cachent des
bool
appels (commeany
,all
,filter
, ...) ceux - ci ne sont généralement pas problématique ,pandas.Series
mais pour être complet que je voulais mentionner ces derniers .Dans votre cas, l'exception n'est pas vraiment utile, car elle ne mentionne pas les bonnes alternatives . Pour
and
etor
vous pouvez utiliser (si vous voulez des comparaisons par élément):numpy.logical_or
:ou simplement l'
|
opérateur:numpy.logical_and
:ou simplement l'
&
opérateur:Si vous utilisez les opérateurs, assurez-vous de définir correctement vos parenthèses en raison de la priorité de l'opérateur .
Il existe plusieurs fonctions logiques numpy qui devraient fonctionner
pandas.Series
.Les alternatives mentionnées dans l'exception sont plus adaptées si vous l'avez rencontré lors de l'exécution de
if
ouwhile
. Je vais expliquer brièvement chacun de ces éléments:Si vous souhaitez vérifier si votre série est vide :
Python interprète normalement le
len
GTH des conteneurs (commelist
,tuple
, ...) comme valeur de vérité si elle n'a pas d' interprétation booléenne explicite. Donc, si vous voulez la vérification de type python, vous pouvez faire:if x.size
ouif not x.empty
au lieu deif x
.Si votre
Series
contient une et une seule valeur booléenne:Si vous souhaitez vérifier le premier et le seul élément de votre série (comme
.bool()
mais fonctionne même pour le contenu non booléen):Si vous souhaitez vérifier si tout ou partie d' un élément n'est pas nul, non vide ou non faux:
la source
and
,or
etnot
en Python. Ces opérateurs utilisent directement ce qui se trouvebool
sur les retours d'opérandes. Et d'une certaine manière, Pandas / NumPy les a déjà surchargés,ValueError
car ils considèrent la valeur de vérité d'une telle structure de données comme ambiguë.Pour la logique booléenne, utilisez
&
et|
.Pour voir ce qui se passe, vous obtenez une colonne de booléens pour chaque comparaison, par exemple
Lorsque vous avez plusieurs critères, vous obtiendrez plusieurs colonnes retournées. C'est pourquoi la logique de jointure est ambiguë. L'utilisation
and
ou leor
traitement de chaque colonne séparément, vous devez donc d'abord réduire cette colonne à une seule valeur booléenne. Par exemple, pour voir si une valeur ou toutes les valeurs de chacune des colonnes sont vraies.Une façon compliquée de réaliser la même chose consiste à compresser toutes ces colonnes et à exécuter la logique appropriée.
Pour plus de détails, reportez-vous à l'indexation booléenne dans la documentation.
la source
Et bien les pandas utilisent bit & '' | ' et chaque condition doit être entourée d'un '()'
Par exemple les travaux suivants
Mais la même requête sans crochets appropriés ne
la source
Ou, vous pouvez également utiliser le module Opérateur. Des informations plus détaillées sont disponibles ici. Documents Python
la source
Cette excellente réponse explique très bien ce qui se passe et fournit une solution. Je voudrais ajouter une autre solution qui pourrait convenir dans des cas similaires: en utilisant la
query
méthode:Voir également http://pandas.pydata.org/pandas-docs/stable/indexing.html#indexing-query .
(Certains tests avec une trame de données avec laquelle je travaille actuellement suggèrent que cette méthode est un peu plus lente que l'utilisation des opérateurs au niveau du bit sur une série de booléens: 2 ms contre 870 µs)
Un avertissement : au moins une situation où ce n'est pas simple est lorsque les noms de colonnes sont des expressions python. J'avais des colonnes nommées
WT_38hph_IP_2
,WT_38hph_input_2
etlog2(WT_38hph_IP_2/WT_38hph_input_2)
et je voulais effectuer la requête suivante:"(log2(WT_38hph_IP_2/WT_38hph_input_2) > 1) and (WT_38hph_IP_2 > 20)"
J'ai obtenu la cascade d'exceptions suivante:
KeyError: 'log2'
UndefinedVariableError: name 'log2' is not defined
ValueError: "log2" is not a supported function
Je suppose que cela s'est produit parce que l'analyseur de requête essayait de créer quelque chose à partir des deux premières colonnes au lieu d'identifier l'expression avec le nom de la troisième colonne.
Une solution de contournement possible est proposée ici .
la source
J'ai rencontré la même erreur et j'ai été bloqué avec une trame de données pyspark pendant quelques jours, j'ai pu le résoudre avec succès en remplissant na valeurs avec 0 car je comparais les valeurs entières de 2 champs.
la source