重排配置
重排(Sort)阶段在精排之后进行,在这里可以进行排序以及打散、添加窗口规则等逻辑
如何配置
重排的配置对应配置总览中的 SortConfs,SortConfs 是一个 []object 结构,可以配置多个重排策略,目前 pairec 内置的有 BoostScoreSort、BoostScoreByWeight、ItemRankScore、DiversityRuleSort、DPPSort、MultiRecallMixSort。
重排公共配置一览
每种重排配置,都会用到公共配置中的一部分,在此统一解释,单独的重排配置中则不再赘述。
配置示例:
"SortConfs":[
{
"Name":"",
"SortType":""
}
]
字段名 | 类型 | 是否必填 | 描述 |
Name | string | 是 | 自定义重排名称,可以在 SortNames 中引用 |
SortType | string | 是 | 排序类型,枚举值
|
提降权重排(BoostScoreSort)
当调用精排模型后,每个 item 会有个模型返回的 score, 有时候根据业务运营需求,需要对 score 进行操作,即提降权操作。
提降权操作在设置上分为两部分
设置条件规则,通过 item 或者 user 的某些属性,比如类目,性别等属性来判断是否符合规则条件
设置提降权表达式,目前只支持对 score 设置表达式,比如 score * 1.2, score * 0.5 等等
配置示例
"SortConfs":[
{
"Name":"BoostScoreSort",
"SortType":"BoostScoreSort",
"Debug":false,
"BoostScoreConditions":[
{
"Conditions":[
{
"Name":"sex",
"Domain":"item",
"Type":"string",
"Value":"gender",
"Operator":"equal"
}
],
"Expression":"score * 2"
}
]
}
]
上面配置中所表达的意思为:对 特征(sex)的值等于 male 的item,score乘以2。
字段名 | 类型 | 是否必填 | 描述 |
Name | string | 是 | 自定义 sort 名称 |
SortType | string | 是 | 重排类型,固定值: BoostScoreSort |
Debug | bool | 否 | 测试标记,这里为 true 情况下, 提降权之前的原始 score 会以 org_score 记录到 item 的 properties 中,然后请求中打开 debug 标记,可以看到 item属性值。这只为了方便调试,线上不应该打开 |
BoostScoreConditions | json array | 是 | 提降权的条件配置,可以配置多个,可以根据不同的条件,进行提降权 |
| []FilterParamConfig | 是 | 提降权的条件规则 |
| string | 是 | 提降权 score 的表达式, score 表示当前的物品得分。表达式里可以引用 item 的属性,比如 item_weight 是 item 的属性,表达式可以这样设置: score * item_weight 。 |
FilterParamConfig 配置如下:
字段名 | 类型 | 是否必填 | 描述 |
Name | string | 是 | item 或者 user 的特征名 |
Domain | string | 是 | 枚举值,item/user。指的是 Name 选项属于 item 特征还是 user 特征,Name 必须在 item 或 user 的 properties 里找到。 |
Operator | string | 是 | 枚举值:equal/not_equal/in/not_in/greater/greaterThan/less/lessThan/contains/not_contains |
Type | string | 是 | 特征的类型 |
Value | object | 是 | 特征的值 |
具体的条件设置,可以参考数量调整过滤(AdjustCountFilter)。
权重提降权重排(BoostScoreByWeight)
在对item进行提降权的时候,不同的item可能会有不同的权重,这个权重是item表中的一个字段,需要通过权重字段对score进行提降权。
score的计算公式:weight * item.score
配置示例
"SortConfs":[
{
"Name":"BoostScoreByWeight",
"SortType":"BoostScoreByWeight",
"TimeInterval":172800,
"BoostScoreByWeightDao":{
"AdapterType":"hologres",
"HologresName":"pai_rec",
"HologresTableName":"test",
"ItemFieldName":"item_id",
"WeightFieldName":"weight"
}
}
]
BoostScoreByWeightDao
字段名 | 类型 | 是否必填 | 描述 |
AdapterType | string | 是 | 数据源的类型,当前只支持 hologres |
HologresName | string | 是 | 在数据源配置(HologresConfs)中配置好的 holo 的自定义名称,如数据源配置中的 holo_info |
HologresTableName | string | 是 | holo 中 item 权重表的表名 |
ItemFieldName | string | 是 | item 权重表的主键 |
WeightFieldName | string | 是 | item 权重表中的权重字段 |
Item分数重排(ItemRankScore)
ItemRankScore 可以通过 item 的 score 对 item 进行倒序排序,这个是引擎内置的,可以直接在 SortNames 中使用。
多样性重排(DiversityRuleSort)
在推荐结果进行输出时,我们除了考虑要抓住用户的兴趣点,还要考虑推荐条目多样性的需求,即不同品类,不同属性的物品可以混合输出。
这里我们配置的规则参考如下:
配置示例
"SortConfs":[
{
"Name": "DiversityRuleSort",
"SortType": "DiversityRuleSort",
"DiversitySize": 100,
"DiversityRules": [
{
"Dimensions": [
"spfl"
],
"WindowSize": 10,
"FrequencySize": 1
}
],
"ExcludeRecalls": [
"ColdStartVideoVectorRecall",
"LinUcbRecall_default2"
],
"Conditions": [
{
"Name": "spflPick",
"Domain": "user",
"Type": "string",
"Value": "",
"Operator": "equal"
}
]
}
]
此重排需要配合 ExcludeRecalls 参数使用。
DiversityRules
字段名 | 类型 | 是否必填 | 描述 |
Name | string | 是 | 自定义 sort 名称 |
SortType | string | 是 | 重排类型,固定值: BoostScoreSort |
DiversitySize | int | 否 | 打散的物品数量,默认值为请求的 size 大小 |
Conditions | []FilterParamConfig | 否 | 打散规则条件,符合一定条件下才能走打散规则。具体条件设置,可以参考条件匹配 Operator 示例。这里的条件是根据 user 的属性来设置的,需要设置 Domain = user |
ExcludeRecalls | []string | 否 | 需要排除多样性排序的召回 id 列表 |
DiversityRules | json array | 是 | 打散规则,可以设置多条规则 |
| []string | 是 | 根据物品 item 的哪些属性进行打散 |
| int | 是 | 控制最小间隔,上面描述的 k 值 |
| int | 否 | 窗口大小, 上面描述的 n 值 |
| int | 否 | 窗口内重复的次数, 上面描述的 m 值 |
DPPSort
DPP多样性打散算法参考资料:《基于行列式点过程的推荐多样性提升算法的直观理解》。
前提条件:使用DPP算法的前提是已经有了item里的embedding向量,而且这个embedding向量能够表示 item 本身的内容,embedding的相似度能够表示item内容层面的相似度,而不是其他层面(如行为)的相似度。举例如下:
建议:item图片embedding/文本描述信息的embedding/类目、属性等静态item内容组合得到embedding
不建议:基于用户行为数据训练模型得到的embedding
本质上,想要打散的维度一定要能够在embedding里反映出来。比如,我们希望在推荐列表在商品价格这个维度有一些多样性,那么在训练模型得到embedding向量时就一定要有价格特征,否则就无法达到我们预期的效果。
配置示例:
"SortConfs":[
{
"Name":"DPPSort",
"SortType":"DPPSort",
"DPPConf":[
{
"Name":"DPPSort",
"DaoConf":{
"AdapterType":"hologres",
"HologresName":"geeko_rec"
},
"TableName":"item_embedding_metric_learning",
"TableSuffixParam":"embedding_date",
"TablePKey":"product_id",
"EmbeddingColumn":"embedding",
"Alpha":4.5,
"NormalizeEmb":"false",
"WindowSize":10
}
]
}
]
DPPConf
字段名 | 类型 | 是否必填 | 描述 |
Name | string | 是 | 自定义 sort 名称 |
TableName | string | 否 | holo中 item的embedding向量表表名;当没有配置EmbeddingHookNames时必填 |
TableSuffixParam | string | 否 | 不为空时,表示需要去pairec配置中心获取场景名为pairec的配置项。配置项的key为${SuffixParam},获取到的value作为TableName的后缀;用来daily切换向量表名,保持embedding是最新的版本;此时Hologres的表一般需要设置为分区表 |
TablePKey | string | 否 | embedding向量表的主键 |
EmbeddingColumn | string | 否 | embedding向量表的向量字段名 |
EmbeddingSeparator | string | 否 | embedding向量的分隔符,默认为英文逗号 |
Alpha | float | 是 | DPP算法用来平衡相关性和多样性的参数;值越大越偏向于相关性 |
CacheTimeInMinutes | int | 否 | embedding向量缓存在内存的时间,默认值:360 |
EmbeddingHookNames | []string | 否 | 生成item embedding的函数名, 需要提前注册好 |
NormalizeEmb | string | 否 | 是否需要对embedding向量做L2 normalize;如果生成embedding时已经做了L2 normalize则不需要再做,否则需要配置为true |
WindowSize | int | 否 | 多样性算法的翻滚窗口大小;只保证窗口内的item列表的多样性;默认值为10 |
EmbMissedThreshold | float | 否 | 当缺失embedding的item占比高于该值时报错,默认值为0.5 |
FilterRetrieveIds | []string | 否 | 指定不需要调用DPP模块的item列表,如冷启动item |
EnsurePositiveSim | string | 否 | 是否需要保证基于embedding计算的item相似度是正值,默认值:true |
多路召回重排(MultiRecallMixSort)
一般情况下,我们会有很多路召回,有时根据业务运营需求,需要根据召回的类型进行混合输出,比如
对冷启动召回有曝光数量的要求
多某一路召回有位置的要求
也可能包括多个混排规则。
配置如下
"SortConfs":[
{
"Name":"MixSort",
"SortType":"MultiRecallMixSort",
"RemainItem":false,
"MixSortRules":[
{
"MixStrategy":"random_position",
"NumberRate":0.1,
"RecallNames":[
"OTSGlobalHot"
]
},
{
"MixStrategy":"fix_position",
"Positions":[
1,
3,
5
],
"RecallNames":[
"RecallName1"
]
}
]
}
]
除了使用召回名称来匹配条目进行过滤,还可以使用条件过滤筛选出 item , 然后进行曝光。
"SortConfs":[
{
"Name":"MixSortByItemFeature",
"SortType":"MultiRecallMixSort",
"RemainItem":false,
"MixSortRules":[
{
"MixStrategy":"random_position",
"NumberRate":0.1,
"Conditions":[
{
"Name":"gender",
"Domain":"item",
"Type":"string",
"Value":"man",
"Operator":"equal"
}
]
}
]
}
]
字段名 | 类型 | 是否必填 | 描述 |
Name | string | 是 | 自定义 sort 名称 |
SortType | string | 是 | 重排类型,固定值: MultiRecallMixSort |
RemainItem | bool | 否 | 是否保留所有的item , 比如有 500 个 item 需要处理,但我们一次请求假设有 30 个, 当为 false 情况下, item 数量只会保留混排的结果, 当为 true 情况下, 剩余的 item 也保留下来,不过在 30 item 结果的后面。 这样后续还可以再对接 sort 进行进一步控制处理 |
MixSortRules | json array | 是 | 打散规则,可以设置多个 |
| string | 是 | 混排策略,枚举值:random_position/fix_position
|
| []int | 否 | fix_position 的情况下,需要指定 Positions。 Positions 的位置从 1 开始 |
| string | 否 | fix_position 的情况下,通过 item 的属性字段获取 Postion。Positions 和 PositionField 冲突,只能设置其中一项 |
| int | 否 | 数量的绝对值。 |
| float | 否 | 混排物品数量占比,只有MixStrategy=random_position 时设置,有效值为 0 ~ 1, 具体数量通过 请求的Size * NumberRate 算出 |
| []string | 否 | 召回的名称,可以设置多个,设置多个的情况下,共享配置,但是具体哪个召回,不固定,顺序由进入到此 Sort 的位置决定 |
| []FilterParamConfig | 否 | 符合匹配条件的物品进行混排。具体条件设置,可以参考条件匹配 Operator 示例。 |
如何使用
重排配置和召回配置类似,配置好之后,提供一个分场景使用的SortNames,SortNames是一个 Map[string]object结构,其中key是场景,每个场景对应一组重排策略
"SortNames": {
"default": [
"ItemRankScore"
]
}
default 为场景名,如果场景没有显式的配置,则使用"default"的配置。
ItemRankScore:此参数为在SortConfis中定义的重排的自定义名称。