文章
问答
冒泡
python django实现拼音搜索关键字

思路:表中新建一个pinyins字段,类型是数组

pinyins = ArrayField(models.CharField(max_length=128), default=list, blank=True)
# 模型里面是数组,但是实际在数据库中存的是字符串

app下面新建一个script文件夹,存放脚本,脚本作用是把数据库已经存在的名称字段转换成拼音存到pinyins

使用pypinyin模块

from pypinyin import lazy_pinyin, Style
from ..models.jobs import (
    JobTitle,
)

STYLES = [
    Style.NORMAL,  # 标准模式 销售-->[xiaoshou]
    Style.FIRST_LETTER,  # 首字母模式 销售-->[xs]
]


def get_name_pinyin(name):
    results = []
    for style in STYLES:
        rs = lazy_pinyin(name, style=style, errors="default")
        results.append("".join(rs))
    return list(set(results))

# python mange.py runscript script下面脚本的文件名,不要后缀


def get_aliases_pinyin(aliases):
    results = []
    for name in aliases:
        results += get_name_pinyin(name)
    return list(set(results))


def get_pinyins(name, aliases):
    return list(set(get_name_pinyin(name) + get_aliases_pinyin(aliases)))


def run():
    queryset = JobTitle.objects.all()
    for title in queryset:
        title.pinyins = get_pinyins(title.name, title.aliases)
        title.save()
#在views中查询
def query_job_title(self, query, size=5, return_fields=None):
        if return_fields is None:
            return_fields = ["name"]
        qs = self.get_queryset().filter(
            (
                Q(name__icontains=query)
                | Q(aliases__icontains=query)
                | Q(pinyins__icontains=query)
            )
            & Q(job_title_job_open__isnull=False)
            & Q(is_official=True)
        )

        if len(return_fields) == 1:
            qs = qs.values_list(*return_fields, flat=True)
        else:
            qs = qs.values(*return_fields)
        qs = qs.distinct()[:size]
        return qs
为了保证每次新插入数据都能更新到pinyins字段,需要在model模型中重写save方法
def save(self, *args, **kwargs):
        w2p = Words2Pinyin(self.name, self.aliases)
        self.pinyins = w2p.get_pinyins()
        super().save(*args, **kwargs)

# Words2Pinyin是一个工具类
from pypinyin import lazy_pinyin, Style
class Words2Pinyin:
    def __init__(self, name, aliases):
        self.STYLES = [
            Style.NORMAL,  # 标准模式 销售-->[xiaoshou]
            Style.FIRST_LETTER,  # 首字母模式 销售-->[xs]
        ]
        self.name = name
        self.aliases = aliases

    def get_name_pinyin(self, name):
        results = []
        for style in self.STYLES:
            s = lazy_pinyin(name, style=style, errors="default")
            results.append("".join(s))
        return list(set(results))

    def get_aliases_pinyin(self, aliases):
        results = []
        for name in aliases:
            results += self.get_name_pinyin(name)
        return list(set(results))

    def get_pinyins(self):
        return list(
            set(self.get_name_pinyin(self.name) + self.get_aliases_pinyin(self.aliases))
        )
python

关于作者

小乙哥
学海无涯,回头是岸
获得点赞
文章被阅读