我知道全文搜索应用程序,如Django Solr和solango等。
我正在寻找的内容更类似于对房地产网站的高级搜索。 例如,他们可以选择类似于www.viewr.com高级搜索的位置,价格等。
到目前为止,我所做的是在模型自定义管理器下:
def advanced_search(self, district, location, type, facilities, features, not_permitted):
q_objects = []
l_objects = []
t_objects = []
fc_objects = []
ft_objects = []
np_objects = []
if district:
if location:
for loc in location:
l_objects.append(Q(location__exact=loc))
else:
l_objects.append(Q(location__district=district))
if type:
for ty in type:
t_objects.append(Q(listing_type__exact=ty))
if facilities:
for fc in facilities:
fc_objects.append(Q(property_facilities__exact=fc))
if features:
for ft in features:
ft_objects.append(Q(property_features__exact=ft))
ft_objects.append(Q(community_features__exact=ft))
if not_permitted:
for np in not_permitted:
np_objects.append(Q(not_permitted__exact=np))
# Start with a bare QuerySet
qs = self.get_query_set()
if location:
qs = qs.filter(reduce(operator.or_, l_objects))
if type:
qs = qs.filter(reduce(operator.or_, t_objects))
if facilities:
qs = qs.filter(reduce(operator.or_, fc_objects))
if features:
qs = qs.filter(reduce(operator.or_, ft_objects))
if not_permitted:
qs = qs.filter(reduce(operator.or_, np_objects))
# Use operator's or_ to string together all of your Q objects.
return qs
现在我没有得到非常可预测的结果。有什么我可能做错了吗?有没有更好的方法来进行各种OR搜索/连接?
答案 0 :(得分:2)
只是一些想法。
在这种情况下,使用kwargs解包为过滤方法提供参数非常有用。 这样的事情可以使代码更简单:
kwargs = {'not_permitted':np,'property_features': ft}
return qs.filter(**kwargs)
也许您应该在admin中查看django的过滤代码。在django中,管理员参数如not_permitted__exact
通过GET传递。然后,经过一些过滤后,整个GET字典可以作为解包的kwargs参数传递给filter方法。当你有很多过滤选项时,这会让事情变得非常简单。
答案 1 :(得分:2)
我最接近这种情况的是雅各布的这篇文章:
http://www.djangosnippets.org/snippets/32/
我所做的是:
def advanced_search(self, form):
# It's easier to store a dict of the possible lookups we want, where
# the values are the keyword arguments for the actual query.
qdict = {'district': 'location__district',
'location': 'location',
'property_type': 'listing_type',
'max_price': 'price__lte',
'property_features': 'property_features',
'community_features': 'community_features',
}
# Then we can do this all in one step instead of needing to call
# 'filter' and deal with intermediate data structures.
q_objs = [Q(**{qdict[k]: form.cleaned_data[k]}) for k in qdict.keys() if form.cleaned_data.get(k, None)]
search_results = RealEstateListing.objects.select_related().filter(*q_objs)
return search_results
当我通过单一选择时,它工作正常,但是当通过多个选择时,它会扼杀并说:
OperationalError:子查询返回多行
答案 2 :(得分:1)
http://code.google.com/p/djapian/可以为您选择的字段编制索引,并允许您通过组合,布尔逻辑等构建复杂的搜索。
答案 3 :(得分:0)
我知道这篇文章有些陈旧,但是我碰到了这一点,我认为在寻求简单快速的解决方案时其他人可能会这么做
not