【问题标题】:Is there an effcient way to perform search query in django?有没有一种在 django 中执行搜索查询的有效方法?
【发布时间】:2019-07-05 08:16:11
【问题描述】:

我正在创建一个博客,我想在其中执行基于评分 (1-5) 的搜索查询。在这里,我的搜索类似于查询:“智能手机技术更新”,评级:“3”。结果应该是包含评分为 3 的查询词(至少一个词)的帖子列表,以 val 上的排序方式(对于每个查询词,如果在标题中找到 val+=1,如果在内容中找到 val+=0.4)。

我的 models.py 文件有以下内容:

class Post(models.Model):
    title = models.CharField(max_length=50)
    content = models.CharField(max_length=500)
    rating = models.IntegerField(default=1)
    enter code here
    date = models.DateTimeField(default=timezone.now)
    author = models.ForeignKey(User, on_delete=models.CASCADE)

我的 view.py 文件有以下内容:

def search(request):
    contents = Post.objects.all()

    if request.method == 'GET':
        query = request.GET['query']
        rating = request.GET['rating']

        # search function

        # contents = InSearch.search_fun(contents,query,rating)
        vector = SearchVector('title', weight='A') + SearchVector('content', weight='B')
        qry = SearchQuery(str(query))
        contents = Post.objects.annotate(rank=SearchRank(vector, qry)).order_by('-rank')

        #print("---->\n\t"+query+ str(contents))

        context = {
            'contents': contents
        }
    else:
        context = {
            'contents': Post.objects.all()
        }

    return render(request, 'feed/home.html', context)

我的 urls.py 是:

urlpatterns = [
    #...
    path('feed/search-result/', views.search, name='feed_search'),
]

我收到此错误 django.db.utils.OperationalError: no such function: plainto_tsquery

【问题讨论】:

  • 你为什么要在 sqlite 中使用 Postgres 函数?
  • 我在 Django 文档中找到了该搜索查询。正如你所说,它是 postgers db 函数,我正在使用 sqlite。有没有办法通过 django 模型或 sqlite 查询得到我想要的东西

标签: python django sqlite search


【解决方案1】:

您可以在视图中尝试这样进行搜索。

from django.db.models import Q
def search(request):
 q = request.GET.get('q')
    if q:
       search_results = Post.objects.filter(Q(title__icontains=q)|Q(rating=q))
   # if you want the exact then do Post.objects.filter(Q(title__iexact=q) & Q(rating=q))

       return render(request, 'feed/home.html','search_results':search_results)
    else:
        messages.info(request,'no results found for {}',format(q))

如果您想按匹配数对搜索查询结果进行排序,那么您可以这样尝试:

search_results = Post.objects.filter(Q(title__icontains=q)|Q(rating=q)).annotate(title_counts=Count('title')).order_by('-title_counts')

并在您的模板中在搜索表单中提供name='q'

 <form  action="{% url 'your search action' %}">
     <input type="text" name="q">
     <input type='submit' value='Search'>
   </form>

【讨论】:

  • 差不多,但是rating 是一个 IntegerField 并且不支持icontains。只需Q(title__icontains=q)|Q(rating=q) 即可。
  • 这不是我要问的。您的答案返回完全匹配的查询。
  • 就问题而言,如果我搜索“智能手机技术更新”,它将仅返回具有相同顺序的帖子或标题包含“智能手机技术更新”的行。但不是具有智能或电话或技术或...的帖子,它也不对数据进行排序,也不返回增值字段以明确排序。
  • 你想如何对数据进行排序?如果你想要确切的结果,那么你可以做title__iexact=q
  • 我想对匹配最大的结果进行排序。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2023-03-07
  • 2018-01-27
  • 1970-01-01
  • 2018-06-02
  • 1970-01-01
相关资源
最近更新 更多