统计熊猫DataFrame中每个组的行值更改

问题描述 投票:1回答:1

我在大熊猫中有DataFrame,其中包含有关人的位置的及时信息。它大约有300+百万行。

示例:

import pandas as pd
inp = [{'Name': 'John', 'Year':2018, 'Address':'Beverly hills'}, {'Name': 'John', 'Year':2018, 'Address':'Beverly hills'}, {'Name': 'John', 'Year':2019, 'Address':'Beverly hills'}, {'Name': 'John', 'Year':2019, 'Address':'Orange county'}, {'Name': 'John', 'Year':2019, 'Address':'New York'}, {'Name': 'Steve', 'Year':2018, 'Address':'Canada'}, {'Name': 'Steve', 'Year':2019, 'Address':'Canada'}, {'Name': 'Steve', 'Year':2019, 'Address':'Canada'}, {'Name': 'Steve', 'Year':2020, 'Address':'California'}, {'Name': 'Steve', 'Year':2020, 'Address':'Canada'}, {'Name': 'John', 'Year':2020, 'Address':'Canada'}, {'Name': 'John', 'Year':2021, 'Address':'Canada'}, {'Name': 'John', 'Year':2021, 'Address':'Beverly hills'}, {'Name': 'Steve', 'Year':2021, 'Address':'California'}, {'Name': 'Steve', 'Year':2022, 'Address':'California'}, {'Name': 'Steve', 'Year':2018, 'Address':'NewYork'}, {'Name': 'Steve', 'Year':2018, 'Address':'California'}, {'Name': 'Steve', 'Year':2022, 'Address':'NewYork'}]
df = pd.DataFrame(inp)
print (df)

输出:

          Address   Name  Year
0   Beverly hills   John  2018
1   Beverly hills   John  2018
2   Beverly hills   John  2019
3   Orange county   John  2019
4        New York   John  2019
5          Canada  Steve  2018
6          Canada  Steve  2019
7          Canada  Steve  2019
8      California  Steve  2020
9          Canada  Steve  2020
10         Canada   John  2020
11         Canada   John  2021
12  Beverly hills   John  2021
13     California  Steve  2021
14     California  Steve  2022
15        NewYork  Steve  2018
16     California  Steve  2018
17        NewYork  Steve  2022

我想计算特定年份地址之间的变化的total。换句话说,2018年有多少人从“加拿大”移居到“加利福尼亚”。

理想的输出:

1]每年的矩阵如下。示例:2019年(包括2018年至2019年)中的所有地址更改。

+---------------+---------------+---------------+----------+------------+
| From\ To      | Beverly hills | Orange county | New York | California |
+---------------+---------------+---------------+----------+------------+
| Beverly hills | 0             | 1             | 0        | 0          |
+---------------+---------------+---------------+----------+------------+
| Orange county | 0             | 0             | 1        | 0          |
+---------------+---------------+---------------+----------+------------+
| New York      | 0             | 2             | 0        | 0          |
+---------------+---------------+---------------+----------+------------+
| California    | 0             | 0             | 0        | 0          |
+---------------+---------------+---------------+----------+------------+

[2)全年地址更改。

+---------------+---------------+------+------+------+
| Address 1     | Address 2     | 2018 | 2019 | 2020 |
+---------------+---------------+------+------+------+
| Beverly hills | Orange county | 0    | 1    | 0    |
+---------------+---------------+------+------+------+
| New York      | Canada        | 0    | 0    | 1    |
+---------------+---------------+------+------+------+
| Canada        | New York      | 1    | 0    | 0    |
+---------------+---------------+------+------+------+
| California    | Canada        | 0    | 1    | 2    |
+---------------+---------------+------+------+------+

到目前为止我的解决方案:感谢@QuangHoang,我可以使用以下代码捕获“年份”的更改和“地址”的更改:

groups = df.groupby('Name')

for col in ['Year', 'Address']:
    df[f'cng-{col}'] = groups[col].shift().fillna(df[col]).ne(df[col]).astype(int)

groups[col].shift()在每个名称中将对应的列移动1。 fillna(df[col]将每个(移位的)组的第一行填充为原始文件,表示没有更改。最后,ne(df[col])将移位后的值与原始值进行比较以进行更改。

收益率:

+----+---------------+-------+------+----------+-------------+
| ID | Address       | Name  | Year | cng-Year | cng-Address |
+----+---------------+-------+------+----------+-------------+
| 0  | Beverly hills | John  | 2018 | 0        | 0           |
+----+---------------+-------+------+----------+-------------+
| 1  | Beverly hills | John  | 2018 | 0        | 0           |
+----+---------------+-------+------+----------+-------------+
| 2  | Beverly hills | John  | 2019 | 1        | 0           |
+----+---------------+-------+------+----------+-------------+
| 3  | Orange county | John  | 2019 | 0        | 1           |
+----+---------------+-------+------+----------+-------------+
| 4  | New York      | John  | 2019 | 0        | 1           |
+----+---------------+-------+------+----------+-------------+
| 10 | Canada        | John  | 2020 | 1        | 1           |
+----+---------------+-------+------+----------+-------------+
| 11 | Canada        | John  | 2021 | 1        | 0           |
+----+---------------+-------+------+----------+-------------+
| 12 | Beverly hills | John  | 2021 | 0        | 1           |
+----+---------------+-------+------+----------+-------------+
| 5  | Canada        | Steve | 2018 | 0        | 0           |
+----+---------------+-------+------+----------+-------------+
| 15 | NewYork       | Steve | 2018 | 1        | 1           |
+----+---------------+-------+------+----------+-------------+
| 16 | California    | Steve | 2018 | 0        | 1           |
+----+---------------+-------+------+----------+-------------+
| 6  | Canada        | Steve | 2019 | 1        | 0           |
+----+---------------+-------+------+----------+-------------+
| 7  | Canada        | Steve | 2019 | 0        | 0           |
+----+---------------+-------+------+----------+-------------+
| 8  | California    | Steve | 2020 | 1        | 1           |
+----+---------------+-------+------+----------+-------------+
| 9  | Canada        | Steve | 2020 | 0        | 1           |
+----+---------------+-------+------+----------+-------------+
| 13 | California    | Steve | 2021 | 1        | 1           |
+----+---------------+-------+------+----------+-------------+
| 14 | California    | Steve | 2022 | 1        | 0           |
+----+---------------+-------+------+----------+-------------+
| 17 | NewYork       | Steve | 2022 | 1        | 1           |
+----+---------------+-------+------+----------+-------------+
python pandas dataframe compare rows
1个回答
0
投票

如果我理解问题的话..

df.drop_duplicates().groupby(['Name','Year']).size().reset_index(name="changes")

具有此输出

    Name  Year  changes
0   John  2018        1
1   John  2019        3
2   John  2020        1
3   John  2021        2
4  Steve  2018        3
5  Steve  2019        1
6  Steve  2020        2
7  Steve  2021        1
8  Steve  2022        2
© www.soinside.com 2019 - 2024. All rights reserved.