将值从一个数据帧切片复制到另一个:使用“IndexSlice”的多索引熊猫数据帧的切片是不是总是一致地排序?

Posted

技术标签:

【中文标题】将值从一个数据帧切片复制到另一个:使用“IndexSlice”的多索引熊猫数据帧的切片是不是总是一致地排序?【英文标题】:Copying values from one dataframe slice to another: are slices from multi-indexed pandas dataframes using `IndexSlice` always ordered consistently?将值从一个数据帧切片复制到另一个:使用“IndexSlice”的多索引熊猫数据帧的切片是否总是一致地排序? 【发布时间】:2022-01-15 22:50:39 【问题描述】:

上下文

假设我有一个多索引数据框,如下所示:

import numpy as np
import pandas as pd

arrays = [
    ["bar", "bar", "baz", "baz", "foo", "foo", "qux", "qux"],
    ["one", "two", "one", "two", "one", "two", "one", "two"],
]
tuples = list(zip(*arrays))
index = pd.MultiIndex.from_tuples(tuples, names=["first", "second"])
data = np.array([
    [1, 2],
    [3, 4],
    [5, 6],
    [7, 8],
    [9, 10],
    [11, 12],
    [13, 14],
    [15, 16],
])
df = pd.DataFrame(data, index=index, columns=('a', 'b'))

看起来像这样:

               a   b
first second        
bar   one      1   2
      two      3   4
baz   one      5   6
      two      7   8
foo   one      9  10
      two     11  12
qux   one     13  14
      two     15  16

我想将第一级索引bar 的列a 的值复制到第一级索引qux 的同一列中,与索引的第二级对齐(这里称为second)。换句话说,我想从上面的数据帧中获取以下数据帧:

               a   b
first second        
bar   one      1   2
      two      3   4
baz   one      5   6
      two      7   8
foo   one      9  10
      two     11  12
qux   one      1  14  # <-- column a changed to match first = bar for second = one
      two      3  16  # <-- column a changed to match first = bar for second = two

根据对this 问题的回答,我理解我可以通过将pd.IndexSlice.loc.values 结合使用来完成此操作,如下所示:

df.loc[pd.IndexSlice['qux', :], 'a'] = df.loc[pd.IndexSlice['bar', :], 'a'].values

我不喜欢这样(也许/可能不合理),因为我不清楚这些值是否会总是在第二个索引级别上对齐:

问题:

我能否保证上述分配(使用.values访问)将始终在多索引的第二级对齐?

如果没有,有没有办法实现我想要实现的目标?

【问题讨论】:

“在第二个索引级别对齐”是什么意思? 在上面的例子中,我很想知道上面通过loc访问的切片是否总是被排序为onetwo(在multi-指数)。一般来说,我很想知道这是否适用于类似问题的两个级别以上的值。 不,它不会对齐,因为通过使用.values(顺便说一句,.to_numpy() 已弃用),您会删除所有索引/列信息。 我认为真正的问题是“我怎样才能做出始终在多索引的第二级对齐的分配?” 谢谢两位。我确实怀疑是这种情况(因此提出了问题)。我对@hpchavaz 描述的问题感兴趣。 【参考方案1】:

不,它不会对齐,因为通过使用.value(顺便说一句,不推荐使用.to_numpy()),它返回底层的numpy数组,你删除所有索引/列信息,所以无法对齐。

这是保持对齐的一种解决方案:

df.loc['qux', 'a'] = df.loc['qux', 'a'].index.map(df.loc['bar', 'a'].to_dict())

输出:

>>> df
                 a   b
first second          
bar   two      1.0   2
      one      3.0   4
baz   one      5.0   6
      two      7.0   8
foo   one      9.0  10
      two     11.0  12
qux   one      3.0  14
      two      1.0  16

【讨论】:

以上是关于将值从一个数据帧切片复制到另一个:使用“IndexSlice”的多索引熊猫数据帧的切片是不是总是一致地排序?的主要内容,如果未能解决你的问题,请参考以下文章

基于两个数据帧中的多列将值从一个映射到另一个df

将值从一个 DataGridView 复制到另一个

通过使用 java 脚本,我如何将值从一个 html 页面传递到另一个 html 页面? [复制]

如何将值从一个php页面传递到另一个? [复制]

将值从一个表单复制到另一个表单

如果满足条件,熊猫将值从一列复制到另一列