Если условие python [duplicate]

Посмотрите пример в здесь , у Стивена есть ясный ответ для вас:

Так вот что происходит, начиная с метода верхнего уровня (Button1_Click for UI / MyController.Get для ASP.NET):

  1. Метод верхнего уровня вызывает GetJsonAsync (в контексте UI / ASP.NET).
  2. GetJsonAsync запускает REST запрос, вызвав HttpClient.GetStringAsync (все еще в контексте).
  3. GetStringAsync возвращает незавершенную задачу, указывая, что запрос REST не завершен.
  4. GetJsonAsync ожидает задачу, возвращенную GetStringAsync. Контекст захвачен и будет использоваться для продолжения использования метода GetJsonAsync позже. GetJsonAsync возвращает незавершенную задачу, указывая, что метод GetJsonAsync не завершен.
  5. Метод верхнего уровня синхронно блокирует задачу, возвращенную GetJsonAsync. Это блокирует контекстный поток.
  6. ... В конце концов, запрос REST завершится. Это завершает задачу, которая была возвращена GetStringAsync.
  7. Продолжение для GetJsonAsync теперь готово к запуску и ожидает, что контекст будет доступен, чтобы он мог выполняться в контексте.
  8. Тупик. Метод верхнего уровня блокирует поток контекста, ожидая завершения GetJsonAsync, и GetJsonAsync ожидает, что контекст будет бесплатным, чтобы он мог завершить. Для примера пользовательского интерфейса «контекст» представляет собой контекст пользовательского интерфейса; для примера ASP.NET «контекст» представляет собой контекст запроса ASP.NET.
  9. Еще одна ссылка, которую вы должны прочитать:

    Ожидание и пользовательский интерфейс, тупики! О, мой!

109
задан Uribe-Convers 8 April 2018 в 06:16
поделиться

4 ответа

Операторы python or и and требуют truth -значений. Для pandas они считаются двусмысленными, поэтому вы должны использовать «побитовые» операции | (или) или & (и):

result = result[(result['var']>0.25) | (result['var']<-0.25)]

Они перегружены для данных типов данных, чтобы получить element-wise or (или and).


Просто добавим еще одно объяснение этому утверждению:

Исключение выбрано, когда вы хотите получить bool в pandas.Series:

>>> import pandas as pd
>>> x = pd.Series([1])
>>> bool(x)
ValueError: The truth value of a Series is ambiguous. Use a.empty, a.bool(), a.item(), a.any() or a.all().

То, что вы нажали, было местом, где оператор неявно преобразовал операнды в bool (вы использовали or, но это также происходит для and, if и while):

>>> x or x
ValueError: The truth value of a Series is ambiguous. Use a.empty, a.bool(), a.item(), a.any() or a.all().
>>> x and x
ValueError: The truth value of a Series is ambiguous. Use a.empty, a.bool(), a.item(), a.any() or a.all().
>>> if x:
...     print('fun')
ValueError: The truth value of a Series is ambiguous. Use a.empty, a.bool(), a.item(), a.any() or a.all().
>>> while x:
...     print('fun')
ValueError: The truth value of a Series is ambiguous. Use a.empty, a.bool(), a.item(), a.any() or a.all().

Помимо этих 4-х инструкций существует несколько функций-питонов, которые скрывают некоторые вызовы bool (например, any, all, filter , ...) они обычно не проблематичны с pandas.Series, но для полноты я хотел упомянуть их.


В вашем случае исключение не очень полезно, потому что оно не упоминает правильные альтернативы. Для and и or вы можете использовать (если вы хотите сравнить по элементам):

  • numpy.logical_or :
    >>> import numpy as np
    >>> np.logical_or(x, y)
    
    или просто |:
    >>> x | y
    
  • numpy.logical_and :
    >>> np.logical_and(x, y)
    
    или просто оператор &:
    >>> x & y
    

Если вы используете операторы, затем убедитесь, что вы правильно установили свою скобку из-за приоритета оператора .

Есть несколько логических функций numpy , которые должен работать pandas.Series.


Альтернативы, упомянутые в Исключении, более подходят, если вы столкнулись с этим при выполнении if или while. Вкратце объясню каждый из них:

  • Если вы хотите проверить, является ли ваша серия пустой:
    >>> x = pd.Series([])
    >>> x.empty
    True
    >>> x = pd.Series([1])
    >>> x.empty
    False
    
    Python обычно интерпретирует контейнеры len gth (например, list, tuple, ...) как значение истины, если оно не имеет явной булевой интерпретации. Поэтому, если вы хотите выполнить проверку типа python, вы можете сделать: if x.size или if not x.empty вместо if x.
  • Если ваш Series содержит одно и только одно логическое значение:
    >>> x = pd.Series([100])
    >>> (x > 50).bool()
    True
    >>> (x < 50).bool()
    False
    
  • Если вы хотите проверить первый и единственный элемент своей серии (например, .bool(), но работает даже для не логического содержимого):
    >>> x = pd.Series([100])
    >>> x.item()
    100
    
  • Если вы хотите проверить, все или любой элемент не равен нулю, не пусто или нет. False:
    >>> x = pd.Series([0, 1, 2])
    >>> x.all()   # because one element is zero
    False
    >>> x.any()   # because one (or more) elements are non-zero
    True
    
