pandas - 根据之前的数据填写数据框

标签 pandas dataframe

我正在与一家零售商合作开展一个项目,我们希望清理一些数据以用于报告目的。 该零售商拥有多家商店,每周商店的工作人员都会扫描不同显示器上的不同商品(他们首先扫描显示器,让我们知道他们正在谈论哪个显示器)。此外,他们只扫描在那一周内发生变化的显示,如果显示没有更改,那么我们假设它保持不变。

现在我们正在使用 2 个数据框:

层次结构数据框示例: 该表基本上为每个商店的每个端盖(展示)提供了第 1 周到第 52 周的信息。假设该公司只有 2 家商店,每家商店有 3 个终端帽。另外,不同的商店可能有不同的端盖代码,但这对我们的目的来说并不重要(我不认为)。

    Week  Store End Cap
0      1      1       A
1      1      1       B
2      1      1       C
3      1      2       A
4      1      2       B
5      1      2       D
6      2      1       A
7      2      1       B
8      2      1       C
9      2      2       A
10     2      2       B
11     2      2       D

接下来,我们有包含实际更改的历史文件,用于更新 End Caps。

    Week  Store End Cap     UPC
0      1      1       A  123456
1      1      1       B  789456
2      1      1       B  546879
3      1      1       C  423156
4      1      2       A  231567
5      1      2       B  456123
6      1      2       D  689741
7      2      1       A  321654
8      2      1       C  852634
9      2      1       C  979541
10     2      2       A  132645
11     2      2       B  787878
12     2      2       D  615432

合并我使用的两个数据框:

merged_df = pd.merge(hierarchy, hist,  how='left', left_on=['Week','Store', 'End Cap'], right_on = ['Week','Store', 'End Cap'])

这给了我:

    Week  Store End Cap       UPC
0      1      1       A  123456.0
1      1      1       B  789456.0
2      1      1       B  546879.0
3      1      1       C  423156.0
4      1      2       A  231567.0
5      1      2       B  456123.0
6      1      2       D  689741.0
7      2      1       A  321654.0
8      2      1       B       NaN
9      2      1       C  852634.0
10     2      1       C  979541.0
11     2      2       A  132645.0
12     2      2       B  787878.0
13     2      2       D  615432.0

除了显示 NAN 的一个实例。第 2 周存储 1 端盖 2 没有变化,因此没有被扫描。所以它没有出现在历史数据框中。在这种情况下,我希望查看在该商店扫描端盖的最新商品(请参阅历史数据帧的第 2 行和第 3 行)。因此从技术上讲,这也可以在去年的第 52 周进行扫描,但我只想用最新信息填充 NAN 以表明它没有改变。我该如何去做呢?

所需的输出如下所示:

    Week  Store End Cap       UPC
0      1      1       A  123456.0
1      1      1       B  789456.0
2      1      1       B  546879.0
3      1      1       C  423156.0
4      1      2       A  231567.0
5      1      2       B  456123.0
6      1      2       D  689741.0
7      2      1       A  321654.0
8      2      1       B  789456.0
9      2      1       B  546879.0
10     2      1       C  852634.0
11     2      1       C  979541.0
12     2      2       A  132645.0
13     2      2       B  787878.0
14     2      2       D  615432.0

谢谢!

编辑: 除此之外,我尝试对数据进行排序,然后转发填充,这仅部分解决了我遇到的问题:

sorted_df = merged_df.sort_values(['End Cap', 'Store'], ascending=[True, True])

    Week  Store End Cap       UPC
0      1      1       A  123456.0
7      2      1       A  321654.0
4      1      2       A  231567.0
11     2      2       A  132645.0
1      1      1       B  789456.0
2      1      1       B  546879.0
8      2      1       B       NaN
5      1      2       B  456123.0
12     2      2       B  787878.0
3      1      1       C  423156.0
9      2      1       C  852634.0
10     2      1       C  979541.0
6      1      2       D  689741.0
13     2      2       D  615432.0

sorted_filled = sorted_df.fillna(method='ffill')

给我:

    Week  Store End Cap       UPC
0      1      1       A  123456.0
7      2      1       A  321654.0
4      1      2       A  231567.0
11     2      2       A  132645.0
1      1      1       B  789456.0
2      1      1       B  546879.0
8      2      1       B  546879.0
5      1      2       B  456123.0
12     2      2       B  787878.0
3      1      1       C  423156.0
9      2      1       C  852634.0
10     2      1       C  979541.0
6      1      2       D  689741.0
13     2      2       D  615432.0

此输出确实将 546879 添加到第 2 周 store1 End Cap B,但没有添加我也需要的 789456。我需要它来添加具有该值的另一​​行。

最佳答案

您还可以像这样创建一个辅助列来处理每个商店/周/结束上限的重复 UPC。

idxcols=['Week', 'Store', 'End Cap']
hist_idx = hist.set_index(idxcols + [hist.groupby(idxcols).cumcount()])

hier_idx = hierarchy.set_index(idxcols+[hierarchy.groupby(idxcols).cumcount()])

hier_idx.join(hist_idx, how='right')\
        .unstack('Week')\
        .ffill(axis=1)\
        .stack('Week')\
        .reorder_levels([3,0,1,2])\
        .sort_index()\
        .reset_index()\
        .drop('level_3', axis=1)

输出:

    Week  Store End Cap       UPC
0      1      1       A  123456.0
1      1      1       B  789456.0
2      1      1       B  546879.0
3      1      1       C  423156.0
4      1      2       A  231567.0
5      1      2       B  456123.0
6      1      2       D  689741.0
7      2      1       A  321654.0
8      2      1       B  789456.0
9      2      1       B  546879.0
10     2      1       C  852634.0
11     2      1       C  979541.0
12     2      2       A  132645.0
13     2      2       B  787878.0
14     2      2       D  615432.0

关于pandas - 根据之前的数据填写数据框,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/66896444/

相关文章:

python - Pandas 的错误​​小数计算

python - 对于数据框中的每一列和单元格,使用该列中的随机值填充 NaN/Nulls

python - 返回 pandas 数据框中出现最小/最大值的索引/索引列表

python - Pandas 在日期列上重新采样

R:绘制data.frame中所有列的直方图

python - 如何将Python数据框中的对象转换为仅int数字?

python - 将 Dataframe 转换为数据透视表,将值分组到列表中

python - 通过匹配 Pandas DataFrame 中另一列中的值来获得行值的差异

python - 根据条件更改 pandas 中的日期值并转换为日期时间

python - 在 pandas DataFrame 中搜索列