如何在django中使用sqlite3数据库全文检索?

问题描述 投票:0回答:3

我正在开发一个带有 sqlite3 数据库的 django 应用程序,它具有固定的数据库内容。固定是指数据库的内容不会随着时间的推移而改变。模型是这样的:

class QScript(models.Model):
    ch_no = models.IntegerField()
    v_no = models.IntegerField()
    v = models.TextField()

表中约有 6500 条记录。给定的文本可能缺少一些单词,或者一些单词拼写错误,我需要确定它的

ch_no
v_no
。例如,如果数据库中有一个
v
字段,其中包含文本 “This is an example verse”,则给定的文本如 “This an example verse” 应该给我来自 db 的
ch_no
v_no
。我相信这可以使用全文搜索来完成。

我的疑问是:

  1. 全文检索可以做到这一点吗?根据我的研究,我的猜测是,它可以,正如sqlite3页面中所述:全文搜索是“Google、Yahoo和Bing对万维网上的文档所做的事情”。在 SO 中引用,我也阅读了这篇文章,以及许多其他文章,但没有找到任何密切符合我的要求的内容。

  2. 如何在 django 模型中使用 FTS?我读了this,但没有帮助。似乎太过时了。请阅读here“...需要直接操作数据库来添加全文索引”。搜索主要提供 MySQL 相关信息,但我需要在 sqlite3 中进行。那么如何在 sqlite3 中做到直接操作


编辑:

我坚持使用 sqlite3 的选择正确吗?或者我应该使用不同的东西(如 Alex Morozov 所说的 haystack+elasticsearch)?我的数据库不会变得更大,而且我研究过,对于小型数据库,sqlite 几乎总是更好(我的情况符合 sqlite 何时使用清单中的第四个)。

python django sqlite full-text-search
3个回答
6
投票

SQLite 的 FTS 引擎 基于标记 - 搜索引擎尝试匹配的关键字。

有多种标记器可用,但它们相对简单。 “简单”分词器只是将每个单词分开并将其小写:例如,在字符串“The Quick Brown Fox Jumps Over the Lazy Dog”中,单词“Jumps”会匹配,但不会匹配“Jump”。 “porter”分词器更先进一些,它剥离了单词的词形变化,因此“jumps”和“jumping”会匹配,但像“jmups”这样的拼写错误不会匹配。

简而言之,SQLite FTS 扩展相当基础,并不意味着与 Google 等公司竞争。

至于Django集成,我不相信有。您可能需要使用 Django 的接口进行原始 SQL 查询,以创建和查询 FTS 表。


4
投票

我认为虽然sqlite是一个令人惊叹的软件,但它的全文搜索功能非常有限。相反,您可以使用 Haystack Django 应用程序和一些后端(如 Elasticsearch)来索引数据库。在我看来,进行此设置(并且仍然能够访问您的 sqlite 数据库)是 FTS 方面最强大、最灵活的方式。

Elasticsearch 有一个基于 Levenshtein 距离的 模糊搜索(简而言之,它将处理您的“egsample”查询)。因此,您所需要做的就是进行正确类型的查询:

from haystack.forms import SearchForm
from haystack.generic_views import SearchView
from haystack import indexes


class QScriptIndex(indexes.SearchIndex, indexes.Indexable):
    v = indexes.CharField(document=True)

    def get_model(self):
        return QScript


class QScriptSearchForm(SearchForm):
    text_fuzzy = forms.CharField(required=False)    

    def search(self):        
        sqs = super(QScriptSearchForm, self).search()

        if not self.is_valid():
            return self.no_query_found()

        text_fuzzy = self.cleaned_data.get('text_fuzzy')
        if text_fuzzy:
            sqs = sqs.filter(text__fuzzy=text_fuzzy)

        return sqs


class QScriptSearchView(SearchView):        
    form_class = QScriptSearchForm

更新:只要 PostgreSQL 具有 Levenshtein 距离函数,您还可以将其用作 Haystack 后端以及独立的搜索引擎。如果您选择第二种方式,则必须实现一个自定义查询表达式,如果您使用的是最新版本的 Django,这相对容易。


0
投票

虽然 SQLite 的 FTS 对于您的应用程序来说可能过于有限,但 Elasticsearch 在设置和维护正在运行的服务器方面可能成本太高。

Haystack 中更轻量级的引擎之一可能值得研究。特别是,Whoosh 易于集成(无需服务器),并且具有一些更高级的 FTS 功能,例如模糊搜索。

这篇关于“使用 django-haystack 和 whoosh改进搜索 API”的文章解释了运行它的基础知识。 Whoosh 文档中解释了设置模糊术语查询

从纯技术角度来看,这绝对不是最“令人兴奋”的解决方案,但它可以快速实施,应该在您的场景中表现“足够好”,并且维护成本相对较低。

© www.soinside.com 2019 - 2024. All rights reserved.