全文检索

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了全文检索相关的知识,希望对你有一定的参考价值。

全文检索不同于特定字段的模糊查询,使用全文检索的效率更高,并且能够对于中文进行分词
  • haystack : 全文检索框架,支持whoosh、solr、Xapian、Elasticsearc四种全文检索引擎。官网:http://haystacksearch.org/
  • whoosh : 纯Python编写的全文本搜索引擎,虽然性能比不上sphinx、xapian、Elasticsearc等,但是无二进制包,程序不会莫名奇妙的崩溃,对于小型的站点,whoos已经足够使用。官网:https://whoosh.readthedocs.io/en/latest/
  • jieba : 一款免费的中文分词包,如果觉得不好用可以使用一些收费产品。详细说明:https://github.com/fxsjy/jieba
 
首先在虚拟环境中依次安装需要的包
pip install django-haystack==2.6.1
pip install whoosh==2.7.4
pip install jieba==0.39
 
 
在settings.py文件中安装haystack
INSTALLED_APPS = (
      .....  
      ‘haystack‘,
)
 
 
在settings.py文件中配置搜索引擎
HAYSTACK_CONNECTIONS = {
        ‘default‘ : {
                #使用whoosh引擎
                ‘ENGINE‘ : ‘haystack.backends.whoosh_cn_backend.WhooshEngine‘,
                #索引文件路径
                ‘PATH‘ : os.path.join(BASE_DIR, ‘whoosh_index‘),
      }
#当添加、修改、删除数据时,自动生成索引
HAYSTACK_SIGNAL_PROCESSOR = ‘haystack.signals.RealtimeSignalProcessor‘
 
在根级urls.py中添加搜索的配置
url(r‘^search/‘, include(‘haystack.urls‘)),
 
 
创建引擎及索引
  • 在项目目录下创建search_indexes.py文件
         
#coding=utf-8
          from haystack import indexes
          from models import GoodsInfo
          #指定对于某个类的某些数据建立索引
         
class GoodsInfoIndex(indexes.SearchIndex, indexes.Indexable):
                    text = indexes.CharField(document=True, use_template = True)
                    def get_model(self):
                            return GoddsInfo
                    def index_queryset(self, using=None):
                            return self.get_model().objects.all()
 
  • 在templates目录下创建“search/indexes/项目名/”目录
  • 在上面的目录中创建“goodsinfo_text.txt”文件
                #在文件中指定索引的属性
                 {{object.gcontent}}
                 {{.....}}
  • 找到虚拟环境py_django下的haystack目录
            /home/python/.virtualenvs/py3_django/lib/python3.6/site-packages/haystack/backends/
  • 在haystack目录中创建ChineseAnalyzer.py文件                
import jieba
from whoosh.analysis import Tokenizer, Token
 
class ChineseTokenizer(Tokenizer):
        def __call__(self, value, positions=False, chars=False,
                             keeporiginal=False, removestops=True,
                             start_pos=0, start_char=0, mode=‘‘, **kwargs):
                t = Token(positions, chars, removestops=removestops, mode=mode,
                                    **kwargs)
                seglist = jieba.cut(value, cut_all=True)
                for w in seglist:
                        t.original = t.text = w
                        t.boost = 1.0
                        if positions:
                                t.pos = start_pos + value.find(w)
                        if chars:
                                t.startchar = start_char + value.find(w)
                                t.endchar = start_char + value.find(w) + len(w)
                        yield t
 
def ChineseAnalyzer():
            return ChineseTokenizer()
 
 
  • 复制whoosh_backend.py文件,改为如下名称(注意:复制出来的文件名,末尾会有一个空格,记得要删除这个空格)
                whoosh_cn_backend.py
  • 打开复制出来的新文件,引入中文分析类,内部采用结巴分词
                from .ChineseAnalyzer import ChineseAnalyzer
  • 更改词语分析类
            查找 analyzer=StemmingAnalyzer() 改为 analyzer = ChineseAnalyzer()
  • 初始化索引数据
             在终端中执行 python manage.py rebuild_index 生成索引
  • 在views.py 中定义视图
from haystack.generic_views import SearchView
class MySearchView(SearchView):
    def get_context_data(self, *args, **kwargs):
        context = super().get_context_data(*args, **kwargs)
        return context
 
 
编辑搜索栏 并在templates/search/目录下创建search.html定义搜索页模板。
搜索结果进行分页,视图向模板中传递的上下文如下
  • query:搜索关键字
  • page:当前页的page对象(haystack内部做了一层封装page.object才代表当前对象)
  • paginator:分页paginator对象
  • 如果你要传其他的参数可以在试图中 给context填加键值对 如:context[‘键‘]=要传的内容
视图接收的参数如下:
  • 参数q表示搜索内容,传递到模板中的数据为query(注意要将输入框的名字改为 name=‘q‘)
  • 参数page表示当前页码
 
配置应用的url.py,添加search项
url(r‘^search/$‘, views.MysearchView.as_view(), name=‘search_view‘),
 
根据列表页的模板来制作搜素结果页的模板

以上是关于全文检索的主要内容,如果未能解决你的问题,请参考以下文章

PHP+MYSQL实现全文检索及全文检索工具

PostgreSQL 全文检索

lucene全文检索技术

全文检索

MySQL内置全文检索

全文检索 部署及使用