185
ответ дан MSeifert 15 August 2018 в 21:49
поделиться
  • 1
    О мой Бог! Ваш комментарий & quot; Если вы используете операторы, убедитесь, что вы правильно установили свою скобку из-за приоритета оператора & quot; наконец, решила проблему, которая сводила меня с ума. Очень важно и, в моем случае, игнорировать точку. Спасибо! – user4896331 18 October 2017 в 21:05
  • 2
    один из наиболее содержательных ответов, которые я прочитал в течение длительного времени – deadcode 24 January 2018 в 12:54
  • 3
    – Jonathan Petitcolas 30 August 2018 в 14:51

Для логической логики используйте & и |.

np.random.seed(0)
df = pd.DataFrame(np.random.randn(5,3), columns=list('ABC'))

>>> df
          A         B         C
0  1.764052  0.400157  0.978738
1  2.240893  1.867558 -0.977278
2  0.950088 -0.151357 -0.103219
3  0.410599  0.144044  1.454274
4  0.761038  0.121675  0.443863

>>> df.loc[(df.C > 0.25) | (df.C < -0.25)]
          A         B         C
0  1.764052  0.400157  0.978738
1  2.240893  1.867558 -0.977278
3  0.410599  0.144044  1.454274
4  0.761038  0.121675  0.443863

Чтобы узнать, что происходит, вы получаете столбец логических значений для каждого сравнения, например

df.C > 0.25
0     True
1    False
2    False
3     True
4     True
Name: C, dtype: bool

Когда у вас есть несколько критериев, вы получите несколько возвращенных столбцов. Вот почему логика объединения неоднозначна. Использование and или or обрабатывает каждый столбец отдельно, поэтому вам сначала нужно свести этот столбец к одному логическому значению. Например, чтобы увидеть, истинно ли любое значение или все значения в каждом столбце.

# Any value in either column is True?
(df.C > 0.25).any() or (df.C < -0.25).any()
True

# All values in either column is True?
(df.C > 0.25).all() or (df.C < -0.25).all()
False

Один из пронумерованных способов добиться того же самого - это объединить все эти столбцы вместе и выполнить соответствующие логика.

>>> df[[any([a, b]) for a, b in zip(df.C > 0.25, df.C < -0.25)]]
          A         B         C
0  1.764052  0.400157  0.978738
1  2.240893  1.867558 -0.977278
3  0.410599  0.144044  1.454274
4  0.761038  0.121675  0.443863

Для получения дополнительной информации см. Boolean Indexing в документах.

22
ответ дан Alexander 15 August 2018 в 21:49
поделиться

Этот отличный ответ очень хорошо объясняет, что происходит, и дает решение. Я хотел бы добавить другое решение, которое может быть подходящим в подобных случаях: с помощью метода query :

result = result.query("(var > 0.25) or (var < -0.25)")

См. Также http: // pandas. pydata.org/pandas-docs/stable/indexing.html#indexing-query.

(Некоторые тесты с фреймворком данных, с которыми я сейчас работаю, показывают, что этот метод немного медленнее, чем используя побитовые операторы в рядах булевых: 2 мс против 870 мкс)

Предупреждение: по крайней мере, одна ситуация, когда это не просто, когда имена столбцов являются выражениями python. Я имел столбцы с именами WT_38hph_IP_2, WT_38hph_input_2 и log2(WT_38hph_IP_2/WT_38hph_input_2) и хотел выполнить следующий запрос: "(log2(WT_38hph_IP_2/WT_38hph_input_2) > 1) and (WT_38hph_IP_2 > 20)"

Я получил следующее исключение:

  • KeyError: 'log2'
  • UndefinedVariableError: name 'log2' is not defined
  • ValueError: "log2" is not a supported function

Я предполагаю, что это произошло потому, что анализатор запросов пытался что-то сделать с первого два столбца вместо того, чтобы идентифицировать выражение с именем третьего столбца.

Предлагается возможное обходное решение здесь .

1
ответ дан bli 15 August 2018 в 21:49
поделиться

Или, альтернативно, вы можете использовать модуль Operator. Более подробная информация здесь Документы Python

import operator
import numpy as np
import pandas as pd
np.random.seed(0)
df = pd.DataFrame(np.random.randn(5,3), columns=list('ABC'))
df.loc[operator.or_(df.C > 0.25, df.C < -0.25)]

          A         B         C
0  1.764052  0.400157  0.978738
1  2.240893  1.867558 -0.977278
3  0.410599  0.144044  1.454274
4  0.761038  0.121675  0.4438
5
ответ дан Cảnh Toàn Nguyễn 15 August 2018 в 21:49
поделиться
Другие вопросы по тегам:

Похожие вопросы: