feat(classify): super-linear positive weighting by hit count
正向改为按命中次数 n(require_title + reaction + charge + weak)做平方加权,使多信号同现的真 reaction 不被单个负向词打穿(1+1>2、1+1+1>5);标题不含 require_title 直接 0 分。库内 796 条有效视频复测:线以下误伤由 47 降至 14。
This commit is contained in:
1 parent
742c67a1c3
commit
337e379514
4 files changed
+78
-75
No files matched your search
+15
-23
@@ -74,11 +74,7 @@ _DATE_PATTERNS = (
|
||||
)
|
||||
_DATE_RE = re.compile("|".join(_DATE_PATTERNS))
|
||||
|
||||
# 各信号的权重(见 project.md §3.3)。
|
||||
REACTION_SCORE = 3
|
||||
CHARGE_MULTI_SCORE = 3
|
||||
CHARGE_SINGLE_SCORE = 1
|
||||
WEAK_SCORE = 1
|
||||
# 负向权重(见 project.md §3.3)。正向改为「命中次数」超线性加权,见 score_item。
|
||||
NEGATIVE_SCORE = 6
|
||||
DATE_SCORE = 6
|
||||
SELF_SCORE = 3
|
||||
@@ -98,29 +94,25 @@ def score_item(
|
||||
) -> int:
|
||||
"""按 project.md §3.3 计算候选分数。
|
||||
|
||||
强正向 ``reaction`` 只在标题同时命中 ``require_title`` 时成立;时长只作为
|
||||
已存在 reaction / charge 信号时的加权,避免纯长录像仅靠时长进池。
|
||||
正向按**命中次数**超线性加权:每命中一个正向词(``require_title`` / ``reaction``
|
||||
/ ``charge`` / ``weak_positive``)记 1 次,正向得分 = 命中次数²(1→1、2→4、
|
||||
3→9……),使多信号同现的真 reaction 不会被单个负向词打穿(1+1>2、1+1+1>5)。
|
||||
标题不含 ``require_title`` 直接 0 分;时长只在此基础上已有命中时加权。
|
||||
"""
|
||||
score = 0
|
||||
require_title = str(classify.get("require_title") or "")
|
||||
if require_title and not passes_required_title(title, require_title):
|
||||
return 0
|
||||
|
||||
reaction_matched = bool(matched_words(title, classify.get("reaction")))
|
||||
reaction_hit = reaction_matched and (
|
||||
not require_title or passes_required_title(title, require_title)
|
||||
)
|
||||
if reaction_hit:
|
||||
score += REACTION_SCORE
|
||||
hits = 0
|
||||
if require_title:
|
||||
hits += 1
|
||||
hits += len(matched_words(title, classify.get("reaction")))
|
||||
hits += len(matched_words(title, classify.get("charge")))
|
||||
hits += len(matched_words(title, classify.get("weak_positive")))
|
||||
|
||||
charge_hits = matched_words(title, classify.get("charge"))
|
||||
if len(charge_hits) >= 2:
|
||||
score += CHARGE_MULTI_SCORE
|
||||
elif len(charge_hits) == 1:
|
||||
score += CHARGE_SINGLE_SCORE
|
||||
score = hits * hits
|
||||
|
||||
if matched_words(title, classify.get("weak_positive")):
|
||||
score += WEAK_SCORE
|
||||
|
||||
if reaction_hit or charge_hits:
|
||||
if hits:
|
||||
boost = classify.get("duration_boost") or {}
|
||||
gt_60 = int(boost.get("gt_60min", 2))
|
||||
gt_30 = int(boost.get("gt_30min", 1))
|
||||
|
||||
Reference in new issue
Block a user