首页 > 解决方案 > Pandas 根据需要匹配的其他列的值创建新的列 ID

问题描述

我是编程和熊猫的新手。因此,请不要严格判断,对不起我的解释。

我基本上有两列(DM1_ID,DM2_ID),我需要根据这两列值创建一个新列('NewID')。基本上我正在做的是为两列创建一个新的 ID。这里首先评估第一列中的值并获取该值并将其放入“NewID”列中。此外,当我们这样做时,需要考虑 DM2_ID,当该 id 出现在 DM1_ID 中时,我需要在 NewID 列中提供相同的 DM1_ID。

作为 0 indexe 中的示例,DM1_ID 1 和 DM2_ID 6,我需要将 1 作为两个 id 的 NewID。当 DM1_ID 达到 6(索引 15)时,无论 DM2_ID 中的什么,我都需要将 1 作为 NewID,因为我同时给出了 DM1_ID 1 和 DM1_ID 6。所以它将是 1。另外,我需要考虑 DM2_ID 以供以后使用和它也是 1。(索引 15 DM1_ID 6 和 DM2_ID 45,因为我已经为 1 和 6 都给了 newId 作为 1 我必须给 1 给 DM1_ID 6。同样对于 45,我需要给 1 作为 NewID(索引 21).)

#I have a large table like this
    DM1_ID  DM2_ID
0   1       6
1   1       7
2   1       15
3   2       5
4   2       10
5   3       21
6   3       28
7   3       32
8   3       35
9   4       39
10  5       2
11  5       10
12  6       1
13  6       7
14  6       15
15  6       45
16  6       55
17  7       1
18  7       6
19  7       15
20  10      75
21  45      120
22  45      10
23  10      27
24  10      28
25  2       335

#I need to create this table

    DM1_ID  DM2_ID  abc
0   1       6        1
1   1       7        1
2   1       15       1
3   2       5        2
4   2       10       2
5   3       21       3
6   3       28       3
7   3       32       3
8   3       35       3
9   4       39       4
10  5       2        2
11  5       10       2
12  6       1        1
13  6       7        1
14  6       15       1
15  6       45       1
16  6       55       1
17  7       1        1
18  7       6        1
19  7       15       1
20  10      75       2
21  45      120      1
22  45      10       2
23  10      27       2
24  10      28       2
25  2       335      2

Any help would be appreciated. Thanks.


标签: pythonpandasdataframepandas-groupby

解决方案


实现目标的一种方法是首先保留您的 ID。然后,一旦满足条件,您就可以使用此持久映射表/字典来分配唯一 ID。我在下面包含了一个带有字典的示例,但您也可以使用数据库或 JSON 文件来保存给定的 ID:

df['pairs'] = df.apply(lambda x: [x[0], x[1]], axis=1)
pairs = df['pairs'].tolist()

u = {}
u_ = {}
for p in pairs:
    if u:
        if not u_:
            u_ = u.copy()
        else:
            u = u_.copy()
           
        for k in list(u.keys()):
            if any(x in u[k] for x in p):
                u_.update(
                    {
                        k: list(set(u[k] + p))
                    }
                )
                
            else:
                pass
            
        vals = [j for i in list(u.values()) for j in i]
        if u == u_ and not any(x in vals for x in p):
            n = max(list(u_.keys())) + 1
            u_[n] = p

        else:
            pass
            
    else:
        u[1] = p
        
u_

输出:

{1: [1, 6, 7, 45, 15, 55, 120],
 2: [75, 2, 10, 5],
 3: [32, 35, 3, 21, 28],
 4: [4, 39]}

现在让我们应用一个函数,根据我们在上一步中创建的字典为每行分配新的 ID:

f = lambda x: next(k for k,v in u_.items() if any(i in v for i in x))
df['new_ID'] = df['pairs'].apply(f)
df.drop('pairs', axis=1, inplace=True)
df

输出:

DM1_ID  DM2_ID  new_ID
0   1   6   1
1   1   7   1
2   1   15  1
3   2   5   2
4   2   10  2
5   3   21  3
6   3   28  3
7   3   32  3
8   3   35  3
9   4   39  4
10  5   2   2
11  5   10  2
12  6   1   1
13  6   7   1
14  6   15  1
15  6   45  1
16  6   55  1
17  7   1   1
18  7   6   1
19  7   15  1
20  10  75  2
21  45  120 1

推荐阅读