如何在Google AppEngine上获取Python对象的字节大小?

7

我需要计算一些Python对象的大小,以便在不超过大小限制的情况下将它们分解并存储在memcache中。

在GAE环境中,'sizeof()' 似乎不存在于Python对象中,而sys.getsizeof()也无法使用。

GAE本身显然在幕后检查大小以强制执行限制。有什么想法可以完成这个任务吗?谢谢。

1个回答

14

memcache 内部总是使用 pickle 并存储结果字符串,因此您可以使用 len(pickle.dumps(yourobject, -1)) 进行检查。请注意,sys.getsizeof(需要2.6或更高版本,这就是为什么在GAE上缺失的原因)并不会真正帮助您:

>>> import sys
>>> sys.getsizeof(23)
12
>>> import pickle
>>> len(pickle.dumps(23, -1))
5

由于序列化pickle对象的大小可能与内存中的对象大小非常不同,正如您所看到的一样(所以我猜你应该感激GAE没有提供sizeof,这会让您误入歧途;-)。


感谢Alex提供的出色答案和解释。非常有道理。 - Dane
相关的是,使用pickle处理用户提供的数据是否安全? - Dane
1
@Dane,pickle.dump(和.dumps)是安全的,load回结果文件或字符串也是安全的。唯一可能不安全的部分是load一个用户提供的字节串,即一个你没有用pickle自己生成的字符串(无论是从文件中获取还是其他方式),而memcache并不会这样做;-)。 - Alex Martelli
不错,好知道。还有一个问题:pickle.dumps 中的 -1 参数是什么协议? - Dane
1
@Dane,-1表示“最佳可用(不受旧版Python兼容性约束)”--显然memcache不需要保持与旧版本的兼容性,因此它可以在运行的任何版本中使用“最新和最好的”(节省空间和/或时间,并可能允许序列化一些旧协议不支持的对象类型)。 - Alex Martelli
1
值得指出的是,腌制操作是一项昂贵的操作,仅为了确定长度而进行这样的操作可能是浪费。最好的做法是乐观地存储到内存缓存,并在如果数据过大时捕捉到异常。 - Nick Johnson

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接