Преглед на файлове

Merge branch 'feature_20250228_new_label_model' of algorithm/recommend-server into master

zhaohaipeng преди 1 месец
родител
ревизия
9c53b50976

+ 48 - 5
recommend-server-service/src/main/java/com/tzld/piaoquan/recommend/server/service/FeatureService.java

@@ -9,6 +9,7 @@ import com.tzld.piaoquan.recommend.server.service.rank.RankParam;
 import com.tzld.piaoquan.recommend.server.util.JSONUtils;
 import lombok.Data;
 import lombok.extern.slf4j.Slf4j;
+import org.apache.commons.collections4.MapUtils;
 import org.apache.commons.lang3.StringUtils;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
@@ -166,16 +167,16 @@ public class FeatureService {
             protos.add(genWithVidAndProvince("alg_vid_feature_feed_province_root_return_v2", vid, province));
 
             // headvid + vid
-            //protos.add(genWithKeyMap("alg_recsys_feature_cf_i2i_new_v2", vid, ImmutableMap.of("vid_a", headVid, "vid_b", vid)));
+            // protos.add(genWithKeyMap("alg_recsys_feature_cf_i2i_new_v2", vid, ImmutableMap.of("vid_a", headVid, "vid_b", vid)));
 
             // ********************* new vid ******************
             protos.add(genWithKeyMap("alg_vid_feature_day", vid, ImmutableMap.of("vid", vid)));
             protos.add(genWithKeyMap("alg_sence_type_feature", vid, ImmutableMap.of("sence_type", sceneType, "videoid", vid)));
             protos.add(genWithKeyMap("alg_videoid_feature", vid, ImmutableMap.of("videoid", vid)));
-            //protos.add(genWithKeyMap("alg_recsys_feature_cf_i2i_scene_rov", vid, ImmutableMap.of("sence_type", i2iSceneType, "vid_a", headVid, "vid_b", vid)));
-            //protos.add(genWithKeyMap("alg_recsys_feature_cf_i2i_scene_ros", vid, ImmutableMap.of("sence_type", i2iSceneType, "vid_a", headVid, "vid_b", vid)));
-            //protos.add(genWithKeyMap("alg_recsys_feature_weak_cf_i2i_scene_rov", vid, ImmutableMap.of("sence_type", i2iSceneType, "vid_a", headVid, "vid_b", vid)));
-            //protos.add(genWithKeyMap("alg_recsys_feature_weak_cf_i2i_scene_ros", vid, ImmutableMap.of("sence_type", i2iSceneType, "vid_a", headVid, "vid_b", vid)));
+            // protos.add(genWithKeyMap("alg_recsys_feature_cf_i2i_scene_rov", vid, ImmutableMap.of("sence_type", i2iSceneType, "vid_a", headVid, "vid_b", vid)));
+            // protos.add(genWithKeyMap("alg_recsys_feature_cf_i2i_scene_ros", vid, ImmutableMap.of("sence_type", i2iSceneType, "vid_a", headVid, "vid_b", vid)));
+            // protos.add(genWithKeyMap("alg_recsys_feature_weak_cf_i2i_scene_rov", vid, ImmutableMap.of("sence_type", i2iSceneType, "vid_a", headVid, "vid_b", vid)));
+            // protos.add(genWithKeyMap("alg_recsys_feature_weak_cf_i2i_scene_ros", vid, ImmutableMap.of("sence_type", i2iSceneType, "vid_a", headVid, "vid_b", vid)));
             if (null != videoBaseInfoMap && videoBaseInfoMap.containsKey(vid)) {
                 Map<String, Map<String, String>> videoInfo = videoBaseInfoMap.get(vid);
                 if (null != videoInfo && videoInfo.containsKey("alg_vid_feature_basic_info")) {
@@ -317,6 +318,48 @@ public class FeatureService {
         return getFeatureByProto(protos);
     }
 
+    public Feature getFeatureByNewLabel(String appType, String hotSceneType, String province, String brand, String mid, String headVideoId, List<String> vidList, Map<String, Map<String, Map<String, String>>> videoBaseInfoMap) {
+
+        List<FeatureKeyProto> protos = new ArrayList<>();
+        // 视频维度的特征
+        for (String vid : vidList) {
+            protos.add(this.genWithKeyMap("alg_vid_global_feature_20250212", vid, ImmutableMap.of("vid", vid)));
+            protos.add(this.genWithKeyMap("alg_vid_recommend_exp_feature_20250212", vid, ImmutableMap.of("vid", vid)));
+            protos.add(this.genWithKeyMap("alg_vid_recommend_flowpool_exp_feature_20250212", vid, ImmutableMap.of("vid", vid)));
+            protos.add(this.genWithKeyMap("alg_vid_apptype_recommend_exp_feature_20250212", vid, ImmutableMap.of("vid", vid, "apptype", appType)));
+            protos.add(this.genWithKeyMap("alg_vid_province_recommend_exp_feature_20250212", vid, ImmutableMap.of("vid", vid, "province", province)));
+            protos.add(this.genWithKeyMap("alg_vid_brand_recommend_exp_feature_20250212", vid, ImmutableMap.of("vid", vid, "brand", brand)));
+            protos.add(this.genWithKeyMap("alg_vid_hotsencetype_recommend_exp_feature_20250212", vid, ImmutableMap.of("vid", vid, "hotscenetype", hotSceneType)));
+            protos.add(this.genWithKeyMap("scene_type_vid_cf_feature_20250212", vid, ImmutableMap.of("vid_a", headVideoId, "vid_b", vid, "sence_type", hotSceneType)));
+            protos.add(this.genWithKeyMap("vid_click_cf_feature_20250212", vid, ImmutableMap.of("vid_a", headVideoId, "vid_b", vid)));
+            protos.add(this.genWithKeyMap("alg_recsys_feature_cf_i2i_v2", vid, ImmutableMap.of("vid_a", headVideoId, "vid_b", vid)));
+
+            if (MapUtils.isNotEmpty(videoBaseInfoMap)) {
+                Map<String, Map<String, String>> baseInfo = videoBaseInfoMap.getOrDefault(vid, new HashMap<>());
+                Map<String, String> featureMap = baseInfo.getOrDefault("alg_vid_feature_basic_info", new HashMap<>());
+                protos.add(this.genWithKeyMap("alg_channel_recommend_exp_feature_20250212", vid, ImmutableMap.of("channel", featureMap.getOrDefault("channel", "unknown"))));
+                protos.add(this.genWithKeyMap("alg_merge_cate1_recommend_exp_feature_20250212", vid, ImmutableMap.of("merge_cate1", featureMap.getOrDefault("merge_first_level_cate", "unknown"))));
+                protos.add(this.genWithKeyMap("alg_merge_cate2_recommend_exp_feature_20250212", vid, ImmutableMap.of("merge_cate2", featureMap.getOrDefault("merge_second_level_cate", "unknown"))));
+                protos.add(this.genWithKeyMap("alg_video_unionid_recommend_exp_feature_20250212", vid, ImmutableMap.of("video_unionid", featureMap.getOrDefault("title_time_w_h_unionid", "unknown"))));
+
+                protos.add(this.genWithKeyMap("mid_merge_cate1_feature_20250212", vid, ImmutableMap.of("mid", mid, "merge_cate1", featureMap.getOrDefault("merge_first_level_cate", "unknown"))));
+                protos.add(this.genWithKeyMap("mid_merge_cate2_feature_20250212", vid, ImmutableMap.of("mid", mid, "merge_cate2", featureMap.getOrDefault("merge_second_level_cate", "unknown"))));
+
+            }
+        }
+
+
+        // 用户维度特征
+        protos.add(this.genWithMid("mid_global_feature_20250212", mid));
+        protos.add(this.genWithMid("mid_u2u_friend_index_feature_20250212", mid));
+        protos.add(this.genWithMid("alg_mid_feature_return_tags", mid));
+        protos.add(this.genWithMid("alg_mid_feature_share_tags", mid));
+        protos.add(this.genWithMid("alg_mid_feature_sharecf", mid));
+        protos.add(this.genWithMid("alg_mid_feature_returncf", mid));
+
+        return this.getFeatureByProto(protos);
+    }
+
     private Feature getFeatureByProto(List<FeatureKeyProto> protos) {
         Map<String, String> result = remoteService.getFeature(protos);
         Feature feature = new Feature();

+ 38 - 0
recommend-server-service/src/main/java/com/tzld/piaoquan/recommend/server/service/rank/extractor/ExtractorUtils.java

@@ -1,7 +1,11 @@
 package com.tzld.piaoquan.recommend.server.service.rank.extractor;
 
+import java.time.Instant;
+import java.time.LocalDate;
 import java.time.LocalDateTime;
+import java.time.ZoneId;
 import java.time.format.DateTimeFormatter;
+import java.time.temporal.ChronoUnit;
 import java.util.ArrayList;
 import java.util.List;
 import java.util.Map;
@@ -217,6 +221,40 @@ public class ExtractorUtils {
         return (int)bucket;
     }
 
+    public static long getDaysBetween(long timestamp1, long timestamp2) {
+        if (timestamp1 == 0 || timestamp2 == 0) {
+            return 0;
+        }
+        Instant instant1 = Instant.ofEpochSecond(timestamp1);
+        Instant instant2 = Instant.ofEpochSecond(timestamp2);
+
+        LocalDate date1 = instant1.atZone(ZoneId.systemDefault()).toLocalDate();
+        LocalDate date2 = instant2.atZone(ZoneId.systemDefault()).toLocalDate();
+
+        return ChronoUnit.DAYS.between(date1, date2);
+    }
+
+    public static int getHourByTimestamp(long timestamp) {
+        return LocalDateTime
+                .ofInstant(Instant.ofEpochSecond(timestamp), ZoneId.systemDefault())
+                .getHour() + 1;
+    }
+
+    public static int getDayOfWeekByTimestamp(long timestamp) {
+        return LocalDateTime
+                .ofInstant(Instant.ofEpochSecond(timestamp), ZoneId.systemDefault())
+                .getDayOfWeek()
+                .getValue();
+    }
+
+
+    public static double reciprocal(double num) {
+        if (num == 0) {
+            return 0;
+        }
+        return 1.0 / (num + 1);
+    }
+
     public static void main(String[] args) {
 //        System.out.println(ceilLogRate(0.0002));
 //        System.out.println(ceilLogRate(0.01));

+ 107 - 318
recommend-server-service/src/main/java/com/tzld/piaoquan/recommend/server/service/rank/strategy/RankStrategy4RegionMergeModelV565.java

@@ -1,7 +1,6 @@
 package com.tzld.piaoquan.recommend.server.service.rank.strategy;
 
 import com.ctrip.framework.apollo.spring.annotation.ApolloJsonValue;
-import com.tzld.piaoquan.recommend.server.common.ThreadPoolFactory;
 import com.tzld.piaoquan.recommend.server.common.base.RankItem;
 import com.tzld.piaoquan.recommend.server.model.Video;
 import com.tzld.piaoquan.recommend.server.service.FeatureService;
@@ -10,17 +9,14 @@ import com.tzld.piaoquan.recommend.server.service.rank.extractor.ExtractorUtils;
 import com.tzld.piaoquan.recommend.server.service.recall.strategy.*;
 import com.tzld.piaoquan.recommend.server.service.score.ScorerUtils;
 import com.tzld.piaoquan.recommend.server.util.CommonCollectionUtils;
+import com.tzld.piaoquan.recommend.server.util.ExtractFeature20250218;
 import com.tzld.piaoquan.recommend.server.util.FeatureBucketUtils;
-import com.tzld.piaoquan.recommend.server.util.SimilarityUtils;
 import lombok.extern.slf4j.Slf4j;
 import org.apache.commons.collections4.MapUtils;
-import org.apache.commons.math3.util.Pair;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
 
 import java.util.*;
-import java.util.concurrent.Future;
-import java.util.concurrent.TimeUnit;
 import java.util.stream.Collectors;
 
 @Service
@@ -32,16 +28,11 @@ public class RankStrategy4RegionMergeModelV565 extends RankStrategy4RegionMergeM
     @Autowired
     private FeatureService featureService;
 
-    private static final List<String> shortPeriod = Arrays.asList("1h", "2h", "4h", "6h", "12h", "24h", "7d");
-    private static final List<String> middlePeriod = Arrays.asList("14d", "30d");
-    private static final List<String> longPeriod = Arrays.asList("7d", "35d", "90d", "365d");
-    private static final List<String> cfRosList = Collections.singletonList("rosn");
-    private static final List<String> cfRovList = Collections.singletonList("rovn");
-    private static final List<String> videoSimAttrs = Arrays.asList("cate1_list", "cate2", "cate2_list",
-            "keywords", "style", "theme", "title", "topic", "user_value");
-
     @Override
     public List<Video> mergeAndRankRovRecall(RankParam param) {
+
+        long startTime = System.currentTimeMillis();
+
         Map<String, Double> mergeWeight = this.mergeWeight != null ? this.mergeWeight : new HashMap<>(0);
         //-------------------融-------------------
         //-------------------合-------------------
@@ -75,6 +66,19 @@ public class RankStrategy4RegionMergeModelV565 extends RankStrategy4RegionMergeM
         v1 = v1.subList(0, Math.min(mergeWeight.getOrDefault("v1", 5.0).intValue(), v1.size()));
         rovRecallRank.addAll(v1);
         setVideo.addAll(v1.stream().map(Video::getVideoId).collect(Collectors.toSet()));
+        //-------------------scene cf rovn------------------
+        List<Video> sceneCFRovn = extractAndSort(param, SceneCFRovnRecallStrategy.PUSH_FORM);
+        sceneCFRovn = sceneCFRovn.stream().filter(r -> !setVideo.contains(r.getVideoId())).collect(Collectors.toList());
+        sceneCFRovn = sceneCFRovn.subList(0, Math.min(mergeWeight.getOrDefault("sceneCFRovn", 5.0).intValue(), sceneCFRovn.size()));
+        rovRecallRank.addAll(sceneCFRovn);
+        setVideo.addAll(sceneCFRovn.stream().map(Video::getVideoId).collect(Collectors.toSet()));
+        //-------------------scene cf rosn------------------
+        List<Video> sceneCFRosn = extractAndSort(param, SceneCFRosnRecallStrategy.PUSH_FORM);
+        sceneCFRosn = sceneCFRosn.stream().filter(r -> !setVideo.contains(r.getVideoId())).collect(Collectors.toList());
+        sceneCFRosn = sceneCFRosn.subList(0, Math.min(mergeWeight.getOrDefault("sceneCFRosn", 5.0).intValue(), sceneCFRosn.size()));
+        rovRecallRank.addAll(sceneCFRosn);
+        setVideo.addAll(sceneCFRosn.stream().map(Video::getVideoId).collect(Collectors.toSet()));
+
 
         //-------------------排-------------------
         //-------------------序-------------------
@@ -89,217 +93,104 @@ public class RankStrategy4RegionMergeModelV565 extends RankStrategy4RegionMergeM
         String headVid = String.valueOf(param.getHeadVid());
         String sceneType = String.valueOf(param.getHotSceneType());
         Map<String, Map<String, Map<String, String>>> videoBaseInfoMap = featureService.getVideoBaseInfo(headVid, vids);
-        FeatureService.Feature feature = featureService.getNewFeature(provinceCn, param.getMid(), sceneType, headVid, videoBaseInfoMap, vids);
+        String appType = String.valueOf(param.getAppType());
+        String brand = "";
+        if (Objects.nonNull(param.getMachineInfo())) {
+            brand = param.getMachineInfo().getBrand();
+        }
+
+        long ts = System.currentTimeMillis() / 1000;
+
+        FeatureService.Feature feature = featureService.getFeatureByNewLabel(appType, sceneType, provinceCn, brand, param.getMid(), headVid, vids, videoBaseInfoMap);
         Map<String, Map<String, String>> featureOriginUser = feature.getUserFeature();
         Map<String, Map<String, Map<String, String>>> featureOriginVideo = feature.getVideoFeature();
         Map<String, String> headVideoInfo = videoBaseInfoMap.getOrDefault(headVid, new HashMap<>()).getOrDefault("alg_vid_feature_basic_info", new HashMap<>());
 
         // 2 特征处理
         Map<String, Double> userFeatureMapDouble = new HashMap<>();
-        String mid = param.getMid();
-        Map<String, String> c1 = featureOriginUser.getOrDefault("alg_mid_feature_play", new HashMap<>());
-        Map<String, String> c2 = featureOriginUser.getOrDefault("alg_mid_feature_share_and_return", new HashMap<>());
-        Map<String, String> c3 = featureOriginUser.getOrDefault("alg_mid_feature_play_tags", new HashMap<>());
-        Map<String, String> c4 = featureOriginUser.getOrDefault("alg_mid_feature_return_tags", new HashMap<>());
-        Map<String, String> c5 = featureOriginUser.getOrDefault("alg_mid_feature_share_tags", new HashMap<>());
-        Map<String, String> c6 = featureOriginUser.getOrDefault("alg_mid_feature_feed_exp_share_tags_v2", new HashMap<>());
-        Map<String, String> c7 = featureOriginUser.getOrDefault("alg_mid_feature_feed_exp_return_tags_v2", new HashMap<>());
-        Map<String, String> c8 = featureOriginUser.getOrDefault("alg_mid_feature_sharecf", new HashMap<>());
-        Map<String, String> c9 = featureOriginUser.getOrDefault("alg_mid_feature_returncf", new HashMap<>());
-
-        if (!c1.isEmpty()) {
-            userFeatureMapDouble.put("playcnt_6h", Double.parseDouble(c1.getOrDefault("playcnt_6h", "0")));
-            userFeatureMapDouble.put("playcnt_1d", Double.parseDouble(c1.getOrDefault("playcnt_1d", "0")));
-            userFeatureMapDouble.put("playcnt_3d", Double.parseDouble(c1.getOrDefault("playcnt_3d", "0")));
-            userFeatureMapDouble.put("playcnt_7d", Double.parseDouble(c1.getOrDefault("playcnt_7d", "0")));
-        }
-        if (!c2.isEmpty()) {
-            userFeatureMapDouble.put("share_pv_12h", Double.parseDouble(c2.getOrDefault("share_pv_12h", "0")));
-            userFeatureMapDouble.put("share_pv_1d", Double.parseDouble(c2.getOrDefault("share_pv_1d", "0")));
-            userFeatureMapDouble.put("share_pv_3d", Double.parseDouble(c2.getOrDefault("share_pv_3d", "0")));
-            userFeatureMapDouble.put("share_pv_7d", Double.parseDouble(c2.getOrDefault("share_pv_7d", "0")));
-            userFeatureMapDouble.put("return_uv_12h", Double.parseDouble(c2.getOrDefault("return_uv_12h", "0")));
-            userFeatureMapDouble.put("return_uv_1d", Double.parseDouble(c2.getOrDefault("return_uv_1d", "0")));
-            userFeatureMapDouble.put("return_uv_3d", Double.parseDouble(c2.getOrDefault("return_uv_3d", "0")));
-            userFeatureMapDouble.put("return_uv_7d", Double.parseDouble(c2.getOrDefault("return_uv_7d", "0")));
-        }
-
-        Map<String, String> c34567Map = new HashMap<>(15);
-        List<Tuple2> tmpList0 = Arrays.asList(
-                new Tuple2(c3, "c3_feature"),
-                new Tuple2(c4, "c4_feature"),
-                new Tuple2(c5, "c5_feature"),
-                new Tuple2(c6, "c6_feature"),
-                new Tuple2(c7, "c7_feature")
-        );
-        for (Tuple2 tuple2 : tmpList0) {
-            for (String key_time : Arrays.asList("tags_1d", "tags_3d", "tags_7d")) {
-                String tags = tuple2.first.getOrDefault(key_time, "");
-                if (!tags.isEmpty()) {
-                    c34567Map.put(tuple2.name + "_" + key_time, tags);
-                }
-            }
-        }
 
-        Map<String, Map<String, String[]>> c89Map = new HashMap<>(4);
-        List<Tuple2> tmpList1 = Arrays.asList(
-                new Tuple2(c8, "c8_feature"),
-                new Tuple2(c9, "c9_feature")
-        );
-        for (Tuple2 tuple2 : tmpList1) {
-            for (String key_action : Arrays.asList("share", "return")) {
-                String cfListStr = tuple2.first.getOrDefault(key_action, "");
-                if (!cfListStr.isEmpty()) {
-                    Map<String, String[]> cfMap = new HashMap<>();
-                    String[] entries = cfListStr.split(",");
-                    for (String entry : entries) {
-                        String[] rList = entry.split(":");
-                        if (rList.length >= 4) { // 确保分割后有四个元素
-                            String key = rList[0];
-                            String value1 = rList[1];
-                            String value2 = rList[2];
-                            String value3 = rList[3];
-                            String[] strs = {value1, value2, value3};
-                            cfMap.put(key, strs);
-                        }
-                    }
-                    c89Map.put(tuple2.name + "_" + key_action, cfMap);
-                }
-            }
-        }
+        Map<String, String> c1 = featureOriginUser.getOrDefault("mid_global_feature_20250212", new HashMap<>());
+        Map<String, String> c4 = featureOriginUser.getOrDefault("mid_u2u_friend_index_feature_20250212", new HashMap<>());
+        Map<String, String> c5 = featureOriginUser.getOrDefault("alg_mid_feature_return_tags", new HashMap<>());
+        Map<String, String> c6 = featureOriginUser.getOrDefault("alg_mid_feature_share_tags", new HashMap<>());
+        Map<String, String> c7 = featureOriginUser.getOrDefault("alg_mid_feature_sharecf", new HashMap<>());
+        Map<String, String> c8 = featureOriginUser.getOrDefault("alg_mid_feature_returncf", new HashMap<>());
 
+        ExtractFeature20250218.handleC1(c1, userFeatureMapDouble);
+        ExtractFeature20250218.handleC4(c4, userFeatureMapDouble);
+        Map<String, Map<String, String[]>> c78FeatureMap = ExtractFeature20250218.handleC7ToC8(c7, c8);
 
         List<RankItem> rankItems = CommonCollectionUtils.toList(rovRecallRank, RankItem::new);
         for (RankItem item : rankItems) {
-            Map<String, Double> featureMap = new HashMap<>();
-            String vid = item.getVideoId() + "";
-            Map<String, String> b1 = featureOriginVideo.getOrDefault(vid, new HashMap<>()).getOrDefault("alg_vid_feature_all_exp_v2", new HashMap<>());
-            Map<String, String> b2 = featureOriginVideo.getOrDefault(vid, new HashMap<>()).getOrDefault("alg_vid_feature_all_share", new HashMap<>());
-            Map<String, String> b3 = featureOriginVideo.getOrDefault(vid, new HashMap<>()).getOrDefault("alg_vid_feature_all_return", new HashMap<>());
-            Map<String, String> b6 = featureOriginVideo.getOrDefault(vid, new HashMap<>()).getOrDefault("alg_vid_feature_exp2share_v2", new HashMap<>());
-            Map<String, String> b7 = featureOriginVideo.getOrDefault(vid, new HashMap<>()).getOrDefault("alg_vid_feature_share2return", new HashMap<>());
-
-            Map<String, String> b8 = featureOriginVideo.getOrDefault(vid, new HashMap<>()).getOrDefault("alg_vid_feature_feed_noflow_exp_v2", new HashMap<>());
-            Map<String, String> b9 = featureOriginVideo.getOrDefault(vid, new HashMap<>()).getOrDefault("alg_vid_feature_feed_noflow_root_share_v2", new HashMap<>());
-            Map<String, String> b10 = featureOriginVideo.getOrDefault(vid, new HashMap<>()).getOrDefault("alg_vid_feature_feed_noflow_root_return_v2", new HashMap<>());
-            Map<String, String> b11 = featureOriginVideo.getOrDefault(vid, new HashMap<>()).getOrDefault("alg_vid_feature_feed_flow_exp_v2", new HashMap<>());
-            Map<String, String> b12 = featureOriginVideo.getOrDefault(vid, new HashMap<>()).getOrDefault("alg_vid_feature_feed_flow_root_share_v2", new HashMap<>());
-            Map<String, String> b13 = featureOriginVideo.getOrDefault(vid, new HashMap<>()).getOrDefault("alg_vid_feature_feed_flow_root_return_v2", new HashMap<>());
-            Map<String, String> b17 = featureOriginVideo.getOrDefault(vid, new HashMap<>()).getOrDefault("alg_vid_feature_feed_province_exp_v2", new HashMap<>());
-            Map<String, String> b18 = featureOriginVideo.getOrDefault(vid, new HashMap<>()).getOrDefault("alg_vid_feature_feed_province_root_share_v2", new HashMap<>());
-            Map<String, String> b19 = featureOriginVideo.getOrDefault(vid, new HashMap<>()).getOrDefault("alg_vid_feature_feed_province_root_return_v2", new HashMap<>());
-
-            List<Tuple4> originData = Arrays.asList(
-                    new Tuple4(b1, b2, b3, "b123"),
-                    new Tuple4(b1, b6, b7, "b167"),
-                    new Tuple4(b8, b9, b10, "b8910"),
-                    new Tuple4(b11, b12, b13, "b111213"),
-                    new Tuple4(b17, b18, b19, "b171819")
-            );
-
-            for (Tuple4 tuple4 : originData) {
-                for (String prefix2 : Arrays.asList("1h", "2h", "3h", "4h", "12h", "1d", "3d", "7d")) {
-                    double exp = tuple4.first.isEmpty() ? 0 : Double.parseDouble(tuple4.first.getOrDefault("exp_pv_" + prefix2, "0.0"));
-                    double share = tuple4.second.isEmpty() ? 0 : Double.parseDouble(tuple4.second.getOrDefault("share_pv_" + prefix2, "0.0"));
-                    double returns = tuple4.third.isEmpty() ? 0 : Double.parseDouble(tuple4.third.getOrDefault("return_uv_" + prefix2, "0.0"));
-
-                    double f1 = ExtractorUtils.calDiv(share, exp);
-                    double f2 = ExtractorUtils.calLog(share);
-                    double f3 = ExtractorUtils.calDiv(returns, exp);
-                    double f4 = ExtractorUtils.calLog(returns);
-                    double f5 = f3 * f4;
-                    double f6 = ExtractorUtils.calDiv(returns, share);
-
-                    String key1 = tuple4.name + "_" + prefix2 + "_" + "STR";
-                    String key2 = tuple4.name + "_" + prefix2 + "_" + "log(share)";
-                    String key3 = tuple4.name + "_" + prefix2 + "_" + "ROV";
-                    String key4 = tuple4.name + "_" + prefix2 + "_" + "log(return)";
-                    String key5 = tuple4.name + "_" + prefix2 + "_" + "ROV*log(return)";
-                    String key6 = tuple4.name + "_" + prefix2 + "_" + "ROS";
-
-                    featureMap.put(key1, f1);
-                    featureMap.put(key2, f2);
-                    featureMap.put(key3, f3);
-                    featureMap.put(key4, f4);
-                    featureMap.put(key5, f5);
-                    featureMap.put(key6, f6);
-                }
-            }
 
-            Map<String, String> videoInfo = videoBaseInfoMap.getOrDefault(vid, new HashMap<>()).getOrDefault("alg_vid_feature_basic_info", new HashMap<>());
-            featureMap.put("total_time", Double.parseDouble(videoInfo.getOrDefault("total_time", "0")));
-            featureMap.put("bit_rate", Double.parseDouble(videoInfo.getOrDefault("bit_rate", "0")));
-
-            String title = videoInfo.getOrDefault("title", "");
-            if (!title.isEmpty()) {
-                List<Future<Pair<String, Double[]>>> futures = new ArrayList<>();
-                for (String name : Arrays.asList("c3_feature", "c4_feature", "c5_feature", "c6_feature", "c7_feature")) {
-                    for (String key_time : Arrays.asList("tags_1d", "tags_3d", "tags_7d")) {
-                        String key = name + "_" + key_time;
-                        String tags = c34567Map.getOrDefault(key, "");
-                        if (!tags.isEmpty()) {
-                            Future<Pair<String, Double[]>> future = ThreadPoolFactory.defaultPool().submit(() -> {
-                                Double[] doubles = ExtractorUtils.funcC34567ForTagsNew(tags, title);
-                                return Pair.create(key, doubles);
-                            });
-                            futures.add(future);
-                        }
-                    }
-                }
-                try {
-                    for (Future<Pair<String, Double[]>> future : futures) {
-                        Pair<String, Double[]> pair = future.get(1000, TimeUnit.MILLISECONDS);
-                        featureMap.put(pair.getFirst() + "_matchnum", pair.getSecond()[0]);
-                        featureMap.put(pair.getFirst() + "_maxscore", pair.getSecond()[1]);
-                        featureMap.put(pair.getFirst() + "_avgscore", pair.getSecond()[2]);
-                    }
-                } catch (Exception e) {
-                    log.error("concurrent similarity error", e);
-                }
-            }
+            String vidStr = String.valueOf(item.getVideoId());
 
-            if (!vid.isEmpty()) {
-                for (String key_feature : Arrays.asList("c8_feature", "c9_feature")) {
-                    for (String key_action : Arrays.asList("share", "return")) {
-                        Map<String, String[]> cfMap = c89Map.getOrDefault(key_feature + "_" + key_action, new HashMap<>());
-                        if (cfMap.containsKey(vid)) {
-                            String[] scores = cfMap.get(vid);
-                            Double score1 = Double.parseDouble(scores[0]);
-                            Double score2 = Double.parseDouble(scores[1]);
-                            Double score3 = Double.parseDouble(scores[2]) <= 0 ? 0D : 1.0 / Double.parseDouble(scores[2]);
-                            featureMap.put(key_feature + "_" + key_action + "_score", score1);
-                            featureMap.put(key_feature + "_" + key_action + "_num", score2);
-                            featureMap.put(key_feature + "_" + key_action + "_rank", score3);
-                        }
-                    }
-                }
-            }
-            Map<String, String> d1 = featureOriginVideo.getOrDefault(vid, new HashMap<>()).getOrDefault("alg_recsys_feature_cf_i2i_new_v2", new HashMap<>());
-            if (!d1.isEmpty()) {
-                featureMap.put("d1_exp", Double.parseDouble(d1.getOrDefault("exp", "0")));
-                featureMap.put("d1_return_n", Double.parseDouble(d1.getOrDefault("return_n", "0")));
-                featureMap.put("d1_rovn", Double.parseDouble(d1.getOrDefault("rovn", "0")));
-            }
-            // ******************** new feature ********************
-            addVideoStatFeature(vid, featureOriginVideo, featureMap);
-            //addVideoCFFeature(vid, featureOriginVideo, featureMap);
-            addVideoSimFeature(headVideoInfo, videoInfo, featureMap);
+            Map<String, Double> featureMap = new HashMap<>();
+            Map<String, String> v1Feature = videoBaseInfoMap.getOrDefault(vidStr, new HashMap<>()).getOrDefault("alg_vid_feature_basic_info", new HashMap<>());
+            Map<String, Map<String, String>> videoFeatureMap = featureOriginVideo.getOrDefault(vidStr, new HashMap<>());
+            Map<String, String> b1 = videoFeatureMap.getOrDefault("alg_vid_global_feature_20250212", new HashMap<>());
+            Map<String, String> b2 = videoFeatureMap.getOrDefault("alg_vid_recommend_exp_feature_20250212", new HashMap<>());
+            Map<String, String> b3 = videoFeatureMap.getOrDefault("alg_vid_recommend_flowpool_exp_feature_20250212", new HashMap<>());
+            Map<String, String> b4 = videoFeatureMap.getOrDefault("alg_vid_apptype_recommend_exp_feature_20250212", new HashMap<>());
+            Map<String, String> b5 = videoFeatureMap.getOrDefault("alg_vid_province_recommend_exp_feature_20250212", new HashMap<>());
+            Map<String, String> b6 = videoFeatureMap.getOrDefault("alg_vid_brand_recommend_exp_feature_20250212", new HashMap<>());
+            Map<String, String> b7 = videoFeatureMap.getOrDefault("alg_vid_hotsencetype_recommend_exp_feature_20250212", new HashMap<>());
+            Map<String, String> b8 = videoFeatureMap.getOrDefault("alg_merge_cate1_recommend_exp_feature_20250212", new HashMap<>());
+            Map<String, String> b9 = videoFeatureMap.getOrDefault("alg_merge_cate2_recommend_exp_feature_20250212", new HashMap<>());
+            Map<String, String> b10 = videoFeatureMap.getOrDefault("alg_channel_recommend_exp_feature_20250212", new HashMap<>());
+            Map<String, String> b11 = videoFeatureMap.getOrDefault("alg_festive_recommend_exp_feature_20250212", new HashMap<>());
+            Map<String, String> b12 = videoFeatureMap.getOrDefault("alg_vid_long_period_recommend_exp_feature_20250212", new HashMap<>());
+            Map<String, String> b13 = videoFeatureMap.getOrDefault("alg_video_unionid_recommend_exp_feature_20250212", new HashMap<>());
+
+            Map<String, String> c2 = videoFeatureMap.getOrDefault("mid_merge_cate1_feature_20250212", new HashMap<>());
+            Map<String, String> c3 = videoFeatureMap.getOrDefault("mid_merge_cate2_feature_20250212", new HashMap<>());
+
+            Map<String, String> d1 = videoFeatureMap.getOrDefault("scene_type_vid_cf_feature_20250212", new HashMap<>());
+            Map<String, String> d2 = videoFeatureMap.getOrDefault("vid_click_cf_feature_20250212", new HashMap<>());
+            Map<String, String> d3 = videoFeatureMap.getOrDefault("alg_recsys_feature_cf_i2i_v2", new HashMap<>());
+
+            Map<String, Map<String, String>> b2ToB11AndB13Map = new HashMap<>();
+            b2ToB11AndB13Map.put("b2", b2);
+            b2ToB11AndB13Map.put("b3", b3);
+            b2ToB11AndB13Map.put("b4", b4);
+            b2ToB11AndB13Map.put("b5", b5);
+            b2ToB11AndB13Map.put("b6", b6);
+            b2ToB11AndB13Map.put("b7", b7);
+            b2ToB11AndB13Map.put("b8", b8);
+            b2ToB11AndB13Map.put("b9", b9);
+            b2ToB11AndB13Map.put("b10", b10);
+            b2ToB11AndB13Map.put("b11", b11);
+            b2ToB11AndB13Map.put("b13", b13);
+
+            ExtractFeature20250218.handleB1(b1, featureMap);
+            ExtractFeature20250218.handleB12(b12, featureMap);
+            ExtractFeature20250218.handleB2ToB11AndB13(b2ToB11AndB13Map, featureMap);
+            ExtractFeature20250218.handleC2ToC3(c2, c3, featureMap);
+            ExtractFeature20250218.useC7ToC8(c78FeatureMap, vidStr, featureMap);
+            ExtractFeature20250218.handleC5ToC6(c5, c6, v1Feature, featureMap);
+            ExtractFeature20250218.handleD1(d1, featureMap);
+            ExtractFeature20250218.handleD2(d2, featureMap);
+            ExtractFeature20250218.handleD3(d3, featureMap);
+            ExtractFeature20250218.handleVideoBasicFeature(v1Feature, ts, featureMap);
+            ExtractFeature20250218.handleVideoSimilarity(v1Feature, headVideoInfo, featureMap);
 
             item.featureMapDouble = featureMap;
         }
 
         // 3 连续值特征分桶
-        Map<String, String> userFeatureMap = FeatureBucketUtils.bucketFeature("20241209_rov_bucket.txt", userFeatureMapDouble);
+        Map<String, String> userFeatureMap = FeatureBucketUtils.bucketFeatureV2("20250218_bucket_322.txt", userFeatureMapDouble);
         for (RankItem item : rankItems) {
             Map<String, Double> featureMapDouble = item.featureMapDouble;
-            item.featureMap = FeatureBucketUtils.bucketFeature("20241209_rov_bucket.txt", featureMapDouble);
+            item.featureMap = FeatureBucketUtils.bucketFeatureV2("20250218_bucket_322.txt", featureMapDouble);
         }
         // 4 排序模型计算
-        double xgbRovNegRate = mergeWeight.getOrDefault("xgbRovNegRate", 0.02);
+        double xgbRovNegRate = mergeWeight.getOrDefault("xgbRovNegRate", 0.05);
+        double calcVorMode = mergeWeight.getOrDefault("calc_vor_mode", 1d);
+
         Map<String, String> sceneFeatureMap = new HashMap<>(0);
-        List<RankItem> items = ScorerUtils.getScorerPipeline("feeds_score_config_xgb_rov_20250109.conf").scoring(sceneFeatureMap, userFeatureMap, rankItems);
+        List<RankItem> items = ScorerUtils.getScorerPipeline("feeds_score_config_xgb_rov_20250228.conf").scoring(sceneFeatureMap, userFeatureMap, rankItems);
         // 5 排序公式特征
-        Map<String, Map<String, String>> vid2MapFeature = this.getVideoRedisFeature(vids, "redis:vid_hasreturn_vor:");
+        Map<String, Map<String, String>> vid2MapFeature = this.getVideoRedisFeature(vids, "redis:vid_hasreturn_vor_4share:");
         List<Video> result = new ArrayList<>();
         for (RankItem item : items) {
             double score;
@@ -308,11 +199,20 @@ public class RankStrategy4RegionMergeModelV565 extends RankStrategy4RegionMergeM
             double fmRov = restoreScore(fmRovOrigin, xgbRovNegRate);
             item.getScoresMap().put("fmRov", fmRov);
             item.getScoresMap().put("xgbRovNegRate", xgbRovNegRate);
-            double hasReturnRovScore = Double.parseDouble(vid2MapFeature.getOrDefault(item.getVideoId() + "", new HashMap<>()).getOrDefault("rov", "0"));
-            item.getScoresMap().put("hasReturnRovScore", hasReturnRovScore);
-            double vor = Double.parseDouble(vid2MapFeature.getOrDefault(item.getVideoId() + "", new HashMap<>()).getOrDefault("vor", "0"));
-            item.getScoresMap().put("vor", vor);
-            score = fmRov * (0.1 + hasReturnRovScore) * (0.1 + vor);
+
+
+            Map<String, String> vidFeatureMap = vid2MapFeature.getOrDefault(String.valueOf(item.getVideoId()), new HashMap<>());
+            double ros24h = Double.parseDouble(vidFeatureMap.getOrDefault("ros_24h", "0"));
+            double vor24h = Double.parseDouble(vidFeatureMap.getOrDefault("vor_24h", "0"));
+            if (calcVorMode == 1d) {
+                vor24h = ExtractorUtils.calLog(vor24h);
+            } else if (vor24h == 2d) {
+                double vorCoefficient = mergeWeight.getOrDefault("vor_coefficient", 1d);
+                vor24h = vorCoefficient * vor24h;
+            }
+            score = fmRov * (0.1 + ros24h) * (0.1 + vor24h);
+
+
             Video video = item.getVideo();
             video.setScore(score);
             video.setSortScore(score);
@@ -333,121 +233,10 @@ public class RankStrategy4RegionMergeModelV565 extends RankStrategy4RegionMergeM
             result.add(video);
         }
         result.sort(Comparator.comparingDouble(o -> -o.getSortScore()));
-        return result;
-    }
-
-    private Map<String, String> getVideoOneTypeInfo(String vid, String name,
-                                                    Map<String, Map<String, Map<String, String>>> videoAllInfoMap) {
-        if (null == videoAllInfoMap) {
-            return new HashMap<>();
-        }
-        return videoAllInfoMap.getOrDefault(vid, new HashMap<>()).getOrDefault(name, new HashMap<>());
-    }
-
-    private double getVideoOneInfo(String name, Map<String, String> infoMap) {
-        if (null == infoMap) {
-            return 0.0;
-        }
-        return infoMap.isEmpty() ? 0 : Double.parseDouble(infoMap.getOrDefault(name, "0.0"));
-    }
 
-    private void addVideoStatFeature(String vid, Map<String, Map<String, Map<String, String>>> videoAllInfoMap,
-                                     Map<String, Double> featureMap) {
-        List<Tuple3> vidStatInfo = Arrays.asList(
-                new Tuple3("b20", shortPeriod, getVideoOneTypeInfo(vid, "alg_cate2_feature", videoAllInfoMap)),
-                new Tuple3("b21", shortPeriod, getVideoOneTypeInfo(vid, "alg_cate1_feature", videoAllInfoMap)),
-                new Tuple3("b22", shortPeriod, getVideoOneTypeInfo(vid, "alg_vid_source_feature", videoAllInfoMap)),
-                new Tuple3("b28", shortPeriod, getVideoOneTypeInfo(vid, "alg_sence_type_feature", videoAllInfoMap)),
-                new Tuple3("b29", shortPeriod, getVideoOneTypeInfo(vid, "alg_videoid_feature", videoAllInfoMap)),
-                new Tuple3("b23", middlePeriod, getVideoOneTypeInfo(vid, "alg_cate2_feature_day", videoAllInfoMap)),
-                new Tuple3("b24", middlePeriod, getVideoOneTypeInfo(vid, "alg_cate1_feature_day", videoAllInfoMap)),
-                new Tuple3("b25", middlePeriod, getVideoOneTypeInfo(vid, "alg_video_source_feature_day", videoAllInfoMap)),
-                new Tuple3("b26", longPeriod, getVideoOneTypeInfo(vid, "alg_video_unionid_feature_day", videoAllInfoMap)),
-                new Tuple3("b27", longPeriod, getVideoOneTypeInfo(vid, "alg_vid_feature_day", videoAllInfoMap))
-        );
-        for (Tuple3 tuple3 : vidStatInfo) {
-            String infoType = tuple3.first;
-            List<String> infoPeriod = tuple3.second;
-            Map<String, String> infoMap = tuple3.third;
-            for (String period : infoPeriod) {
-                double share = getVideoOneInfo("share_" + period, infoMap);
-                double return_ = getVideoOneInfo("return_" + period, infoMap);
-                double view_hasreturn = getVideoOneInfo("view_hasreturn_" + period, infoMap);
-                double share_hasreturn = getVideoOneInfo("share_hasreturn_" + period, infoMap);
-                double ros = getVideoOneInfo("ros_" + period, infoMap);
-                double rov = getVideoOneInfo("rov_" + period, infoMap);
-                double r_cnt = getVideoOneInfo("r_cnt_" + period, infoMap);
-                double r_rate = getVideoOneInfo("r_rate_" + period, infoMap);
-                double r_cnt4s = getVideoOneInfo("r_cnt4s_" + period, infoMap);
-                double str = getVideoOneInfo("str_" + period, infoMap);
-
-                featureMap.put(infoType + "_" + period + "_" + "share", ExtractorUtils.calLog(share));
-                featureMap.put(infoType + "_" + period + "_" + "return", ExtractorUtils.calLog(return_));
-                featureMap.put(infoType + "_" + period + "_" + "view_hasreturn", ExtractorUtils.calLog(view_hasreturn));
-                featureMap.put(infoType + "_" + period + "_" + "share_hasreturn", ExtractorUtils.calLog(share_hasreturn));
-                featureMap.put(infoType + "_" + period + "_" + "ros", ros);
-                featureMap.put(infoType + "_" + period + "_" + "rov", rov);
-                featureMap.put(infoType + "_" + period + "_" + "r_cnt", r_cnt);
-                featureMap.put(infoType + "_" + period + "_" + "r_rate", r_rate);
-                featureMap.put(infoType + "_" + period + "_" + "r_cnt4s", r_cnt4s);
-                featureMap.put(infoType + "_" + period + "_" + "str", str);
-            }
-        }
-    }
+        log.info("565 run time: {}", (System.currentTimeMillis() - startTime));
 
-    private void addVideoCFFeature(String vid, Map<String, Map<String, Map<String, String>>> videoAllInfoMap,
-                                   Map<String, Double> featureMap) {
-        List<Tuple3> vidCFInfo = Arrays.asList(
-                new Tuple3("d2", cfRosList, getVideoOneTypeInfo(vid, "alg_recsys_feature_weak_cf_i2i_scene_ros", videoAllInfoMap)),
-                new Tuple3("d3", cfRosList, getVideoOneTypeInfo(vid, "alg_recsys_feature_cf_i2i_scene_ros", videoAllInfoMap)),
-                new Tuple3("d4", cfRovList, getVideoOneTypeInfo(vid, "alg_recsys_feature_weak_cf_i2i_scene_rov", videoAllInfoMap)),
-                new Tuple3("d5", cfRovList, getVideoOneTypeInfo(vid, "alg_recsys_feature_cf_i2i_scene_rov", videoAllInfoMap))
-        );
-        for (Tuple3 tuple3 : vidCFInfo) {
-            String infoType = tuple3.first;
-            List<String> valTypeList = tuple3.second;
-            Map<String, String> infoMap = tuple3.third;
-            if (!infoMap.isEmpty()) {
-                for (String valType : valTypeList) {
-                    String expKey = "exp";
-                    if (valType.equals("rosn")) {
-                        expKey = "share";
-                    }
-                    double exp = getVideoOneInfo(expKey, infoMap);
-                    double return_n = getVideoOneInfo("return_n", infoMap);
-                    double value = getVideoOneInfo(valType, infoMap);
-
-                    featureMap.put(infoType + "_exp", ExtractorUtils.calLog(exp));
-                    featureMap.put(infoType + "_return_n", ExtractorUtils.calLog(return_n));
-                    featureMap.put(infoType + "_" + valType, value);
-                }
-            }
-        }
+        return result;
     }
 
-    private void addVideoSimFeature(Map<String, String> headInfo, Map<String, String> rankInfo, Map<String, Double> featureMap) {
-        if (!headInfo.isEmpty() && !rankInfo.isEmpty()) {
-            List<Future<Pair<String, Double>>> futures = new ArrayList<>();
-            for (String attr : videoSimAttrs) {
-                String headAttr = headInfo.getOrDefault(attr, "");
-                String rankAttr = rankInfo.getOrDefault(attr, "");
-                if (!"".equals(headAttr) && !"unknown".equals(headAttr) && !"".equals(rankAttr) && !"unknown".equals(rankAttr)) {
-                    String key = "video_sim_" + attr;
-                    Future<Pair<String, Double>> future = ThreadPoolFactory.defaultPool().submit(() -> {
-                        double simScore = SimilarityUtils.word2VecSimilarity(headAttr, rankAttr);
-                        return Pair.create(key, simScore);
-                    });
-                    futures.add(future);
-                }
-            }
-            try {
-                for (Future<Pair<String, Double>> future : futures) {
-                    Pair<String, Double> pair = future.get(1000, TimeUnit.MILLISECONDS);
-                    featureMap.put(pair.getFirst(), pair.getSecond());
-                }
-            } catch (Exception e) {
-                log.error("video attr similarity error", e);
-            }
-        }
-    }
 }

+ 4 - 1
recommend-server-service/src/main/java/com/tzld/piaoquan/recommend/server/service/score/ScorerUtils.java

@@ -5,6 +5,7 @@ import com.typesafe.config.Config;
 import com.tzld.piaoquan.recommend.server.service.score4recall.AbstractScorer4Recall;
 import com.tzld.piaoquan.recommend.server.service.score4recall.ScorerPipeline4Recall;
 import com.tzld.piaoquan.recommend.server.util.FeatureBucketUtils;
+import com.tzld.piaoquan.recommend.server.util.FestiveUtil;
 import lombok.extern.slf4j.Slf4j;
 import org.apache.commons.lang.exception.ExceptionUtils;
 import org.slf4j.Logger;
@@ -39,13 +40,15 @@ public final class ScorerUtils {
         ScorerUtils.init("feeds_score_config_xgb_20250109.conf");
         ScorerUtils.init("feeds_score_config_xgb_rov_20241209.conf");
         ScorerUtils.init("feeds_score_config_xgb_rov_20250109.conf");
+        ScorerUtils.init("feeds_score_config_xgb_rov_20250228.conf");
         ScorerUtils.init4Recall("feeds_recall_config_region_v1.conf");
         ScorerUtils.init4Recall("feeds_recall_config_region_ros.conf");
         ScorerUtils.init4Recall("feeds_score_config_bless.conf");
         ScorerUtils.init4Recall("feeds_recall_config_tomson.conf");
         ScorerUtils.init4Recall("feeds_recall_config_region_v7_longterm.conf");
-        List<String> bucketFileList = Arrays.asList("20241209_rov_bucket.txt", "20241209_nor_bucket.txt");
+        List<String> bucketFileList = Arrays.asList("20241209_rov_bucket.txt", "20241209_nor_bucket.txt", "20250218_bucket_322.txt");
         FeatureBucketUtils.init(bucketFileList);
+        FestiveUtil.init();
     }
 
     private ScorerUtils() {

+ 303 - 0
recommend-server-service/src/main/java/com/tzld/piaoquan/recommend/server/util/ExtractFeature20250218.java

@@ -0,0 +1,303 @@
+package com.tzld.piaoquan.recommend.server.util;
+
+import com.tzld.piaoquan.recommend.server.service.rank.extractor.ExtractorUtils;
+import org.apache.commons.lang3.StringUtils;
+
+import java.time.Instant;
+import java.time.LocalDateTime;
+import java.time.ZoneId;
+import java.time.format.DateTimeFormatter;
+import java.util.Arrays;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+public class ExtractFeature20250218 {
+
+    private ExtractFeature20250218() {
+    }
+
+    public static void handleB1(Map<String, String> b1Feature, Map<String, Double> featureMap) {
+        List<String> times = Arrays.asList("1h", "3h", "6h", "12h", "24h", "72h", "168h");
+        List<String> indexList = Arrays.asList("is_share", "share_cnt", "is_return_1", "return_1_uv", "str_one", "ros_one", "str", "ros", "str_plus", "ros_minus", "rovn");
+        for (String time : times) {
+            for (String index : indexList) {
+                double value = Double.parseDouble(b1Feature.getOrDefault(index + "_" + time, "0"));
+                featureMap.put("b1_" + index + "_" + time, value);
+            }
+
+            double rovn = Double.parseDouble(b1Feature.getOrDefault("rovn_" + time, "0"));
+            double returnNUv = Double.parseDouble(b1Feature.getOrDefault("return_1_uv_" + time, "0"));
+
+            featureMap.put("b1_rovn*log(r)_" + time, rovn * ExtractorUtils.calLog(returnNUv));
+        }
+
+    }
+
+    public static void handleB2ToB11AndB13(Map<String, Map<String, String>> videoFeature, Map<String, Double> featureMap) {
+        List<String> times = Arrays.asList("1h", "3h", "6h", "12h", "24h", "72h", "168h");
+        List<String> indexList = Arrays.asList("is_share", "share_cnt", "is_return_1", "return_n_uv", "str_one", "ros_one", "str", "ros", "str_plus", "ros_minus", "rovn");
+        for (Map.Entry<String, Map<String, String>> entry : videoFeature.entrySet()) {
+            String key = entry.getKey();
+            Map<String, String> feature = entry.getValue();
+            for (String time : times) {
+                for (String index : indexList) {
+                    double value = Double.parseDouble(feature.getOrDefault(index + "_" + time, "0"));
+                    featureMap.put(key + "_" + index + "_" + time, value);
+                }
+
+                double rovn = Double.parseDouble(feature.getOrDefault("rovn_" + time, "0"));
+                double returnNUv = Double.parseDouble(feature.getOrDefault("return_n_uv_" + time, "0"));
+
+                featureMap.put(key + "_rovn*log(r)_" + time, rovn * ExtractorUtils.calLog(returnNUv));
+            }
+
+        }
+    }
+
+    public static void handleB12(Map<String, String> b12Feature, Map<String, Double> featureMap) {
+        List<String> times = Arrays.asList("7d", "14d", "30d", "60d");
+        List<String> indexList = Arrays.asList("is_share", "share_cnt", "is_return_1", "return_n_uv", "str_one", "ros_one", "str", "ros", "str_plus", "ros_minus", "rovn");
+        for (String time : times) {
+            for (String index : indexList) {
+                double value = Double.parseDouble(b12Feature.getOrDefault(index + "_" + time, "0"));
+                featureMap.put("b12_" + index + "_" + time, value);
+            }
+            double rovn = Double.parseDouble(b12Feature.getOrDefault("rovn_" + time, "0"));
+            double returnNUv = Double.parseDouble(b12Feature.getOrDefault("return_n_uv_" + time, "0"));
+            featureMap.put("b12_rovn*log(r)_" + time, rovn * ExtractorUtils.calLog(returnNUv));
+        }
+    }
+
+    public static void handleVideoBasicFeature(Map<String, String> videoFeature, long ts, Map<String, Double> featureMap) {
+        Double totalTime = Double.parseDouble(videoFeature.getOrDefault("total_time", "0"));
+        Double width = Double.parseDouble(videoFeature.getOrDefault("width", "0d"));
+        Double height = Double.parseDouble(videoFeature.getOrDefault("height", "0d"));
+        Double size = Double.parseDouble(videoFeature.getOrDefault("size", "0d"));
+        Double bit_rate = Double.parseDouble(videoFeature.getOrDefault("bit_rate", "0d"));
+        String festiveLabel1 = videoFeature.getOrDefault("festive_label1", "");
+        String festiveLabel2 = videoFeature.getOrDefault("festive_label2", "");
+
+
+        featureMap.put("total_time", totalTime);
+        featureMap.put("width", width);
+        featureMap.put("height", height);
+        featureMap.put("size", size);
+        featureMap.put("bit_rate", bit_rate);
+        featureMap.put("width/height", ExtractorUtils.divisionDouble(width, height));
+        featureMap.put("is_festive", 0d);
+        featureMap.put("is_greeting", 0d);
+        if (StringUtils.equals(festiveLabel1, "节假日")) {
+            featureMap.put("is_festive", 1d);
+        } else if (StringUtils.equals(festiveLabel1, "问候语")) {
+            featureMap.put("is_greeting", 1d);
+        }
+
+        featureMap.put("hour", Double.parseDouble(String.valueOf(ExtractorUtils.getHourByTimestamp(ts))));
+        featureMap.put("day_of_week", Double.parseDouble(String.valueOf(ExtractorUtils.getDayOfWeekByTimestamp(ts))));
+
+        long createTs = Long.parseLong(videoFeature.getOrDefault("gmt_create_timestamp", "0")) / 1000;
+        featureMap.put("create_ts_diff", Double.parseDouble(String.valueOf(ExtractorUtils.getDaysBetween(createTs, ts))));
+
+        String date = LocalDateTime.ofInstant(Instant.ofEpochSecond(ts), ZoneId.systemDefault()).format(DateTimeFormatter.ofPattern("yyyy-MM-dd"));
+        String festiveByDate = FestiveUtil.getFestiveByDate(date);
+        featureMap.put("today_is_fes", 0d);
+        featureMap.put("video_fes_eq", 0d);
+        if (StringUtils.isNotBlank(festiveByDate)) {
+            featureMap.put("today_is_fes", 1d);
+            if (StringUtils.equals(festiveByDate, festiveLabel2)) {
+                featureMap.put("video_today_fes_eq", 1d);
+            }
+        }
+
+    }
+
+    public static void handleC1(Map<String, String> c1Feature, Map<String, Double> featureMap) {
+        List<String> times = Arrays.asList("12h", "24h", "72h", "168h");
+        List<String> indexList = Arrays.asList("is_share", "share_cnt", "is_return_1", "return_1_uv", "click", "str_one", "ros_one", "str", "ros", "str_plus", "ros_minus", "rovn");
+        for (String time : times) {
+            for (String index : indexList) {
+                double value = Double.parseDouble(c1Feature.getOrDefault(index + "_" + time, "0"));
+                featureMap.put("c1_" + index + "_" + time, value);
+            }
+            double rovn = Double.parseDouble(c1Feature.getOrDefault("rovn_" + time, "0"));
+            double returnNUv = Double.parseDouble(c1Feature.getOrDefault("return_1_uv_" + time, "0"));
+            featureMap.put("c1_rovn*log(r)_" + time, rovn * ExtractorUtils.calLog(returnNUv));
+        }
+    }
+
+    public static void handleC2ToC3(Map<String, String> c2Feature, Map<String, String> c3Feature, Map<String, Double> featureMap) {
+        Map<String, Map<String, String>> featureMaps = new HashMap<>();
+        featureMaps.put("c2", c2Feature);
+        featureMaps.put("c3", c3Feature);
+
+        List<String> times = Arrays.asList("12h", "24h", "72h", "168h");
+        List<String> indexList = Arrays.asList("is_share", "share_cnt", "is_return_1", "return_n_uv", "click");
+
+        for (Map.Entry<String, Map<String, String>> entry : featureMaps.entrySet()) {
+            String key = entry.getKey();
+            Map<String, String> feature = entry.getValue();
+            for (String time : times) {
+                for (String index : indexList) {
+                    double value = Double.parseDouble(feature.getOrDefault(index + "_" + time, "0"));
+                    featureMap.put(key + "_" + index + "_" + time, value);
+                }
+            }
+        }
+    }
+
+    public static void handleC4(Map<String, String> c4Feature, Map<String, Double> featureMap) {
+        List<String> times = Arrays.asList("24h", "72h", "168h");
+        List<String> indexList = Arrays.asList("str_one", "ros_one", "str", "ros", "str_plus", "ros_minus", "rovn");
+
+        for (String time : times) {
+            for (String index : indexList) {
+                double value = Double.parseDouble(c4Feature.getOrDefault("avg_" + index + "_" + time, "0"));
+                featureMap.put("c4_avg_" + index + "_" + time, value);
+
+                double max = Double.parseDouble(c4Feature.getOrDefault("max_" + index + "_" + time, "0"));
+                double min = Double.parseDouble(c4Feature.getOrDefault("min_" + index + "_" + time, "0"));
+
+                featureMap.put("c4_diff_" + index + "_" + time, max - min);
+            }
+        }
+
+    }
+
+    public static void handleC5ToC6(Map<String, String> c5Feature, Map<String, String> c6Feature, Map<String, String> videoMap, Map<String, Double> featureMap) {
+        Map<String, Map<String, String>> featureMaps = new HashMap<>();
+        featureMaps.put("c5", c5Feature);
+        featureMaps.put("c6", c6Feature);
+        List<String> times = Arrays.asList("tags_1d", "tags_3d", "tags_7d");
+
+        String title = videoMap.getOrDefault("title", "");
+
+        for (Map.Entry<String, Map<String, String>> entry : featureMaps.entrySet()) {
+            String key = entry.getKey();
+            Map<String, String> feature = entry.getValue();
+            for (String time : times) {
+                String tags = feature.getOrDefault(time, "");
+                Double[] scores = ExtractorUtils.funcC34567ForTagsNew(tags, title);
+                featureMap.put(key + "_matchnum" + "_" + time, scores[0]);
+                featureMap.put(key + "_maxscore" + "_" + time, scores[1]);
+                featureMap.put(key + "_avgscore" + "_" + time, scores[2]);
+            }
+        }
+
+    }
+
+    public static Map<String, Map<String, String[]>> handleC7ToC8(Map<String, String> c7Feature, Map<String, String> c8Feature) {
+        Map<String, Map<String, String[]>> resultMap = new HashMap<>();
+
+        Map<String, Map<String, String>> featureMaps = new HashMap<>();
+        featureMaps.put("c7", c7Feature);
+        featureMaps.put("c8", c8Feature);
+        List<String> indexList = Arrays.asList("share", "return");
+        for (Map.Entry<String, Map<String, String>> entry : featureMaps.entrySet()) {
+            String key = entry.getKey();
+            Map<String, String> feature = entry.getValue();
+            for (String index : indexList) {
+                if (feature.containsKey(index)) {
+                    Map<String, String[]> cfMap = new HashMap<>();
+                    String[] entries = feature.get(index).split(",");
+                    for (String e : entries) {
+                        String[] rList = e.split(":");
+                        if (rList.length >= 4) {
+                            String vid = rList[0];
+                            String value1 = rList[1];
+                            String value2 = rList[2];
+                            String value3 = rList[3];
+                            String[] strs = {value1, value2, value3};
+                            cfMap.put(vid, strs);
+                        }
+                    }
+                    resultMap.put(key, cfMap);
+                }
+            }
+        }
+
+        return resultMap;
+    }
+
+    public static void useC7ToC8(Map<String, Map<String, String[]>> map, String vid, Map<String, Double> featureMap) {
+        if (StringUtils.isBlank(vid)) {
+            return;
+        }
+        for (String key : Arrays.asList("c6", "c7")) {
+            for (String action : Arrays.asList("share", "return")) {
+                String featureKey = key + "_" + action;
+                if (map.containsKey(featureKey)) {
+                    Map<String, String[]> cfMap = map.get(featureKey);
+                    String[] scores = cfMap.get(vid);
+                    featureMap.put(featureKey + "_score", Double.parseDouble(scores[0]));
+                    featureMap.put(featureKey + "_num", Double.parseDouble(scores[1]));
+                    featureMap.put(featureKey + "_rank", ExtractorUtils.reciprocal(Double.parseDouble(scores[2])));
+                }
+            }
+        }
+    }
+
+    public static void handleD3(Map<String, String> d3Feature, Map<String, Double> featureMap) {
+        for (String index : Arrays.asList("exp", "return_n", "rovn")) {
+            double value = Double.parseDouble(d3Feature.getOrDefault(index, "0"));
+            featureMap.put("d3_" + index, value);
+        }
+    }
+
+    public static void handleD1(Map<String, String> d1Feature, Map<String, Double> featureMap) {
+        double rosCfScores = Double.parseDouble(d1Feature.getOrDefault("ros_cf_score", "0"));
+        featureMap.put("d1_ros_cf_score", rosCfScores);
+        double rovCfScores = Double.parseDouble(d1Feature.getOrDefault("rov_cf_score", "0"));
+        featureMap.put("d1_rov_cf_score", rovCfScores);
+
+        double rosCfRank = Double.parseDouble(d1Feature.getOrDefault("ros_cf_rank", "0"));
+        featureMap.put("d1_ros_cf_rank", ExtractorUtils.reciprocal(rosCfRank));
+        double rovCfRank = Double.parseDouble(d1Feature.getOrDefault("rov_cf_rank", "0"));
+        featureMap.put("d1_rov_cf_rank", ExtractorUtils.reciprocal(rovCfRank));
+    }
+
+    public static void handleD2(Map<String, String> d5Feature, Map<String, Double> featureMap) {
+        double score = Double.parseDouble(d5Feature.getOrDefault("score", "0"));
+        featureMap.put("d2_score", score);
+
+        double rank = Double.parseDouble(d5Feature.getOrDefault("rank", "0"));
+        featureMap.put("d2_rank", ExtractorUtils.reciprocal(rank));
+    }
+
+    public static void handleVideoSimilarity(Map<String, String> videoFeature, Map<String, String> headVideoFeature, Map<String, Double> featureMap) {
+        String headVideoTitle = headVideoFeature.getOrDefault("title", "");
+        String headVideoMergeCate2 = headVideoFeature.getOrDefault("merge_second_level_cate", "");
+        String headVideoMergeCate1 = headVideoFeature.getOrDefault("merge_first_level_cate", "");
+        String headVideoFestiveLabel2 = headVideoFeature.getOrDefault("festive_label2", "");
+
+
+        String videoTitle = videoFeature.getOrDefault("title", "");
+        String videoMergeCate2 = videoFeature.getOrDefault("merge_second_level_cate", "");
+        String videoMergeCate1 = videoFeature.getOrDefault("merge_first_level_cate", "");
+        String videoFestiveLabel2 = videoFeature.getOrDefault("festive_label2", "");
+
+        double titleSimilarity = ExtractFeature20250218.calcTxtSimilarity(headVideoTitle, videoTitle);
+        double headTitleAndMerge1Similarity = ExtractFeature20250218.calcTxtSimilarity(headVideoTitle, videoMergeCate1);
+        double headTitleAndMerge2Similarity = ExtractFeature20250218.calcTxtSimilarity(headVideoTitle, videoMergeCate2);
+        double headTitleAndFestiveSimilarity = ExtractFeature20250218.calcTxtSimilarity(headVideoTitle, videoFestiveLabel2);
+        double merge1Similarity = ExtractFeature20250218.calcTxtSimilarity(headVideoMergeCate1, videoMergeCate1);
+        double merge2Similarity = ExtractFeature20250218.calcTxtSimilarity(headVideoMergeCate2, videoMergeCate2);
+        double festiveSimilarity = ExtractFeature20250218.calcTxtSimilarity(headVideoFestiveLabel2, videoFestiveLabel2);
+
+        featureMap.put("title_sim", titleSimilarity);
+        featureMap.put("head_title_merge1_sim", headTitleAndMerge1Similarity);
+        featureMap.put("head_title_merge2_sim", headTitleAndMerge2Similarity);
+        featureMap.put("head_title_festive_sim", headTitleAndFestiveSimilarity);
+        featureMap.put("merge1_sim", merge1Similarity);
+        featureMap.put("merge2_sim", merge2Similarity);
+        featureMap.put("festive_sim", festiveSimilarity);
+
+    }
+
+    private static double calcTxtSimilarity(String txt1, String txt2) {
+        if (StringUtils.isBlank(txt1) || StringUtils.isBlank(txt2)) {
+            return 0d;
+        }
+        return SimilarityUtils.word2VecSimilarity(txt1, txt2);
+    }
+}

+ 28 - 0
recommend-server-service/src/main/java/com/tzld/piaoquan/recommend/server/util/FeatureBucketUtils.java

@@ -73,6 +73,34 @@ public class FeatureBucketUtils {
         return featureMap;
     }
 
+    public static Map<String, String> bucketFeatureV2(String bucketFile, Map<String, Double> srcFeature) {
+        if (MapUtils.isEmpty(srcFeature)) {
+            return new HashMap<>();
+        }
+        Map<String, String> featureMap = new HashMap<>(srcFeature.size());
+        Pair<Map<String, Double>, Map<String, double[]>> pair = featureBucketMap.get(bucketFile);
+        if (null != pair && MapUtils.isNotEmpty(pair.getLeft()) && MapUtils.isNotEmpty(pair.getRight())) {
+            Map<String, Double> bucketsLen = pair.getLeft();
+            Map<String, double[]> bucketsMap = pair.getRight();
+            for (Map.Entry<String, Double> entry : srcFeature.entrySet()) {
+                String name = entry.getKey();
+                Double score = entry.getValue();
+                // 注意:0值、不在分桶文件中的特征,会被过滤掉。
+                if (score > 1E-8 && bucketsLen.containsKey(name) && bucketsMap.containsKey(name)) {
+                    Double bucketNum = bucketsLen.get(name);
+                    double[] buckets = bucketsMap.get(name);
+                    Double scoreNew = 1.0 / bucketNum * (ExtractorUtils.findInsertPosition(buckets, score) + 1.0);
+                    featureMap.put(name, String.valueOf(scoreNew));
+                } else if (score > 1E-8) {
+                    featureMap.put(name, String.valueOf(score));
+                }
+            }
+        } else {
+            log.error("failed to get {} bucket feature", bucketFile);
+        }
+        return featureMap;
+    }
+
     private static Pair<Map<String, Double>, Map<String, double[]>> loadBucket(String bucketFile) {
         Map<String, Double> bucketsLen = new HashMap<>();
         Map<String, double[]> bucketsMap = new HashMap<>();

+ 46 - 0
recommend-server-service/src/main/java/com/tzld/piaoquan/recommend/server/util/FestiveUtil.java

@@ -0,0 +1,46 @@
+package com.tzld.piaoquan.recommend.server.util;
+
+import lombok.extern.slf4j.Slf4j;
+
+import java.io.BufferedReader;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.Objects;
+
+@Slf4j
+public class FestiveUtil {
+
+    private static Map<String, String> festiveMap = new HashMap<>();
+
+    public static void init() {
+        long start = System.currentTimeMillis();
+        InputStream resourceAsStream = FestiveUtil.class.getClassLoader().getResourceAsStream("festive.txt");
+
+        if (Objects.nonNull(resourceAsStream)) {
+            try (BufferedReader reader = new BufferedReader(new InputStreamReader(resourceAsStream))) {
+                Map<String, String> tmpMap = new HashMap<>();
+                String line;
+                while ((line = reader.readLine()) != null) {
+                    String[] split = line.split(",");
+                    if (split.length >= 2) {
+                        tmpMap.put(split[0], split[1]);
+                    }
+                }
+
+                FestiveUtil.festiveMap = tmpMap;
+            } catch (IOException e) {
+                log.error("read festive.txt error: ", e);
+            }
+        }
+
+        long end = System.currentTimeMillis();
+        log.info("festive.txt loaded successfully cost {}", end - start);
+    }
+
+    public static String getFestiveByDate(String date) {
+        return festiveMap.get(date);
+    }
+}

Файловите разлики са ограничени, защото са твърде много
+ 41 - 0
recommend-server-service/src/main/resources/20250218_bucket_322.txt


+ 315 - 0
recommend-server-service/src/main/resources/feeds_score_config_xgb_rov_20250228.conf

@@ -0,0 +1,315 @@
+scorer-config = {
+  rov-score-config = {
+    scorer-name = "com.tzld.piaoquan.recommend.server.service.score.XGBoostScorer"
+    scorer-priority = 99
+    model-path = "zhangbo/model_xgb_for_str_v2.tar.gz"
+    param = {
+      localDir = "xgboost/model_xgb_for_str_v2"
+      features = [
+            "b1_is_return_1_1h"
+            "b1_is_return_1_3h"
+            "b1_is_return_1_24h"
+            "b1_is_return_1_168h"
+            "b1_is_share_1h"
+            "b1_is_share_3h"
+            "b1_is_share_24h"
+            "b1_is_share_168h"
+            "b1_rovn*log(r)_1h"
+            "b1_rovn*log(r)_3h"
+            "b1_rovn*log(r)_24h"
+            "b1_rovn*log(r)_168h"
+            "b1_str_1h"
+            "b1_str_3h"
+            "b1_str_24h"
+            "b1_str_168h"
+            "b1_str_one_1h"
+            "b1_str_one_3h"
+            "b1_str_one_24h"
+            "b1_str_one_168h"
+            "b1_str_plus_1h"
+            "b1_str_plus_3h"
+            "b1_str_plus_24h"
+            "b1_str_plus_168h"
+            "b2_is_return_1_1h"
+            "b2_is_return_1_3h"
+            "b2_is_return_1_24h"
+            "b2_is_return_1_168h"
+            "b2_is_share_1h"
+            "b2_is_share_3h"
+            "b2_is_share_24h"
+            "b2_is_share_168h"
+            "b2_rovn*log(r)_1h"
+            "b2_rovn*log(r)_3h"
+            "b2_rovn*log(r)_24h"
+            "b2_rovn*log(r)_168h"
+            "b2_str_1h"
+            "b2_str_3h"
+            "b2_str_24h"
+            "b2_str_168h"
+            "b2_str_one_1h"
+            "b2_str_one_3h"
+            "b2_str_one_24h"
+            "b2_str_one_168h"
+            "b2_str_plus_1h"
+            "b2_str_plus_3h"
+            "b2_str_plus_24h"
+            "b2_str_plus_168h"
+            "b3_is_return_1_24h"
+            "b3_is_return_1_168h"
+            "b3_is_share_24h"
+            "b3_is_share_168h"
+            "b3_rovn*log(r)_24h"
+            "b3_rovn*log(r)_168h"
+            "b3_str_24h"
+            "b3_str_168h"
+            "b3_str_one_24h"
+            "b3_str_one_168h"
+            "b3_str_plus_24h"
+            "b3_str_plus_168h"
+            "b4_is_return_1_6h"
+            "b4_is_return_1_24h"
+            "b4_is_share_6h"
+            "b4_is_share_24h"
+            "b4_rovn*log(r)_6h"
+            "b4_rovn*log(r)_24h"
+            "b4_str_6h"
+            "b4_str_24h"
+            "b4_str_one_6h"
+            "b4_str_one_24h"
+            "b4_str_plus_6h"
+            "b4_str_plus_24h"
+            "b5_is_return_1_6h"
+            "b5_is_return_1_24h"
+            "b5_is_share_6h"
+            "b5_is_share_24h"
+            "b5_rovn*log(r)_6h"
+            "b5_rovn*log(r)_24h"
+            "b5_str_6h"
+            "b5_str_24h"
+            "b5_str_one_6h"
+            "b5_str_one_24h"
+            "b5_str_plus_6h"
+            "b5_str_plus_24h"
+            "b6_is_return_1_6h"
+            "b6_is_return_1_24h"
+            "b6_is_share_6h"
+            "b6_is_share_24h"
+            "b6_rovn*log(r)_6h"
+            "b6_rovn*log(r)_24h"
+            "b6_str_6h"
+            "b6_str_24h"
+            "b6_str_one_6h"
+            "b6_str_one_24h"
+            "b6_str_plus_6h"
+            "b6_str_plus_24h"
+            "b7_is_return_1_6h"
+            "b7_is_return_1_24h"
+            "b7_is_share_6h"
+            "b7_is_share_24h"
+            "b7_rovn*log(r)_6h"
+            "b7_rovn*log(r)_24h"
+            "b7_str_6h"
+            "b7_str_24h"
+            "b7_str_one_6h"
+            "b7_str_one_24h"
+            "b7_str_plus_6h"
+            "b7_str_plus_24h"
+            "b8_is_return_1_1h"
+            "b8_is_return_1_12h"
+            "b8_is_share_1h"
+            "b8_is_share_12h"
+            "b8_rovn*log(r)_1h"
+            "b8_rovn*log(r)_12h"
+            "b8_str_1h"
+            "b8_str_12h"
+            "b8_str_one_1h"
+            "b8_str_one_12h"
+            "b8_str_plus_1h"
+            "b8_str_plus_12h"
+            "b9_is_return_1_1h"
+            "b9_is_return_1_12h"
+            "b9_is_share_1h"
+            "b9_is_share_12h"
+            "b9_rovn*log(r)_1h"
+            "b9_rovn*log(r)_12h"
+            "b9_str_1h"
+            "b9_str_12h"
+            "b9_str_one_1h"
+            "b9_str_one_12h"
+            "b9_str_plus_1h"
+            "b9_str_plus_12h"
+            "b10_is_return_1_6h"
+            "b10_is_share_6h"
+            "b10_rovn*log(r)_6h"
+            "b10_str_6h"
+            "b10_str_one_6h"
+            "b10_str_plus_6h"
+            "b11_is_return_1_1h"
+            "b11_is_share_1h"
+            "b11_rovn*log(r)_1h"
+            "b11_str_1h"
+            "b11_str_one_1h"
+            "b11_str_plus_1h"
+            "b13_is_return_1_1h"
+            "b13_is_return_1_3h"
+            "b13_is_return_1_24h"
+            "b13_is_return_1_168h"
+            "b13_is_share_1h"
+            "b13_is_share_3h"
+            "b13_is_share_24h"
+            "b13_is_share_168h"
+            "b13_rovn*log(r)_1h"
+            "b13_rovn*log(r)_3h"
+            "b13_rovn*log(r)_24h"
+            "b13_rovn*log(r)_168h"
+            "b13_str_1h"
+            "b13_str_3h"
+            "b13_str_24h"
+            "b13_str_168h"
+            "b13_str_one_1h"
+            "b13_str_one_3h"
+            "b13_str_one_24h"
+            "b13_str_one_168h"
+            "b13_str_plus_1h"
+            "b13_str_plus_3h"
+            "b13_str_plus_24h"
+            "b13_str_plus_168h"
+            "c1_click_12h"
+            "c1_click_24h"
+            "c1_click_72h"
+            "c1_click_168h"
+            "c1_is_return_1_12h"
+            "c1_is_return_1_24h"
+            "c1_is_return_1_72h"
+            "c1_is_return_1_168h"
+            "c1_is_share_12h"
+            "c1_is_share_24h"
+            "c1_is_share_72h"
+            "c1_is_share_168h"
+            "c1_rovn*log(r)_12h"
+            "c1_rovn*log(r)_24h"
+            "c1_rovn*log(r)_72h"
+            "c1_rovn*log(r)_168h"
+            "c1_str_12h"
+            "c1_str_24h"
+            "c1_str_72h"
+            "c1_str_168h"
+            "c1_str_one_12h"
+            "c1_str_one_24h"
+            "c1_str_one_72h"
+            "c1_str_one_168h"
+            "c1_str_plus_12h"
+            "c1_str_plus_24h"
+            "c1_str_plus_72h"
+            "c1_str_plus_168h"
+            "c2_click_12h"
+            "c2_click_168h"
+            "c2_click_24h"
+            "c2_click_72h"
+            "c2_is_return_1_12h"
+            "c2_is_return_1_168h"
+            "c2_is_return_1_24h"
+            "c2_is_return_1_72h"
+            "c2_is_share_12h"
+            "c2_is_share_168h"
+            "c2_is_share_24h"
+            "c2_is_share_72h"
+            "c2_return_n_uv_12h"
+            "c2_return_n_uv_168h"
+            "c2_return_n_uv_24h"
+            "c2_return_n_uv_72h"
+            "c2_share_cnt_12h"
+            "c2_share_cnt_168h"
+            "c2_share_cnt_24h"
+            "c2_share_cnt_72h"
+            "c3_click_12h"
+            "c3_click_168h"
+            "c3_click_24h"
+            "c3_click_72h"
+            "c3_is_return_1_12h"
+            "c3_is_return_1_168h"
+            "c3_is_return_1_24h"
+            "c3_is_return_1_72h"
+            "c3_is_share_12h"
+            "c3_is_share_168h"
+            "c3_is_share_24h"
+            "c3_is_share_72h"
+            "c3_return_n_uv_12h"
+            "c3_return_n_uv_168h"
+            "c3_return_n_uv_24h"
+            "c3_return_n_uv_72h"
+            "c3_share_cnt_12h"
+            "c3_share_cnt_168h"
+            "c3_share_cnt_24h"
+            "c3_share_cnt_72h"
+            "c4_avg_rovn_24h"
+            "c4_avg_rovn_72h"
+            "c4_avg_rovn_168h"
+            "c4_avg_str_24h"
+            "c4_avg_str_72h"
+            "c4_avg_str_168h"
+            "c4_avg_str_one_24h"
+            "c4_avg_str_one_72h"
+            "c4_avg_str_one_168h"
+            "c4_avg_str_plus_24h"
+            "c4_avg_str_plus_72h"
+            "c4_avg_str_plus_168h"
+            "c4_diff_rovn_24h"
+            "c4_diff_rovn_72h"
+            "c4_diff_rovn_168h"
+            "c4_diff_str_24h"
+            "c4_diff_str_72h"
+            "c4_diff_str_168h"
+            "c4_diff_str_one_24h"
+            "c4_diff_str_one_72h"
+            "c4_diff_str_one_168h"
+            "c4_diff_str_plus_24h"
+            "c4_diff_str_plus_72h"
+            "c4_diff_str_plus_168h"
+            "c5_avgscore_tags_1d"
+            "c5_avgscore_tags_3d"
+            "c5_avgscore_tags_7d"
+            "c5_matchnum_tags_1d"
+            "c5_matchnum_tags_3d"
+            "c5_matchnum_tags_7d"
+            "c5_maxscore_tags_1d"
+            "c5_maxscore_tags_3d"
+            "c5_maxscore_tags_7d"
+            "c6_avgscore_tags_1d"
+            "c6_avgscore_tags_3d"
+            "c6_avgscore_tags_7d"
+            "c6_matchnum_tags_1d"
+            "c6_matchnum_tags_3d"
+            "c6_matchnum_tags_7d"
+            "c6_maxscore_tags_1d"
+            "c6_maxscore_tags_3d"
+            "c6_maxscore_tags_7d"
+            "d1_ros_cf_rank"
+            "d1_ros_cf_score"
+            "d1_rov_cf_rank"
+            "d1_rov_cf_score"
+            "d2_rank"
+            "d2_score"
+            "d3_exp"
+            "d3_return_n"
+            "d3_rovn"
+            "total_time"
+            "width"
+            "height"
+            "width/height"
+            "size"
+            "bit_rate"
+            "is_greeting"
+            "festive_sim"
+            "head_title_festive_sim"
+            "head_title_merge1_sim"
+            "head_title_merge2_sim"
+            "merge1_sim"
+            "merge2_sim"
+            "title_sim"
+            "hour"
+            "create_ts_diff"
+      ]
+    }
+  }
+}

+ 249 - 0
recommend-server-service/src/main/resources/festive.txt

@@ -0,0 +1,249 @@
+2024-01-01,元旦
+2024-01-18,腊八节
+2024-02-02,小年
+2024-02-03,小年
+2024-02-09,除夕
+2024-02-10,春节
+2024-02-10,初一
+2024-02-11,初二
+2024-02-12,初三
+2024-02-13,初四
+2024-02-14,初五
+2024-02-15,初六
+2024-02-16,初七
+2024-02-17,初八
+2024-02-18,初九
+2024-02-19,初十
+2024-02-14,情人节
+2024-02-24,元宵节
+2024-03-11,龙抬头
+2024-03-08,妇女节
+2024-03-12,植树节
+2024-05-01,劳动节
+2024-05-12,母亲节
+2024-06-01,儿童节
+2024-06-10,端午节
+2024-06-16,父亲节
+2024-07-01,建党节
+2024-08-01,建军节
+2024-08-10,七夕节
+2024-08-18,中元节
+2024-09-17,中秋节
+2024-10-01,国庆节
+2024-10-11,重阳节
+2024-11-28,感恩节
+2024-12-13,公祭日
+2024-12-24,平安夜
+2024-12-25,圣诞节
+2024-01-06,小寒
+2024-01-20,大寒
+2024-02-04,立春
+2024-02-19,雨水
+2024-03-05,惊蛰
+2024-03-20,春分
+2024-04-04,清明
+2024-04-19,谷雨
+2024-05-05,立夏
+2024-05-20,小满
+2024-06-05,芒种
+2024-06-21,夏至
+2024-07-06,小暑
+2024-07-22,大暑
+2024-08-07,立秋
+2024-08-22,处暑
+2024-09-07,白露
+2024-09-22,秋分
+2024-10-08,寒露
+2024-10-23,霜降
+2024-11-07,立冬
+2024-11-22,小雪
+2024-12-06,大雪
+2024-12-21,冬至
+2024-11-12,孙中山诞辰
+2024-03-12,孙中山逝世
+2024-12-26,毛主席诞辰
+2024-09-09,毛主席逝世
+2024-03-05,周恩来诞辰
+2024-01-08,周恩来逝世
+2024-08-22,邓小平诞辰
+2024-02-19,邓小平逝世
+2024-07-03,李克强诞辰
+2024-10-27,李克强逝世
+2024-09-18,九一八
+2024-07-07,七七事变
+2024-09-07,袁隆平诞辰
+2024-05-22,袁隆平逝世
+2024-10-24,彭德怀诞辰
+2024-11-29,彭德怀逝世
+2024-12-01,朱德诞辰
+2024-07-06,朱德逝世
+2024-10-27,吴尊友逝世
+2024-03-05,学雷锋
+2024-03-05,两会
+2024-03-15,315国际消费者权益日
+2025-01-01,元旦
+2025-01-07,腊八节
+2025-01-22,小年
+2025-01-23,小年
+2025-01-28,除夕
+2025-01-29,春节
+2025-01-29,初一
+2025-01-30,初二
+2025-01-31,初三
+2025-02-01,初四
+2025-02-02,初五
+2025-02-03,初六
+2025-02-04,初七
+2025-02-05,初八
+2025-02-06,初九
+2025-02-07,初十
+2025-02-14,情人节
+2025-02-22,元宵节
+2025-03-01,龙抬头
+2025-03-08,妇女节
+2025-03-12,植树节
+2025-05-01,劳动节
+2025-05-11,母亲节
+2025-06-01,儿童节
+2025-05-31,端午节
+2025-06-15,父亲节
+2025-07-01,建党节
+2025-08-01,建军节
+2025-08-29,七夕节
+2025-09-06,中元节
+2025-10-06,中秋节
+2025-10-01,国庆节
+2025-10-29,重阳节
+2025-11-27,感恩节
+2025-12-13,公祭日
+2025-12-24,平安夜
+2025-12-25,圣诞节
+2025-01-05,小寒
+2025-01-20,大寒
+2025-02-03,立春
+2025-02-18,雨水
+2025-03-05,惊蛰
+2025-03-20,春分
+2025-04-04,清明
+2025-04-20,谷雨
+2025-05-05,立夏
+2025-05-21,小满
+2025-06-05,芒种
+2025-06-21,夏至
+2025-07-07,小暑
+2025-07-22,大暑
+2025-08-07,立秋
+2025-08-23,处暑
+2025-09-07,白露
+2025-09-23,秋分
+2025-10-08,寒露
+2025-10-23,霜降
+2025-11-07,立冬
+2025-11-22,小雪
+2025-12-07,大雪
+2025-12-21,冬至
+2025-11-12,孙中山诞辰
+2025-03-12,孙中山逝世
+2025-12-26,毛主席诞辰
+2025-09-09,毛主席逝世
+2025-03-05,周恩来诞辰
+2025-01-08,周恩来逝世
+2025-08-22,邓小平诞辰
+2025-02-19,邓小平逝世
+2025-07-03,李克强诞辰
+2025-10-27,李克强逝世
+2025-09-18,九一八
+2025-07-07,七七事变
+2025-09-07,袁隆平诞辰
+2025-05-22,袁隆平逝世
+2025-10-24,彭德怀诞辰
+2025-11-29,彭德怀逝世
+2025-12-01,朱德诞辰
+2025-07-06,朱德逝世
+2025-10-27,吴尊友逝世
+2025-03-05,学雷锋
+2024-03-05,两会
+2024-03-15,315国际消费者权益日
+2026-01-01,元旦
+2026-01-26,腊八节
+2026-02-10,小年
+2026-02-11,小年
+2026-02-16,除夕
+2026-02-17,春节
+2026-02-17,初一
+2026-02-18,初二
+2026-02-19,初三
+2026-02-20,初四
+2026-02-21,初五
+2026-02-22,初六
+2026-02-23,初七
+2026-02-24,初八
+2026-02-25,初九
+2026-02-26,初十
+2026-02-14,情人节
+2026-03-03,元宵节
+2026-03-20,龙抬头
+2026-03-08,妇女节
+2026-03-12,植树节
+2026-05-01,劳动节
+2026-05-10,母亲节
+2026-06-01,儿童节
+2026-06-19,端午节
+2026-06-21,父亲节
+2026-07-01,建党节
+2026-08-01,建军节
+2026-08-19,七夕节
+2026-08-27,中元节
+2026-09-25,中秋节
+2026-10-01,国庆节
+2026-10-18,重阳节
+2026-11-26,感恩节
+2026-12-13,公祭日
+2026-12-24,平安夜
+2026-12-25,圣诞节
+2026-01-05,小寒
+2026-01-20,大寒
+2026-02-04,立春
+2026-02-18,雨水
+2026-03-05,惊蛰
+2026-03-20,春分
+2026-04-05,清明
+2026-04-20,谷雨
+2026-05-05,立夏
+2026-05-21,小满
+2026-06-05,芒种
+2026-06-21,夏至
+2026-07-07,小暑
+2026-07-23,大暑
+2026-08-07,立秋
+2026-08-23,处暑
+2026-09-07,白露
+2026-09-23,秋分
+2026-10-08,寒露
+2026-10-23,霜降
+2026-11-07,立冬
+2026-11-22,小雪
+2026-12-07,大雪
+2026-12-22,冬至
+2026-11-12,孙中山诞辰
+2026-03-12,孙中山逝世
+2026-12-26,毛主席诞辰
+2026-09-09,毛主席逝世
+2026-03-05,周恩来诞辰
+2026-01-08,周恩来逝世
+2026-08-22,邓小平诞辰
+2026-02-19,邓小平逝世
+2026-07-03,李克强诞辰
+2026-10-27,李克强逝世
+2026-09-18,九一八
+2026-07-07,七七事变
+2026-09-07,袁隆平诞辰
+2026-05-22,袁隆平逝世
+2026-10-24,彭德怀诞辰
+2026-11-29,彭德怀逝世
+2026-12-01,朱德诞辰
+2026-07-06,朱德逝世
+2026-10-27,吴尊友逝世
+2026-03-05,学雷锋
+2024-03-05,两会
+2024-03-15,315国际消费者权益日

Някои файлове не бяха показани, защото твърде много файлове са промени