pandas.merge_asof#
- pandas.merge_asof(left, right, on=None, left_on=None, right_on=None, left_index=False, right_index=False, by=None, left_by=None, right_by=None, suffixes=('_x', '_y'), tolerance=None, allow_exact_matches=True, direction='backward')[源代码][源代码]#
按键距离执行合并。
这类似于左连接,只不过我们是匹配最近的键而不是相等的键。两个DataFrame都必须按键排序。
对于左 DataFrame 中的每一行:
“backward” 搜索选择右侧 DataFrame 中最后一行,其 ‘on’ 键小于或等于左侧的键。
“forward” 搜索选择右侧 DataFrame 中第一个 ‘on’ 键大于或等于左侧键的行。
“nearest” 搜索选择右侧 DataFrame 中其 ‘on’ 键在绝对距离上最接近左侧键的行。
可选地在使用 ‘on’ 搜索之前,通过 ‘by’ 匹配等效键。
- 参数:
- 左DataFrame 或命名 Series
第一个要合并的 pandas 对象。
- 右DataFrame 或命名 Series
第二个要合并的 pandas 对象。
- 开label
要连接的字段名。必须在两个DataFrame中都能找到。数据必须是已排序的。此外,这必须是一个数值列,例如日期时间类型、整数或浮点数。必须给出on或left_on/right_on。
- left_onlabel
左 DataFrame 中用于连接的字段名。
- right_onlabel
右DataFrame中用于连接的字段名。
- left_indexbool
使用左边DataFrame的索引作为连接键。
- right_indexbool
使用右侧DataFrame的索引作为连接键。
- 通过列名或列名列表
在进行合并操作之前,先在这些列上进行匹配。
- left_by列名
在左侧 DataFrame 中匹配的字段名称。
- right_by列名
在右侧 DataFrame 中匹配的字段名称。
- 后缀2-长度序列(元组、列表等)
分别应用于左侧和右侧重叠列名的后缀。
- toleranceint 或 timedelta, 可选, 默认 None
在此范围内选择asof容差;必须与合并索引兼容。
- allow_exact_matches布尔值, 默认为 True
如果为真,允许匹配相同的 ‘on’ 值(即小于等于 / 大于等于)
如果为 False,不匹配相同的 ‘on’ 值(即,严格小于 / 严格大于)。
- 方向‘backward’ (默认), ‘forward’, 或 ‘nearest’
是否搜索先前、后续或最接近的匹配项。
- 返回:
- DataFrame
两个合并对象的 DataFrame。
参见
合并
与数据库风格的连接合并。
merge_ordered
带有可选填充/插值的合并。
例子
>>> left = pd.DataFrame({"a": [1, 5, 10], "left_val": ["a", "b", "c"]}) >>> left a left_val 0 1 a 1 5 b 2 10 c
>>> right = pd.DataFrame({"a": [1, 2, 3, 6, 7], "right_val": [1, 2, 3, 6, 7]}) >>> right a right_val 0 1 1 1 2 2 2 3 3 3 6 6 4 7 7
>>> pd.merge_asof(left, right, on="a") a left_val right_val 0 1 a 1 1 5 b 3 2 10 c 7
>>> pd.merge_asof(left, right, on="a", allow_exact_matches=False) a left_val right_val 0 1 a NaN 1 5 b 3.0 2 10 c 7.0
>>> pd.merge_asof(left, right, on="a", direction="forward") a left_val right_val 0 1 a 1.0 1 5 b 6.0 2 10 c NaN
>>> pd.merge_asof(left, right, on="a", direction="nearest") a left_val right_val 0 1 a 1 1 5 b 6 2 10 c 7
我们也可以使用索引的 DataFrame。
>>> left = pd.DataFrame({"left_val": ["a", "b", "c"]}, index=[1, 5, 10]) >>> left left_val 1 a 5 b 10 c
>>> right = pd.DataFrame({"right_val": [1, 2, 3, 6, 7]}, index=[1, 2, 3, 6, 7]) >>> right right_val 1 1 2 2 3 3 6 6 7 7
>>> pd.merge_asof(left, right, left_index=True, right_index=True) left_val right_val 1 a 1 5 b 3 10 c 7
这是一个现实世界的时间序列示例
>>> quotes = pd.DataFrame( ... { ... "time": [ ... pd.Timestamp("2016-05-25 13:30:00.023"), ... pd.Timestamp("2016-05-25 13:30:00.023"), ... pd.Timestamp("2016-05-25 13:30:00.030"), ... pd.Timestamp("2016-05-25 13:30:00.041"), ... pd.Timestamp("2016-05-25 13:30:00.048"), ... pd.Timestamp("2016-05-25 13:30:00.049"), ... pd.Timestamp("2016-05-25 13:30:00.072"), ... pd.Timestamp("2016-05-25 13:30:00.075"), ... ], ... "ticker": [ ... "GOOG", ... "MSFT", ... "MSFT", ... "MSFT", ... "GOOG", ... "AAPL", ... "GOOG", ... "MSFT", ... ], ... "bid": [720.50, 51.95, 51.97, 51.99, 720.50, 97.99, 720.50, 52.01], ... "ask": [720.93, 51.96, 51.98, 52.00, 720.93, 98.01, 720.88, 52.03], ... } ... ) >>> quotes time ticker bid ask 0 2016-05-25 13:30:00.023 GOOG 720.50 720.93 1 2016-05-25 13:30:00.023 MSFT 51.95 51.96 2 2016-05-25 13:30:00.030 MSFT 51.97 51.98 3 2016-05-25 13:30:00.041 MSFT 51.99 52.00 4 2016-05-25 13:30:00.048 GOOG 720.50 720.93 5 2016-05-25 13:30:00.049 AAPL 97.99 98.01 6 2016-05-25 13:30:00.072 GOOG 720.50 720.88 7 2016-05-25 13:30:00.075 MSFT 52.01 52.03
>>> trades = pd.DataFrame( ... { ... "time": [ ... pd.Timestamp("2016-05-25 13:30:00.023"), ... pd.Timestamp("2016-05-25 13:30:00.038"), ... pd.Timestamp("2016-05-25 13:30:00.048"), ... pd.Timestamp("2016-05-25 13:30:00.048"), ... pd.Timestamp("2016-05-25 13:30:00.048"), ... ], ... "ticker": ["MSFT", "MSFT", "GOOG", "GOOG", "AAPL"], ... "price": [51.95, 51.95, 720.77, 720.92, 98.0], ... "quantity": [75, 155, 100, 100, 100], ... } ... ) >>> trades time ticker price quantity 0 2016-05-25 13:30:00.023 MSFT 51.95 75 1 2016-05-25 13:30:00.038 MSFT 51.95 155 2 2016-05-25 13:30:00.048 GOOG 720.77 100 3 2016-05-25 13:30:00.048 GOOG 720.92 100 4 2016-05-25 13:30:00.048 AAPL 98.00 100
默认情况下,我们采用报价的截止日期
>>> pd.merge_asof(trades, quotes, on="time", by="ticker") time ticker price quantity bid ask 0 2016-05-25 13:30:00.023 MSFT 51.95 75 51.95 51.96 1 2016-05-25 13:30:00.038 MSFT 51.95 155 51.97 51.98 2 2016-05-25 13:30:00.048 GOOG 720.77 100 720.50 720.93 3 2016-05-25 13:30:00.048 GOOG 720.92 100 720.50 720.93 4 2016-05-25 13:30:00.048 AAPL 98.00 100 NaN NaN
我们仅在报价时间和交易时间之间2毫秒内进行操作
>>> pd.merge_asof( ... trades, quotes, on="time", by="ticker", tolerance=pd.Timedelta("2ms") ... ) time ticker price quantity bid ask 0 2016-05-25 13:30:00.023 MSFT 51.95 75 51.95 51.96 1 2016-05-25 13:30:00.038 MSFT 51.95 155 NaN NaN 2 2016-05-25 13:30:00.048 GOOG 720.77 100 720.50 720.93 3 2016-05-25 13:30:00.048 GOOG 720.92 100 720.50 720.93 4 2016-05-25 13:30:00.048 AAPL 98.00 100 NaN NaN
我们只在报价时间和交易时间之间10毫秒内进行比较,并且我们排除时间上的精确匹配。然而,*之前*的数据会向前传播
>>> pd.merge_asof( ... trades, ... quotes, ... on="time", ... by="ticker", ... tolerance=pd.Timedelta("10ms"), ... allow_exact_matches=False, ... ) time ticker price quantity bid ask 0 2016-05-25 13:30:00.023 MSFT 51.95 75 NaN NaN 1 2016-05-25 13:30:00.038 MSFT 51.95 155 51.97 51.98 2 2016-05-25 13:30:00.048 GOOG 720.77 100 NaN NaN 3 2016-05-25 13:30:00.048 GOOG 720.92 100 NaN NaN 4 2016-05-25 13:30:00.048 AAPL 98.00 100 NaN NaN