摘要:
合集:AI案例-NLP-广告传媒
赛题:2018腾讯广告算法大赛-Lookalike相似人群拓展
数据集:腾讯广告的相似社交用户数据集
数据集发布方:腾讯
数据集价值:通过用户画像客户分群,支持广告精准投放降低获客成本。
解决方案:广告受众特征提取、LightGBM梯度提升框架
一、赛题描述
赛题背景
基于社交关系的广告已成为互联网广告行业中发展最为迅速的广告之一。腾讯社交广告依托于腾讯丰富的社交产品,植根于腾讯海量的数据,借助强大的数据分析、机器学习和云计算能力打造出一个服务于千万商家和亿万用户的商业广告平台。我们一直致力于提供精准及高效的广告解决方案,而复杂的社交场景,多样的广告形态,以及庞大的人群数据,给实现这一目标带来了不小的挑战。为攻克这些挑战,腾讯社交广告也在不断地寻找更为优秀的数据挖掘方式和机器学习算法。 本次算法大赛的题目源自一个基于真实业务场景的广告技术产品 —— 腾讯社交广告Lookalike相似人群拓展。Lookalike的原理是基于某目标人群,从海量的其他人群中找出和目标人群相似的人群,以拓展目标人群规模。在实际广告业务应用场景中,Lookalike能基于广告主已有的消费者,找出和已有消费者相似的潜在消费者,以此有效帮助广告主挖掘新客、拓展业务。目前,腾讯社交广告Lookailke相似人群拓展已集合广告主提供的第一方数据及广告投放效果数据,基于腾讯丰富的数据标签及能力,透过深度神经网络挖掘,实现了可在线实时为多个广告主同时拓展具有相似特征的高质潜客的能力。在这次算法比赛中,经过数据处理,我们采用了Lookalike相似人群拓展产品中的模拟数据包作为参赛数据。 我们希望通过本次大赛,挑选出更为优秀的Lookalike算法以及遴选出杰出的社交广告算法达人加入腾讯。
评分标准
初赛:初赛A阶段使用初赛测试集数据的30%来计算得分和排名,初赛B阶段使用初赛测试集数据剩余的70%来计算得分和排名,最终成绩排行榜将以初赛B阶段各参赛队伍的历史最好成绩进行排名。
复赛:复赛A阶段使用复赛测试集数据的30%来计算得分和排名,复赛B阶段使用复赛测试集数据剩余的70%来计算得分和排名,最终成绩排行榜将以复赛B阶段各参赛队的历史最好成绩进行排名。
应用
“Lookalike”简单理解是一个人或事物和另外的人或事物非常相似。在互联网商业应用中,许多广告主在“搜寻潜客”时,都会遇到如难以识别高潜人群、难于平衡成本与规模等问题。该技术可以利用广告主第一方数据,基于少量的种子用户,通过大数据分析和机器学习拓展出和种子相似的用户人群。而这些拓展出的相似人群同时也有很大可能成为客户的目标人群(比如,APP的下载激活、商品的收藏购买,目标粉丝的扩展等等)。
近几年来,各大互联网公司纷纷推出Lookalike相关的产品和技术,应用其商业项目。如Google推出的“Similar Audiences”根据用户近期的浏览和下载APP行为,为广告主推荐扩展人群。Facebook推出Lookalike Audiences,可以根据Custom Audiences所筛选出的用户名单为参考,再筛选出与其相似的受众,让广告主可以将广告投递给此名单内的用户。阿里推出达摩盘(DMP)Lookalike 模型根据对店铺或品牌最忠实的那批用户(种子用户),并通过Lookalike 模型找到与这些种子用户相似的人来增加店铺的有效浏览和转化。
腾讯社交广告团队最早在 2013 年开始调研探索 Lookalike 定向技术,基于种子用户画像和关系链寻找相似用户,即根据种子人群的共有属性进行自动化扩展,以扩大受众覆盖面,提升广告效果。例如,家庭、社会身份、地位、相关群体等社会因素,文化、次文化等文化因素,以及行为、动机、兴趣等心理因素等都能形成相似人群拓展Lookalike的筛选标准。以社交关系链为基础,腾讯社交广告可以助力广告主寻找相似线索、捕捉高潜客户。
二、数据集内容
目录结构
- src:源码
- preliminary_competition_data:原始初赛数据
- final_competition_data:原始复赛数据
- data_preprocessing:数据处理目录
- run.sh
adFeature.csv
广告数据样例:
aid | advertiserId | campaignId | creativeId | creativeSize | adCategoryId | productId | productType |
---|---|---|---|---|---|---|---|
177 | 8203 | 76104 | 1500666 | 59 | 282 | 0 | 6 |
2050 | 19441 | 178687 | 245165 | 53 | 1 | 0 | 6 |
1716 | 5552 | 158101 | 1080850 | 35 | 27 | 113 | 9 |
336 | 370 | 4833 | 119845 | 22 | 67 | 113 | 9 |
671 | 45705 | 352827 | 660519 | 42 | 67 | 0 | 4 |
529 | 10122 | 163352 | 220558 | 35 | 10 | 3733 | 11 |
927 | 370 | 219802 | 492484 | 35 | 67 | 113 | 9 |
userFeature.csv
用户特征数据样例:
LBS | age | carrier | consumptionAbility | ct | education | gender | interest1 | interest2 | interest5 | kw1 | kw2 | kw3 | marriageStatus | os | topic1 | topic2 | uid |
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
950 | 4 | 1 | 2 | 3 1 | 7 | 2 | 93 70 77 86 … | 46 19 13 29 | 52 100 72 131 116 11 71 12 8 113 28 73 6 132 99 76 46 62 121 59 129 21 93 | 664359 276966 734911 103617 562294 | 11395 79112 115065 77033 36176 | 11 | 2 | 9826 105 8525 5488 7281 | 9708 5553 6745 7477 7150 | 26325489 | |
803 | 2 | 1 | 1 | 3 1 | 2 | 1 | 75 29 | 33 | 338851 361151 542834 496283 229952 | 80263 39618 53539 180 38163 | 5 13 | 1 | 4391 9140 5669 1348 4388 | 9401 7724 1380 8890 7153 | 1184123 |
train.csv
对于一个广告和一个用户是否是潜在消费者(用label标识)的训练数据样例:
aid | uid | label |
---|---|---|
699 | 78508957 | 0 |
1991 | 3637295 | 0 |
1119 | 19229018 | 0 |
2013 | 79277120 | 0 |
692 | 41528441 | 0 |
1119 | 62381478 | 0 |
117 | 36832847 | 0 |
389 | 22023604 | 0 |
1119 | 48708770 | 1 |
test.csv
对于一个广告和一个用户是否是潜在消费者的测试数据样例:
aid | uid |
---|---|
2118 | 64355836 |
692 | 45051997 |
692 | 10869198 |
1918 | 75929554 |
1596 | 5790162 |
1044 | 14187856 |
12 | 6387181 |
三、解决方案样例
以下为排名11的解决方案。
解决方案
特征提取
五大类特征:投放量(click)、投放比例(ratio)、转化率(cvr)、特殊转化率(CV_cvr)、多值长度(length),每类特征基本都做了一维字段和二维组合字段的统计。值得注意的是转化率利用预处理所得的分块标签独立出一个分块验证集不加入统计,其余分块做dropout交叉统计,测试集则用全部训练集数据进行统计。此外,我们发现一些多值字段的重要性很高,所以利用了lightgbm特征重要性对ct\marriage\interest字段的稀疏编码矩阵进行了提取,提取出排名前20的编码特征与其他单值特征进行类似上述cvr的统计生成CV_cvr的统计,这组特征和cvr的效果几乎相当。
特征筛选
因内存大小限制的原因,没办法一次性加载所有特征,故对每组特征进行组内筛选,对组内特征进行重要性排序,排序完筛选办法有两种,一种是按照排名进行前向搜索,另一种就是直接测试前n*5(n位正整数)个特征的效果,由于多数统计特征之间相关性很高,大概每组30+个特征的信息就能代表整组特征所包含的信息。第一种精度会好一些但速度慢,第二种办法就相对快很多。
点击行为特征工程与特征选择
以点击行为特征工程与特征选择为例。
17个类别特征为:label_feature=[‘aid’,’uid’,’advertiserId’, ‘campaignId’, ‘creativeId’, ‘creativeSize’, ‘adCategoryId’, ‘productId’, ‘productType’, ‘age’, ‘gender’,’education’, ‘consumptionAbility’, ‘LBS’, ‘os’, ‘carrier’, ‘house’]
006_click.py – 点击行为特征生成脚本。这个脚本主要执行以下操作:
- 数据读取与预处理:
- 从
data_preprocessing/train_test_merge.csv
读取数据 - 根据
n_parts
和label
列划分数据集索引(训练集、验证集、测试集1、测试集2) - 对17个类别特征进行LabelEncoder编码
- 从
- 特征工程:
- 单特征点击统计:
- 计算每个特征值的出现次数(
value_counts
) - 进行最小-最大归一化(缩放到0-100范围)
- 特征命名格式:
cnt_click_of_<feature>
- 计算每个特征值的出现次数(
- 双特征交叉点击统计:
- 计算两个特征组合的出现次数(
groupby().sum()
) - 同样进行最小-最大归一化
- 特征命名格式:
cnt_click_of_<feature1>_and_<feature2>
- 计算两个特征组合的出现次数(
- 单特征点击统计:
- 数据保存:
- 每生成31个特征就保存一次中间结果
- 分别保存训练集、验证集和两个测试集的特征到CSV文件
- 最终共生成约153个特征(17单特征 + 136交叉特征)
006_click_select.py – 点击特征选择脚本,这个脚本执行以下操作:
- 预定义特征列表:
- 包含30个精选的点击统计特征(单特征和交叉特征)
- 重点关注用户(uid)、广告创意(creativeSize)、人口统计特征(age/gender)等组合
- 特征筛选:
- 从之前生成的5个特征文件中读取数据
- 只保留预定义的特征列表中的特征
- 对训练集、验证集和两个测试集都执行相同的筛选操作
- 数据保存:
- 将筛选后的特征保存为新的CSV文件(文件名带有”_select”后缀)
主要技术点:
- 点击行为特征工程:
- 使用计数统计反映用户或广告的流行度
- 通过交叉统计捕捉特征间的交互效应
- 特征归一化:
- 采用最小-最大归一化将特征缩放到0-100范围
- 公式:
(value - min) / (max - min) * 100
- 特征选择策略:
- 基于领域知识预先定义重要特征
- 重点关注用户行为相关的特征组合
- 数据处理优化:
- 分批处理特征以减少内存压力
- 记录每个特征的处理时间
这两个脚本共同构成了点击行为相关的特征工程流程,从原始数据生成统计特征,然后筛选出重要的特征用于模型训练。
模型融合
由于数据量过大,lgb根据分块数据与分组特征跑了很多个子模型,最后根据验证集的多组预测值进行auc排序后,依次百分比(list(range(0,101))*0.01)遍历加权以获得最佳权值,再将同样的权值应用到测试集的预测结果上,这样每多加权一个子模型,验证集的auc只会大于等于加权这个子模型之前的auc。整个加权过程其实就类似于是一种线性拟合,也可以利用各个子模型的验证集和测试集的预测结果作为特征,利用验证集的标签作为真实标签,采用xgboost等模型进行训练,这样效果与之前的遍历加权差不多。
安装
依赖的开发库:pandas, numpy, scikit-learn, lightgbm
LightGBM模型
LightGBM(Light Gradient Boosting Machine)是由微软开发的梯度提升框架,以其高效性和高性能著称,尤其适用于处理大规模数据和高维特征。
核心创新技术
梯度单边采样(Goss) 目的:解决样本分布不均问题,减少计算量。 原理:仅保留梯度方向一致的样本(如正负样本中损失下降最快的部分),按比例采样,保持多样性。 优势:加速训练,提升在不平衡数据集上的效果。 互斥特征捆绑(EFB) 目的:减少高维稀疏特征(如One-Hot编码)的维度灾难。 原理:将相关性强的互斥特征捆绑为单一特征,建模其特征组合效应。 优势:降低特征数量,防止过拟合,提升计算效率。 基于叶子的生长策略 与传统方法对比:不同于XGBoost的“预排序”(Pre-sorted),LGB在每个节点动态计算梯度统计量(如梯度均值、方差),选择最优分割点。 优势:减少内存占用,训练速度提升10倍以上,尤其适合大数据场景。 正则化与优化 叶子正则化:对叶子节点权重施加L1/L2惩罚,控制模型复杂度。 交叉熵损失:支持概率预测,适用于分类任务。 类别特征支持:无需额外编码,直接指定类别列即可自动处理。
应用场景
金融风控:信用评分、欺诈检测(处理高维稀疏数据,如用户行为日志)。 医疗领域:疾病预测、药物响应分析(快速处理海量医学特征)。 推荐系统:用户点击率预测、个性化推荐(高效处理用户-物品交互数据)。 自然语言处理:文本分类、主题建模(结合TF-IDF或词嵌入特征)。
使用流程
数据准备
- 缺失值处理:插值、删除或使用算法内置处理(如max_depth控制)。
- 分类变量编码:明确指定categorical_feature参数。
- 数据集划分:训练集、验证集、测试集,常用交叉验证(cv参数)。
参数调优 关键参数:
- objective:目标函数(如binary:logistic、multi:softmax)。
- metric:评估指标(如auc、binary_logloss)。
- num_leaves、max_depth:控制模型复杂度,防止过拟合。
- learning_rate:步长衰减,降低方差。
- min_data_in_leaf、min_child_samples:防止过拟合的小样本剪枝。
调优方法:网格搜索、随机搜索、贝叶斯优化(如Optuna)。
数据预处理
预处理有个特别的地方就是对合并完的训练集进行了分块,后续利用这个分块进行转化率特征的提取以及统一利用其中一个分块数据作为验证集。
训练
以src\nffm_final\004_train_1.py为例,基于NFFM模型的广告点击率预测训练。
1. 代码概述
该脚本实现了一个基于Neural Field-aware Factorization Machine (NFFM)模型的广告点击率(CTR)预测系统,主要功能包括:
- 定义模型超参数
- 配置特征工程
- 训练NFFM模型
- 生成测试集预测结果
2. 主要组件分析
2.1 超参数配置 (create_hparams()
)
def create_hparams():
return tf.contrib.training.HParams(
k=8, # 隐向量维度
batch_size=4096, # 训练batch大小
optimizer="adam", # 优化器
learning_rate=0.0002, # 学习率
num_display_steps=100, # 显示日志的步数间隔
num_eval_steps=1000, # 评估的步数间隔
l2=0.000002, # L2正则化系数
hidden_size=[128,128], # 神经网络隐藏层大小
evl_batch_size=5000, # 评估batch大小
all_process=3, # 处理进程数
idx=1,
epoch=int(44628906//4096), # 训练epoch数(总样本数/batch_size)
mode='train', # 运行模式
data_path='./ffm_data/', # 数据路径
sub_name='sub' # 提交文件前缀
)
2.2 特征工程配置
单值特征 (single_features
)
single_features=[
# 基础广告特征
'aid','advertiserId','campaignId','creativeId','creativeSize','adCategoryId',
'productId','productType',
# 用户基础特征
'age','gender','education','consumptionAbility','LBS','carrier','house',
# 广告-用户交叉特征
'aid_age','aid_gender','aid_LBS',
# CVR(转化率)相关特征
'cvr_of_creativeId_and_onehot2','cvr_of_creativeId_and_onehot9',
'cvr_of_creativeId_and_onehot16','cvr_of_consumptionAbility_and_onehot1',
# ...(其他CVR特征)
# 点击比例特征
'ratio_click_of_aid_in_uid','ratio_click_of_creativeSize_in_uid',
'ratio_click_of_age_in_aid','ratio_click_of_age_in_creativeSize',
# ...(其他点击比例特征)
]
多值特征 (mutil_features
)
mutil_features=[
'interest1','interest2','interest3','interest4','interest5', # 兴趣标签
'kw1','kw2','kw3', # 关键词
'topic1','topic2','topic3', # 主题
'appIdAction','appIdInstall', # APP行为
'marriageStatus','ct','os' # 其他特征
]
2.3 特征分组
# 广告相关特征组
hparams.aid=[
'aid','advertiserId','campaignId','creativeId','creativeSize',
'adCategoryId','productId','productType',
# 精选的CVR特征
'cvr_of_creativeId_and_onehot2','cvr_of_creativeId_and_onehot9',
# ...(其他精选CVR特征)
'cvr_of_aid_and_age','cvr_of_creativeSize','cvr_of_uid_and_adCategoryId',
'ratio_click_of_productType_in_uid'
]
# 用户相关特征组
hparams.user=[
'age','gender','education','consumptionAbility','LBS','carrier','house',
'interest1','interest2','interest3','interest4','interest5',
'kw1','kw2','kw3','topic1','topic2','topic3',
'appIdAction','appIdInstall','marriageStatus','ct','os',
# 广告-用户交叉特征
'aid_age','aid_gender','aid_LBS',
# 精选的CVR特征
'cvr_of_consumptionAbility_and_onehot1','cvr_of_age_and_onehot10',
'cvr_of_uid'
]
3. 模型训练与预测
# 训练NFFM模型
preds = nffm.train(hparams)
# 生成预测结果
test_df = pd.read_csv('../final_competition_data/test2.csv')
test_df['score'] = preds
test_df['score'] = test_df['score'].apply(lambda x: round(x, 9))
test_df[['aid', 'uid', 'score']].to_csv('submission_nffm_75866_1.csv', index=False)
4. 技术亮点
- NFFM模型架构:
- 结合了Field-aware Factorization Machines(FFM)和深度神经网络的优势
- 能够有效处理高维稀疏特征
- 精细的特征工程:
- 包含基础广告特征、用户特征、交叉特征
- 使用CVR(转化率)特征作为重要信号
- 包含点击比例特征反映用户行为模式
- 特征分组策略:
- 将特征明确分为广告相关(aid)和用户相关(user)组
- 有助于模型更好地学习不同领域的特征交互
- 工程优化:
- 使用GPU加速训练(CUDA_VISIBLE_DEVICES配置)
- 合理的batch size和训练步数设置
这个实现展示了一个完整的CTR预测流程,从特征工程到模型训练再到预测生成,结构清晰且考虑了广告推荐系统中的关键因素。
执行步骤
按文件名顺序依次运行代码,先后完成:数据预处理、提取特征工程、模型训练、测试集预测与模型结果融合。
文件:run.sh
# 复赛数据预处理
echo --------------------final_competition_data--------------------------
python ./src/001_final_merge.py
# sparse
echo ---------------------------------sparse------------------------------------
python ./src/002_sparse_one.py
python ./src/002_sparse_one_select.py
python ./src/003_sparse_two.py
python ./src/003_sparse_two_select.py
# length
echo -------------------------------length------------------------------------
python ./src/004_length_ratio.py
# cvr
echo ---------------------------------cvr------------------------------------
python ./src/005_cvr.py
python ./src/005_cvr_select.py
python ./src/005_cvr_select2.py
# click
echo --------------------------------click------------------------------------
python ./src/006_click.py
python ./src/006_click_select.py
# ratio
echo --------------------------------ratio------------------------------------
python ./src/007_ratio.py
python ./src/007_ratio_select.py
# unique
echo -------------------------------unique------------------------------------
python ./src/008_unique.py
python ./src/008_unique_select.py
# CV_cvr
echo ------------------------------- CV_cvr------------------------------------
python ./src/009_CV_cvr.py
python ./src/009_CV_cvr_select.py
python ./src/009_CV_cvr_select2.py
# lightgbm 部分
echo --------------------------------lightgbm------------------------------------
python ./src/010_train_predict.py
python ./src/011_ronghe.py
# 加入初赛数据进行构造特征
echo ----------------------preliminary_competition_data--------------------------
python ./src/012_merge_part_p.py
python ./src/013_stat_p.py
python ./src/014_CV_cvr_p.py
python ./src/014_CV_cvr_select_p.py
python ./src/015_length_p.py
python ./src/016_sparse_p.py
# 融合得到lgb模型的最终结果
echo --------------------------------lightgbm------------------------------------
python ./src/017_train_predict_p.py
python ./src/018_rong_p.py
# nffm 部分
# nffm 复赛数据训练
echo --------------------------------nffm final------------------------------------
python ./src/nffm_final/001_prepared_data.py
python ./src/nffm_final/001_select_feat.py
python ./src/nffm_final/002_doFeature.py
python ./src/nffm_final/003_extract_features.py
python ./src/nffm_final/004_train_0.py
python ./src/nffm_final/004_train_1.py
python ./src/nffm_final/004_train_2.py
# nffm 初赛加复赛数据训练
echo --------------------------------nffm final preliminary------------------------------------
python ./src/nffm_final_preliminary/001_prepared_data.py
python ./src/nffm_final_preliminary/001_select_feat.py
python ./src/nffm_final_preliminary/002_doFeature.py
python ./src/nffm_final_preliminary/003_extract_features.py
python ./src/nffm_final_preliminary/nffm_train_763.py
python ./src/nffm_final_preliminary/nffm_train_765.py
python ./src/nffm_final_preliminary/nffm_train_7688.py
# 最终融合
echo ---------------------------------------blending--------------------------------------------
python ./src/019_ronghe_lgb_nffm.py
执行过程:
python ./src/001_final_merge.py
Reading...
0
1000000
2000000
3000000
4000000
5000000
6000000
7000000
8000000
9000000
10000000
11000000
12000000
。。。
最后输出到文件:../submission.csv
源码开源协议
作者:LiuPengsay/Algorithm Engineer at Huawei Tencent2018AdsRank11/儿须成名酒须醉
来源:机器学习算法竞赛
四、获取案例套装
文件大小:约 8 GB
获取大容量AI案例套装:广告传媒业自然语言处理案例套装