基于 pandas 数据帧中唯一性的 2 列值的编号组合



我有一个数据帧,我想在其中基于另外两列创建一个新列。 这是我的数据帧的样子:

HOUSEID    PERSONID
20000017      1            
20000017      1            
20000017      2            
20000017      3            
20000017      3            
20000231      1            
20000231      1
20000231      2
20000521      1
20000521      2 
20000521      2
20001283      1
20001283      2
20001283      3
20001283      3

我需要在新列中按顺序定义一个数字,用于"HOUSEID"和"PERSONID"的唯一组合,标有"PERSON_COUNTER"。 每当有一个新的组合时,它就会上升一个数字,并将其放在从 1 开始的组合前面。 这是我的意思:

HOUSEID    PERSONID   PERSON_COUNTER
20000017      1            1
20000017      1            1
20000017      2            2
20000017      3            3
20000017      3            3
20000231      1            4
20000231      1            4
20000231      2            5
20000521      1            6
20000521      2            7 
20000521      2            7
20001283      1            8
20001283      2            9
20001283      3            10
20001283      3            10

我已经尝试了下面的代码,它运行良好,但由于我有一个相对较大的数据帧(大约 100 万行(,因此执行大约需要 2 个小时:

df.insert(2, 'PERSON_COUNTER', '')
list_person_counter = []
def person_counter(houseid, personid):
if [houseid, personid] in list_person_counter:
return len(list_person_counter)
else:
list_person_counter.append([houseid, personid])
return len(list_person_counter)
df['PERSON_COUNTER'] = df.apply(lambda row: person_counter(row['HOUSEID'], row['PERSONID']), axis=1)

如果有人能提供最快的方法,我将不胜感激。

谢谢

DataFrame.ne比较具有DataFrame.shifted 值的!=的选定列,然后按DataFrame.any测试每行至少一个True,最后添加累积总和Series.cumsum

c = ['PERSONID', 'HOUSEID']
df['PERSON_COUNTER'] = df[c].ne(df[c].shift()).any(axis=1).cumsum()
print (df)
HOUSEID  PERSONID  PERSON_COUNTER
0   20000017         1               1
1   20000017         1               1
2   20000017         2               2
3   20000017         3               3
4   20000017         3               3
5   20000231         1               4
6   20000231         1               4
7   20000231         2               5
8   20000521         1               6
9   20000521         2               7
10  20000521         2               7
11  20001283         1               8
12  20001283         2               9
13  20001283         3              10
14  20001283         3              10

如果只想按一列工作:

df['PERSON_COUNTER'] = df['PERSONID'].ne(df['PERSONID'].shift()).cumsum()

最新更新