Return 多索引中每个第一个 row/observation 的计数

Return the count of every first row/observation in a Multi-index

我有一个多索引数据框:

                  pid  time
 id_main  id_sub 
   
 id_1   sub_id1  pid1   t1
        sub_id3  pid2   t2
        sub_id9  pid3   t3
           .       .    .
           .       .    .
 id_2   sub_id2  pid_1  t1
        sub_id3  pid_1  t2
          .        .     .
          .        .     .

Context:每个 id_main 是用户的个人会话 ID,pid 是包含用户旅行的“路径”的字符串(一次我们当然按时间排序)

df = df.set_index(['main_id','sub_id'])`
df = df.sort_values('time')

目标:我想找到所有会话的每个 FIRST pid 的计数。所以我基本上想要一个以 pid 作为索引的系列(这样我就可以将它合并到别处)和一个列,其中每个 pid 在每个会话 [=17] 中首先出现的次数=].然后有点复杂,但我想创建另一个数据框,它根据会话 ID (id_main) 为每个页面创建出现次数,然后是包含所有 pids 及其相对值的第二个索引数数。所以基本上,我需要每个会话的第一次出现,并且对于每个第一次出现的 pids 我希望能够计算出它们各自的后续步骤。

查找每个会话第一页的行:

>>> df.groupby('id_main')['time'].idxmin()
id_main
id1    (id1, sub0)
id2    (id2, sub7)
id3    (id3, sub5)
Name: time, dtype: object

因此每个第一页的编号为:

>>> df.loc[df.groupby('id_main')['time'].idxmin(), 'pid'].value_counts()
pid8     1
pid13    1
pid1     1
Name: pid, dtype: int64

当然在这个例子中我只有 3 个用户,每个用户都从不同的页面开始。

然后您需要每个会话每个页面的出现次数(您可以向其添加 .unstack('pid')):

>>> df.groupby('id_main')['pid'].value_counts()
id_main  pid  
id1      pid14    1
         pid5     1
         pid8     1
id2      pid13    1
         pid15    1
         pid5     1
id3      pid1     1
         pid10    1
         pid11    1
         pid14    1
         pid15    1
         pid7     1
Name: pid, dtype: int64

如果你想知道页面转换,即从哪一页到下一页,你可以这样做:

>>> df.sort_values('time').groupby('id_main')['pid'].shift().to_frame('from_pid').join(df.sort_values('time')['pid'].rename('to_pid'))
               from_pid to_pid
id_main id_sub                
id3     sub5        NaN   pid1
        sub1       pid1  pid14
id2     sub7        NaN  pid13
id1     sub0        NaN   pid8
        sub8       pid8   pid5
id3     sub0      pid14   pid7
id1     sub4       pid5  pid14
id3     sub4       pid7  pid11
id2     sub2      pid13   pid5
id3     sub8      pid11  pid15
        sub3      pid15  pid10
id2     sub3       pid5  pid15

这对于模型了解从哪个页面转到哪个页面可能很有用,也许简单的马尔可夫链是一个好的开始。