Django/Python 在获取缓存结果后进行排序

发布于 2024-11-09 06:54:27 字数 704 浏览 0 评论 0原文

您好,

一些快速的事情(django 1.2.3、python 2.6、memcached)。

我有一个函数,我首先执行一个有点昂贵的查询,当我执行此查询时,我执行 order_by。然后我更新一些可能会改变结果顺序的值。然后我将所有值放入缓存中。

然后在另一个函数中,我获取缓存,并想重新使用结果,以便它们再次按顺序排列。

所以这会是这样的。

function 1():
    mylist = myevent.people.order_by('-score')
    ....do up date....
    cache.set(cache_key,mylist)

function(2):
    my_cache_list = cache.get(cache_key)
    newlist = sorted(my_cache_list,key=operator.attrgetter('score'), reverse=True )

根据其他帖子,我认为这应该可行,但我收到一个类型错误,指出 my_cache_list 不可订阅。

有人有什么想法吗?我可能做了一些愚蠢的事情......

谢谢。

注意:更新将operator.attrgetter更改为operator.itemgetter,删除了错误!上面这段代码确实有效。问题在于使用operator.itemgetter。

Greetings,

A few quick things (django 1.2.3, python 2.6, memcached).

I have a function where I first do a somewhat expensive query, when I do this query I do an oder_by. I then update some values which may change the order of the results. I then put all of the values in the cache.

Then in another function I get the cache and I want to resort the results so that they are again in order.

so this would be something like.

function 1():
    mylist = myevent.people.order_by('-score')
    ....do up date....
    cache.set(cache_key,mylist)

function(2):
    my_cache_list = cache.get(cache_key)
    newlist = sorted(my_cache_list,key=operator.attrgetter('score'), reverse=True )

based on other posts I would think this should work but I get a typeerror saying that my_cache_list is unsubsriptable.

Anyone have any ideas? Im probably doing something stupid....

thanks.

NOTE: Update made change operator.attrgetter for operator.itemgetter removed error! This code above does work. The problem was in using the operator.itemgetter.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

撞了怀 2024-11-16 06:54:27

Python 函数 sorted() 适用于可变列表类型,而 Django 查询集则不然:这就是您收到的错误基本上告诉您的内容。从技术上讲,下标是通过索引访问列表元素的行为,如下所示:

list = ['a', 'b', 'c']
list[0] # This is a subscript

如果您在查询集上尝试这样做,它将失败并出现相同的异常:

list = MyModel.objects.all()
list[0] # This subscript will fail: a queryset doesn't support the operation

如果您想保留加载有序查询集的方案,请缓存结果并在缓存访问时对它们重新排序,您必须将查询集转换为真实列表并将其存储在缓存中(但这将占用更多的缓存空间)。在你的函数1中:

qs = myevent.people.order_by('-score')
mylist = list(qs.all())
....do up date....
cache.set(cache_key, mylist)

The Python function sorted() works with Mutable List Types, which a Django queryset is not: this is what the error you're getting is basically telling you. Technically, subscripting is the act of accessing a list element by its index, like this:

list = ['a', 'b', 'c']
list[0] # This is a subscript

If you try that on a queryset, it will fail with the same exception you got:

list = MyModel.objects.all()
list[0] # This subscript will fail: a queryset doesn't support the operation

If you want to keep your scheme of loading an ordered queryset, caching the results and reordering them on cache access, you will have to turn your queryset into a real list and store that in cache (this will take a lot more cache space, though). In your function 1:

qs = myevent.people.order_by('-score')
mylist = list(qs.all())
....do up date....
cache.set(cache_key, mylist)
南汐寒笙箫 2024-11-16 06:54:27

从您的示例代码中跳出一件事。您似乎将缓存视为可靠的数据存储。你永远不应该假设缓存会返回一个值。

当您收到 TypeError 时,my_cache_list 可能为 None,这意味着未找到缓存键。您应该始终测试 None 值并重新生成该值。

当您使用支持的内存缓存时,您需要记住,您只能存储最大 1MB 的值。大于此值的值将被默默丢弃。

There is one thing that jumps out from your example code. You seem to be treating your cache as a reliable datastore. You should never assume that the cache will return a value.

my_cache_list is probably None when you're getting the TypeError, which means that the cache key was not found. You should always test for a None value and regenerate the value.

As you're using the memcache backened you need to remember that you can only store values up to 1MB in size. Values larger than this are silently discarded.

画▽骨i 2024-11-16 06:54:27

在将列表设置到缓存中之前尝试对其进行腌制:

import cPickle as pickle

cache.set(pickle.dumps(mylist))


function(2):
    my_cache_list = cache.get(cache_key)
    newlist = sorted(pickle.loads(my_cache_list),key=operator.itemgetter('score'), reverse=True )

try to pickle your list before you set it in cache:

import cPickle as pickle

cache.set(pickle.dumps(mylist))


function(2):
    my_cache_list = cache.get(cache_key)
    newlist = sorted(pickle.loads(my_cache_list),key=operator.itemgetter('score'), reverse=True )
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文