使用列表查询并保持列表顺序的最佳方法是什么?

时间:2014-04-09 22:50:59

标签: django

我在网上搜索过,只能找到一个看起来像是试图保持查询列表顺序的hackish的博客。我希望使用ORM查询字符串列表,但这样做不会保持列表的顺序。

据我所知,只有拥有要查询的项目的ID时,bulk_query才有效。

有人能推荐一种理想的查询字符串列表并确保对象保持正确顺序吗?

所以在一个完美的世界里,我可以通过做这样的事情来查询一组对象......

Entry.objects.filter(id__in=['list', 'of', 'strings'])

但是,他们没有保持秩序,所以字符串可以在列表之前等...

我看到的唯一的工作,我可能只是累了,或者这可能完全可以接受我不确定是这样做的......

for i in listOfStrings:
    object = Object.objects.get(title=str(i))
    myIterableCorrectOrderedList.append(object)

谢谢,

2 个答案:

答案 0 :(得分:3)

您的解决方案的问题在于它为每个项目执行单独的数据库查询。

如果您使用ids

This answer会提供正确的解决方案:使用in_bulk在ID和商品之间创建地图,然后根据需要重新排序。

如果你没有使用ids,你可以自己创建映射:

values = ['list', 'of', 'strings']

# one database query
entries = Entry.objects.filter(field__in=values)

# one trip through the list to create the mapping
entry_map = {entry.field: entry for entry in entries}

# one more trip through the list to build the ordered entries
ordered_entries = [entry_map[value] for value in values]

(您可以使用index使用index保存一行,但由于{{1}}为O(n),因此效果不会对长列表有效。)< / p>

答案 1 :(得分:2)

请记住,最终这一切都是对数据库完成的;这些操作在某处被转换为SQL。

你的Django查询松散地翻译成SQL就像是:

SELECT * FROM entry_table e WHERE e.title IN ("list", "of", "strings");

因此,在某种程度上,您的问题等同于询问如何ORDER BYWHERE子句中指定了某些内容。 (不用说,我希望,这是一个用SQL编写的令人困惑的请求 - 而不是它被设计为使用的方式。)

您可以通过多种方式执行此操作,如StackOverflow [1] [2]上的其他一些答案中所述。但是,正如您所看到的,两者都依赖向数据库添加(临时)信息以对选择进行排序。

实际上,这应该建议正确的答案:您要排序的信息应该在您的数据库中。或者,回到高级Django-land,它应该在你的模型中。当用户添加收藏夹时,请考虑将模型修改为save a timestampan ordering,如果这是您要保留的内容。

否则,您将陷入其中一个解决方案,这些解决方案要么从数据库中获取无序数据,然后在Python中“修复”它,要么构建自己的SQL查询并从我链接的解决方案之一实现您自己的丑陋黑客攻击(不要这样做)。

  

tl; dr “正确”的答案是保持数据库中的排序顺序; “快速修复”是按照您的喜好从数据库中按下未分类的数据。

编辑:显然MySQL has some weird feature可以让你这样做,如果这恰好是你的后端。