Authored by hugufei

品类价格带添加AB测试

... ... @@ -55,7 +55,7 @@ public class UserRecallResponseBuilder {
sknResultList = this.fillBaseInfo(sknResultList);
//4、填充是否满足品类价格带的过滤
sknResultList = this.fillIsLikePriceArea(sknResultList, userPersonalFactor);
sknResultList = this.fillIsLikePriceArea(userRecallRequest.getUid(),sknResultList, userPersonalFactor);
//5、按相关性计算得分
sknResultList = this.doCalScoreAndSort(sknResultList, userRecallRequest.getUid());
... ... @@ -130,7 +130,7 @@ public class UserRecallResponseBuilder {
* @param sknResults
* @return
*/
private List<RecallMergerResult.SknResult> fillIsLikePriceArea(List<RecallMergerResult.SknResult> sknResults, UserPersonalFactor userPersonalFactor) {
private List<RecallMergerResult.SknResult> fillIsLikePriceArea(int uid, List<RecallMergerResult.SknResult> sknResults, UserPersonalFactor userPersonalFactor) {
//1、获取用户价格带偏好
List<SortPriceAreas> userSortPriceAreasList = userPersonalFactor.getSortPriceAreasList();
if (userSortPriceAreasList == null || userSortPriceAreasList.isEmpty()) {
... ... @@ -144,16 +144,67 @@ public class UserRecallResponseBuilder {
//3、填充当前skn是否属于用户偏好的价格带
for (RecallMergerResult.SknResult sknResult : sknResults) {
Integer misortId = sknResult.getMiddleSortId();
List<Integer> priceAreas = userMisort2PriceAreasMap.getOrDefault(misortId, new ArrayList<>());
if (priceAreas.contains(sknResult.getPriceArea())) {
sknResult.setLikePriceArea(true);
} else {
sknResult.setLikePriceArea(false);
}
List<Integer> userPriceAreas = userMisort2PriceAreasMap.getOrDefault(misortId, new ArrayList<>());
boolean isLikePriceArea = this.isLikePriceArea(uid,userPriceAreas,sknResult.getPriceArea());
sknResult.setLikePriceArea(isLikePriceArea);
}
return sknResults;
}
/**
* AB test
* @param uid
* @param userPriceAreas
* @param sknPriceArea
* @return
*/
private boolean isLikePriceArea(int uid, List<Integer> userPriceAreas,Integer sknPriceArea){
if(userPriceAreas==null || userPriceAreas.isEmpty()){
return false;
}
if(uid%2==1){
if(searchDynamicConfigService.isAStrategyOpen()){
return isLikePriceAreaWithAStrategy(userPriceAreas,sknPriceArea);
}else{
return isLikePriceAreaWithBStrategy(userPriceAreas,sknPriceArea);
}
}else{
if(searchDynamicConfigService.isBStrategyOpen()){
return isLikePriceAreaWithBStrategy(userPriceAreas,sknPriceArea);
}else{
return isLikePriceAreaWithAStrategy(userPriceAreas,sknPriceArea);
}
}
}
private boolean isLikePriceAreaWithAStrategy(List<Integer> userPriceAreas,Integer sknPriceArea){
return userPriceAreas.contains(sknPriceArea);
}
/**
* 价格带左右各扩展一位
* @param userPriceAreas
* @param sknPriceArea
* @return
*/
private boolean isLikePriceAreaWithBStrategy(List<Integer> userPriceAreas,Integer sknPriceArea){
Collections.sort(userPriceAreas);
int min = userPriceAreas.get(0);
int max = userPriceAreas.get(userPriceAreas.size()-1);
int leftCount = min<=1 ? 0 : max>=7 ? 2 : 1;
int rightCount = min<=1 ? 2 : max>=7 ? 0 : 1;
for(int i = 1;i<=leftCount;i++){
if(min-i>=1){
userPriceAreas.add(0,min-i);
}
}
for(int i = 1;i<=rightCount;i++){
if(max+i<=7){
userPriceAreas.add(max+i);
}
}
return userPriceAreas.contains(sknPriceArea);
}
/**
* 粗排-按相关性计算得分,并按得分排序
... ... @@ -304,24 +355,24 @@ public class UserRecallResponseBuilder {
}
public static void main(String[] args) {
List<Integer> fromList = new ArrayList<>();
for (int index =1;index <=30;index ++){
fromList.add(index);
List<Integer> userPriceAreas = new ArrayList<>();
userPriceAreas.addAll(Arrays.asList(5,6,7));
Collections.sort(userPriceAreas);
int min = userPriceAreas.get(0);
int max = userPriceAreas.get(userPriceAreas.size()-1);
int leftCount = min<=1 ? 0 : max>=7 ? 2 : 1;
int rightCount = min<=1 ? 2 : max>=7 ? 0 : 1;
for(int i = 1;i<=leftCount;i++){
if(min-i>=1){
userPriceAreas.add(0,min-i);
}
}
List<Integer> toList = new ArrayList<>();
for (int index =0;index <100;index ++){
toList.add(0);
for(int i = 1;i<=rightCount;i++){
if(max+i<=7){
userPriceAreas.add(max+i);
}
}
addByIndexIndex(fromList, toList, 1, 2, (value -> value%2==1),null);
addByIndexIndex(fromList, toList, 2, 3, (value -> value%2==0),null);
System.out.println(toList);
// addByIndexIndex(fromList, toList, 4, 4, (value -> value%2==0));
// System.out.println(toList);
System.out.println(userPriceAreas);
}
}
... ...
... ... @@ -48,8 +48,6 @@ public class SknRecallCacheBean {
private SearchRedis searchRedis;
@Autowired
private EhCache ehCache;
@Autowired
private SearchDynamicConfigService searchDynamicConfigService;
private static final Boolean recallWithCache = false;
... ... @@ -66,7 +64,7 @@ public class SknRecallCacheBean {
filterSknList.addAll(userPersonalFactor.getRecommendSknList());
}
//1.1添加AB-Test逻辑
if (searchDynamicConfigService.isAbTestUser(userRecallRequest.getUid()) && userPersonalFactor.getRealTimeSimilarSknList() != null) {
if (userPersonalFactor.getRecommendSknList() != null) {
filterSknList.addAll(userPersonalFactor.getRealTimeSimilarSknList());
}
//2、执行查询
... ... @@ -80,9 +78,7 @@ public class SknRecallCacheBean {
List<RecallRequestResponse> results = new ArrayList<>();
ParamQueryFilter paramQueryFilter = userRecallRequest.getParamQueryFilter();
results.addAll(this.buildResults(paramQueryFilter, userPersonalFactor.getRecommendSknList(), RecommendSknStrategy.class, filterSknResults, maxReturnCount));
if(searchDynamicConfigService.isAbTestUser(userRecallRequest.getUid())){
results.addAll(this.buildResults(paramQueryFilter, userPersonalFactor.getRealTimeSimilarSknList(), RealTimeSimilarSknStrategy.class, filterSknResults, maxReturnCount));
}
results.addAll(this.buildResults(paramQueryFilter, userPersonalFactor.getRealTimeSimilarSknList(), RealTimeSimilarSknStrategy.class, filterSknResults, maxReturnCount));
return results;
} catch (Exception e) {
RECALL_NEW_LOGGER.error(e.getMessage(), e);
... ...
... ... @@ -242,18 +242,19 @@ public class SearchDynamicConfigService {
}
/**
* 奇数的uid使用AB-TEST
* A策略是否打开
* @return
*/
public boolean isAbTestUser(int uid) {
boolean abTestOpen = configReader.getBoolean("search.persional.abTest.open", false);
if(!abTestOpen){
return true;
}
if(uid%2==1){
return true;
}
return false;
public boolean isAStrategyOpen() {
return configReader.getBoolean("search.persional.abTest.a.strategy.open", true);
}
/**
* B策略是否打开
* @return
*/
public boolean isBStrategyOpen() {
return configReader.getBoolean("search.persional.abTest.b.strategy.open", true);
}
}
... ...
... ... @@ -62,7 +62,8 @@ search.persional.newstrategy.max_join_sort_brand.count=20
search.persional.newstrategy.directtrain.index.interval=4
search.persional.newstrategy.sort_brand_balance.open=false
search.persional.abTest.open=true
search.persional.abTest.a.strategy.open=true
search.persional.abTest.b.strategy.open=true
#rateLimit
search.persional.rateLimit.open=true
... ...