第24章 第二个标签怎么造:层级标签
小白一句话
第二个目标不是凭空造一个新问题,而是在已有的"回访"标签上加一档更苛刻的:未来 7 天不只"来过",还得"活跃 3 天以上"。两个标签一高一低,天然是层级关系------先回访,才谈得上持续。
这一章在干嘛
第23章讲了为什么需要第二个目标,但没给具体的标签。这一章把它造出来,并且回答三个问题:
- 第二个标签长什么样,和第一个是什么关系;
- 为什么它是"层级"的(
sustained永远 ≤returned),以及这个性质有什么用; - "3 天"这个阈值哪来的,能不能动。
第二个标签:在"回访"上面加一档
第一个标签沿用前面所有章节的口径:
returned = 1 未来 7 天(不含当天)至少回来 1 次
returned = 0 否则
第二个标签在上面加一档:
sustained_active_7d = 1 未来 7 天至少活跃 3 天
sustained_active_7d = 0 否则
这个标签不是另起炉灶------它就是第6章讲辅助标签时算过的 active_days_7d >= 3("未来 7 天活跃几天"这个数 >= 3)。第6章顺手埋了个伏笔,说这个数"第24章会用到",现在兑现了。
两个标签在 162 行上的分布:
| 标签 | 定义 | 正例数 | 正例率 |
|---|---|---|---|
| returned | 未来 7 天 ≥ 1 天 | 134 | 0.827 |
| sustained_active_7d | 未来 7 天 ≥ 3 天 | 84 | 0.519 |
returned 有 134 个正例,sustained 只有 84 个------少掉的 50 个,正是第23章说的"回来但只待 1~2 天"的人。
层级关系:sustained ≤ returned 永远成立
两个标签摆到交叉表里看:
| returned = 0 | returned = 1 | |
|---|---|---|
| sustained = 0 | 28 行(没回) | 50 行(回访但不黏) |
| sustained = 1 | 0 行 | 84 行(回访且黏) |
左下角那格是空的------没有一个人"持续活跃 3 天"却没回访。这不奇怪:能活跃 3 天的人,当然至少来过 1 天。写成不等式就是:
sustained ≤ returned (对每一行都成立)
跑脚本验证了一遍,162 行里违反这一条的行数是 0。
这个性质是"层级标签"这个词的全部意义,它带来两个实实在在的好处:
- 逻辑上不会闹矛盾。不会出现"模型说这个人持续活跃,但回访概率却很低"这种运营会当场质疑的输出。后面第26章会看到,双头的概率乘出来天然满足这个不等式。
- 标签语义可以拆开讲。任何一个人,用两个标签就能归类到三个格子里:没回(28 行)、回访但不黏(50 行)、回访且黏(84 行)。每一格对应一种运营动作。
一个熟人的轨迹:三格都走了一遍
把 U0009 的三个评分日翻出来,看他的双标签怎么变:
| 评分日 | returned | sustained | 活跃天数 | 属于哪格 |
|---|---|---|---|---|
| 07-08 | 1 | 1 | 3 天 | 回访且黏 |
| 07-15 | 1 | 0 | 2 天 | 回访但不黏 |
| 07-22 | 0 | 0 | 0 天 | 没回 |
同一个用户,从"黏"滑到"浅层"再到"没回"------这个轨迹单目标模型只看得见"回访"那列的 1→1→0(前两次看不出差别),双标签把"黏度先于回访恶化"的过程显出来了:07-15 那次他就已经只来 2 天了,回访标签还看不出问题,sustained 先翻了。这就是第二个标签的增量信息------它比回访标签更敏感地反映"在掉"。
条件标签的定义域:只在"已回访"的人身上有意义
sustained 的正例全部落在 returned = 1 的子集里(84 行都在右边那列)。所以它天生是个条件标签:它的定义本身就建立在"回访过"的前提上。算比例也要在子集里算:
P(sustained | returned) = 84 / 134 = 0.627
意思是"回来的 134 个人里,62.7% 待了 3 天以上"。这个 0.627 和第23章那个"黏的人占回访的 62.7%"是同一个数,换了个叫法------从"统计描述"变成"条件概率"。
这个定义域很重要,后面两章都靠它:训练的时候,条件头只在 returned = 1 的样本上算损失 (第25章),评估的时候,条件指标也只在 returned = 1 的子集上算(第27章)。把没回访的人混进来,等于让"黏度"问题去猜一批根本不会回来的人,指标会被稀释。
"3 天"这个阈值,不是天条
为什么是 ≥3 天而不是 ≥4、≥5?先看数据:
| 阈值 | 正例数 | 正例率 | 占回访的比例 |
|---|---|---|---|
| ≥ 1 天(returned) | 134 | 0.827 | 100% |
| ≥ 3 天 | 84 | 0.519 | 62.7% |
| ≥ 4 天 | 58 | 0.358 | 43.3% |
| ≥ 5 天 | 45 | 0.278 | 33.6% |
阈值每抬一档,正例掉一截。≥5 天时只有 45 个正例,样本量太少,模型学不动。所以 3 天是个平衡点:语义上 ,3 天是"露脸就走"和"持续活跃"的直观分界(来一天谁都行,连着来三天说明真在待);数据上,84 个正例够撑起一个条件头的训练。
但这只是示例数据的说法。真实项目里这个阈值是个旋钮,定它要结合两件事:运营对"黏"的定义(业务上怎么算留住),以及正例规模(调太高正例不够训)。第23章动手题里让你把阈值改成 4 重跑,就是在感受这个旋钮的力度。
它和前后章节的关系
- 第6章的
active_days_7d是素材,本章把它翻成sustained_active_7d标签; - 第23章讲了动机(回访≠黏),本章把第二个标签落地并验证层级;
- 第25章把这个双标签喂给双头模型:共享特征底座 + 两个分支,条件头只吃
returned = 1的样本; - 第26章把两个头的输出拼成
P(sustained) = P(returned) × P(sustained | returned),层级一致不用硬约束; - 第27章评估时,条件指标只在
returned = 1子集上算。
动手
- 跑
附件/07_双目标模型升级篇/activity_dual_label.py,对照交叉表:28 / 50 / 84 / 0 四个数,重点看左下角那个 0------层级验证就靠它。 - 把脚本里
>= 3改成>= 4和>= 5重跑,看正例从 84 掉到 58、45------感受"阈值是旋钮,调太高样本不够"。 - 打开
附件/05_活跃度预测篇/activity_train_table.csv,给 U0009 的三行手动标双标签,对照正文那张轨迹表(1,1 → 1,0 → 0,0)。想想单目标模型在这三行上能不能看出他在掉------前两行回访标签都是 1,看不出;sustained 在第二行就翻了,这正是第二个标签的增量信息。
本章配套脚本
附件/07_双目标模型升级篇/activity_dual_label.py(双标签分布 + 交叉表 + 层级验证 + U0009 轨迹 + 阈值敏感性)。只用标准库,环境搭建见第4章。训练表由第12章附件/05_活跃度预测篇/activity_train_table.py生成,sustained口径与第6章active_days_7d一致。