Pandas dataframe.query 方法语法

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/41922130/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-14 02:52:55  来源:igfitidea点击:

Pandas dataframe.query method syntax

pythonpandas

提问by ade1e

Question:

题:

I would like to gain a better understanding of the Pandas DataFrame.querymethod and what the following expression represents:

我想更好地了解 Pandas DataFrame.query方法以及以下表达式所代表的含义:

match = dfDays.query('index > @x.name & price >= @x.target')

What does @x.namerepresent?

什么是@x.name代表?

I understand what the resulting output is for this code (a new column with pandas.tslib.Timestampdata) but don't have a clear understanding of the expression used to get this end result.

我了解此代码(包含pandas.tslib.Timestamp数据的新列)的结果输出是什么,但对用于获得此最终结果的表达式没有清晰的理解。

Data:

数据:

From here:

从这里:

Vectorised way to query date and price data

查询日期和价格数据的矢量化方式

np.random.seed(seed=1)
rng = pd.date_range('1/1/2000', '2000-07-31',freq='D')
weeks = np.random.uniform(low=1.03, high=3, size=(len(rng),))
ts2 = pd.Series(weeks
               ,index=rng)
dfDays = pd.DataFrame({'price':ts2})
dfWeeks = dfDays.resample('1W-Mon').first()
dfWeeks['target'] = (dfWeeks['price'] + .5).round(2)

def find_match(x):
    match = dfDays.query('index > @x.name & price >= @x.target')
    if not match.empty:
        return match.index[0]

dfWeeks.assign(target_hit=dfWeeks.apply(find_match, 1))

采纳答案by piRSquared

Everything @MaxU said is perfect!

@MaxU 所说的一切都是完美的!

I wanted to add some context to the specific problem that this was applied to.

我想为所应用的特定问题添加一些上下文。

find_match

find_match

This is a helper function that is used in the dataframe dfWeeks.apply. Two things to note:

这是在 dataframe 中使用的辅助函数dfWeeks.apply。有两点需要注意:

  1. find_matchtakes a single argument x. This will be a single row of dfWeeks.
    • Each row is a pd.Seriesobject and each row will be passed through this function. This is the nature of using apply.
    • When applypasses this row to the helper function, the row has a nameattribute that is equal to the index value for that row in the dataframe. In this case, I know that the index value is a pd.Timestampand I'll use it to do the comparing I need to do.
  2. find_matchreferences dfDayswhich is outside the scope of find_matchitself.
  1. find_match需要一个参数x。这将是dfWeeks.
    • 每一行都是一个pd.Series对象,每一行都将通过这个函数传递。这是使用apply.
    • apply将此行传递给辅助函数时,该行的name属性等于数据帧中该行的索引值。在这种情况下,我知道索引值是 a pd.Timestamp,我将用它来做我需要做的比较。
  2. find_matchdfDays超出find_match自身范围的引用。

I didn't have to use query... I like using query. It is my opinion that it makes some code prettier. The following function, as provided by the OP, could've been written differently

我不必使用query...我喜欢使用query. 我认为它使一些代码更漂亮。OP 提供的以下函数可以用不同的方式编写

def find_match(x):
    """Original"""
    match = dfDays.query('index > @x.name & price >= @x.target')
    if not match.empty:
        return match.index[0]

dfWeeks.assign(target_hit=dfWeeks.apply(find_match, 1))

find_match_alt

find_match_alt

Or we could've done this, which may help to explain what the querystring is doing above

或者我们可以这样做,这可能有助于解释query上面的字符串在做什么

def find_match_alt(x):
    """Alternative to OP's"""
    date_is_afterwards = dfDays.index > x.name
    price_target_is_met = dfDays.price >= x.target
    both_are_true = price_target_is_met & date_is_afterwards
    if (both_are_true).any():
        return dfDays[both_are_true].index[0]

dfWeeks.assign(target_hit=dfWeeks.apply(find_match_alt, 1))


Comparing these two functions should give good perspective.

比较这两个函数应该会给出很好的视角。

回答by MaxU

@x.name- @helps .query()to understand that xis an external object (doesn't belong to the DataFrame for which the query() method was called). In this case xis a DataFrame. It could be a scalar value as well.

@x.name-@有助于.query()理解这x是一个外部对象(不属于调用 query() 方法的 DataFrame)。在这种情况下x是一个 DataFrame。它也可以是一个标量值。

I hope this small demonstration will help you to understand it:

我希望这个小演示能帮助你理解它:

In [79]: d1
Out[79]:
   a  b  c
0  1  2  3
1  4  5  6
2  7  8  9

In [80]: d2
Out[80]:
   a   x
0  1  10
1  7  11

In [81]: d1.query("a in @d2.a")
Out[81]:
   a  b  c
0  1  2  3
2  7  8  9

In [82]: d1.query("c < @d2.a")
Out[82]:
   a  b  c
1  4  5  6

Scalar x:

标量x

In [83]: x = 9

In [84]: d1.query("c == @x")
Out[84]:
   a  b  c
2  7  8  9