一个query属不属于音乐,这和咱们对音乐的理解有很大的关系,须要进行产品上的定义。如你会唱歌吗,刘德华,换一首音乐,如何让孩子爱上学习等,既能够属于音乐也能够不属于音乐。对音乐的理解最终落到标注数据上,继而来影响咱们的打分模型给出高分或者低分。html
咱们对query进行了不少的清理、转换、知识查询、类似度计算、拼音转换、纠错、句型辅助等工做,因此要从里面找到对query是否归属于音乐领域有影响的特征。咱们目前抽取了slot数、各slot抽取状况、slot的组合、总体类似度、资源热度、歌手职业、标签数、标签强度、主干query长度、音乐日志、句型得分、意图词得分等特征,特征还在增长。java
服务为了配合抽特征的须要进行了改造,针对特定的deviceid,返回中间计算过程当中的各特征值。python
在上机器学习模型前,咱们是用人工规则来进行的打分,针对各类状况写了复杂的if-else,是一步步的决策过程,因此选打分模型时,天然选择了决策树(GBDT)。离线模型的训练使用了python xgboost。windows
标注数据:咱们共标注了近5万条数据,音乐近2万,其余领域数据近3万作为反例。经过服务解析,将query转换成特征集,libsvm格式(label \t id:value \t id:value)。bash
0 0:0.0000 1:0.0000 2:0.0000 3:0.0000 4:0.0000 5:0.0000 6:0.5000 7:0.0000 .. 0 0:0.0000 1:0.0000 2:0.0000 3:0.0000 4:0.0000 5:0.0000 6:1.0000 7:0.0000 .. 1 0:1.0000 1:1.0000 2:0.0000 3:0.0000 4:1.0000 5:0.0000 6:0.7000 7:0.0000 ..
训练集/测试集拆分:训练集占数据集的比例通常为2/3 - 4/5,而且须要保证训练集/测试集中的类别平衡(正负比例和数据集中的一致)。咱们随机抽取了1/5的数据做为测试集。机器学习
调节参数:xgboost支持对eta(学习率)、max_depth(树的最大深度)、lambda(L2正则化因子)等,使用了模拟退火对参数进行调优,给每一个参数指定起取值范围、步长。训练过程当中,每次随机选择一个参数对其增长或减少一个步长,训练一个模型算出其在测试集上的精度作为模型的评价值。学习
样本补充:测试调节过程当中,会碰到一些case特征没有被学到(想让这一类case打分高,却打了低分),这时就人工补充必定量的这类数据到训练集中,再从新训练模型。我是对没有学到的case给重复增长了10条。测试
另外:日志
gbdt支持一个样本丢失部分特征,对于不存在的特征,咱们进行了丢弃,以避免干扰选择。htm
为了保证特征名和特征索引的一致,在离线训练的时候,把特征统一存在了一个文件中;在线服务抽取特征时用了枚举定义。更好的办法,能够写一个thrift定义,保证在线离线的统一。
xgboost提供的java版xgboost4j须要依赖底层本地实现的支持,用的过程当中windows没有编译成功。因为xgboot导出的模型有可读的文本版本,就使用了组里自实现的加载模型决策树java代码。
booster[0]: 0:[wholeSim<0.80175] yes=1,no=2,missing=1,gain=9265.91,cover=18714.5 1:[intentScore<0.95] yes=3,no=4,missing=3,gain=972.265,cover=12050.5 3:[tagSim<0.6795] yes=7,no=8,missing=7,gain=465.15,cover=11553.5 7:[rank<0.97265] yes=13,no=14,missing=13,gain=389.613,cover=11183.5
在模型打分后,保留了一些规则(如slot正向/负向得分,用于修复紧急case。
后续会继续增长特征,另外想引入语言模型,对抽取的slot用entity名代替,而后来训练出一个word embedding或者其余的语言模型。
参考:http://xgboost.readthedocs.io/en/latest/python/python_intro.html#install-xgboost