Python根据无法识别搜索词找出可能输入内容模型

下面是一个 Python 示例:根据"无法识别"的搜索词,从已知词库/历史搜索词中找出可能想输入的内容,并记录未知搜索词和候选结果。

```python

import difflib

import json

from collections import Counter, defaultdict

class SearchSuggester:

def init(self, known_words, history_queries=None, min_score=0.3):

已知可识别词库

self.known_words = set(known_words)

历史搜索词,可作为候选池

self.history_queries = list(history_queries or \[\])

self.min_score = min_score

记录无法识别的搜索词出现次数

self.unknown_counter = Counter()

记录每个未知搜索词对应的候选输入

self.candidate_log = defaultdict(list)

def is_recognized(self, query: str) -> bool:

"""判断搜索词是否可识别,这里简单判断是否在已知词库中"""

return query in self.known_words

@staticmethod

def _edit_distance(a: str, b: str) -> int:

"""计算编辑距离,用于衡量字符串相似程度"""

m, n = len(a), len(b)

dp = list(range(n + 1))

for i in range(1, m + 1):

prev = dp0

dp0 = i

for j in range(1, n + 1):

tmp = dpj

if ai - 1 == bj - 1:

dpj = prev

else:

dpj = min(prev, dpj, dpj - 1) + 1

prev = tmp

return dpn

def _score(self, query: str, candidate: str) -> float:

"""综合相似度评分"""

序列相似度

seq_score = difflib.SequenceMatcher(None, query, candidate).ratio()

编辑距离相似度

dist = self._edit_distance(query, candidate)

edit_score = 1 - dist / max(len(query), len(candidate), 1)

前缀、包含关系加分

prefix_bonus = 0.08 if candidate.startswith(query) else 0.0

contains_bonus = 0.04 if query in candidate else 0.0

return 0.55 * seq_score + 0.45 * edit_score + prefix_bonus + contains_bonus

def suggest(self, query: str, top_n: int = 5):

"""为未知搜索词推荐可能输入"""

pool = set(self.history_queries) | self.known_words

scored = \[\]

for word in pool:

if word == query:

continue

score = self._score(query, word)

if score >= self.min_score:

scored.append((word, round(score, 4)))

scored.sort(key=lambda x: x1, reverse=True)

return scored:top_n

def collect(self, query: str, top_n: int = 5):

"""

搜集无法识别的搜索词及其可能输入内容。

如果搜索词可识别,则不记录,直接返回空列表。

"""

if self.is_recognized(query):

return \[\]

self.unknown_counterquery += 1

suggestions = self.suggest(query, top_n=top_n)

self.candidate_logquery = suggestions

return suggestions

def dump(self, path: str):

"""将搜集结果保存到 JSON 文件"""

data = {

"unknown_counter": dict(self.unknown_counter),

"candidate_log": dict(self.candidate_log),

}

with open(path, "w", encoding="utf-8") as f:

json.dump(data, f, ensure_ascii=False, indent=2)

if name == "main":

known_words = {

"苹果手机", "华为手机", "小米手机", "蓝牙耳机", "机械键盘"

}

history_queries = [

"苹果手机", "苹果电脑", "华为手机", "小米手机",

"蓝牙耳机", "机械键盘", "显示器", "笔记本电脑"

]

suggester = SearchSuggester(known_words, history_queries)

test_queries = [

"苹果手几",

"篮牙耳机",

"机械健盘",

"苹果手机", # 可识别,不会被记录

]

for q in test_queries:

result = suggester.collect(q)

print(f"搜索词: {q!r} -> 可能输入: {result}")

print("\n未知词统计:", suggester.unknown_counter)

print("候选记录:", dict(suggester.candidate_log))

保存搜集结果

suggester.dump("unknown_query_candidates.json")

```

输出示例:

```text

搜索词: '苹果手几' -> 可能输入: ('苹果手机', 0.9), ('苹果电脑', 0.5), ...

搜索词: '篮牙耳机' -> 可能输入: ('蓝牙耳机', 0.9), ...

搜索词: '机械健盘' -> 可能输入: ('机械键盘', 0.9), ...

搜索词: '苹果手机' -> 可能输入: \[\]

```

这个实现的核心是:

  1. 判断搜索词是否在已知词库中;

  2. 如果无法识别,就从历史搜索词和已知词库中找相似词;

  3. 使用编辑距离和字符串相似度综合打分;

  4. 记录未知搜索词及其候选内容,方便后续分析或人工审核。

实际生产中可以进一步使用 rapidfuzz、拼音纠错、Elasticsearch Suggest、用户点击日志等提升效果。

文章仅供参考用。

相关推荐
aifannihao1 小时前
AI 学习第 14 课:CNN 训 6 轮卡在 0.5352,数据没打乱
pytorch·python·深度学习·cnn·学习路线
yuyuxun11 小时前
协同过滤的校园二手物品智能推荐系统的设计与实现 毕业设计-附源码40082
javascript·vue.js·spring boot·python·数据分析·django·课程设计
如夏倾城2 小时前
百度文心(容易被忽略的好用AI)使用方式
人工智能·python·百度·语言模型·dubbo
用户019027581612 小时前
quotes 实时价和 klines 最新收盘价为什么对不上?
python
another heaven2 小时前
【C/C++ Ranges 是零开销抽象吗?拆开管道、惰性求值和编译期膨胀】
c语言·开发语言·c++
少司府3 小时前
嵌入式入门篇(二):初识STM32F103ZET6
linux·python·stm32·单片机·嵌入式硬件·mcu·嵌入式软件
打工仔折腾 AI4 小时前
Changedetection.io 网页变动监控:Docker 部署、通知配置与公网暴露实践
运维·人工智能·后端·python·docker·容器·性能优化
火云代理4 小时前
Python 使用代理 IP 前,先弄清 Requests 的配置来源与验证方法
网络·python·网络协议·tcp/ip·ip
SomeOtherTime4 小时前
Rust 闭包语法和原理(AI回答)
开发语言·后端·rust
apcipot_rain4 小时前
C++转Java日记(10)
java·开发语言