Zhu*_*Tao 2 python database serialization
如果我们有一些应该存储在DB中的代码(数据结构),有人总是建议我们存储序列化数据而不是原始代码字符串.
所以我不太清楚为什么我们应该更喜欢序列化数据.
给一个简单的实例(在python中):
我们有一个字段可以存储python的字典,就像
{ "name" : "BMW", "category":"car", "cost" : "200000"}
Run Code Online (Sandbox Code Playgroud)
所以我们可以使用pickle(python模块)对其进行序列化,然后将pickle数据存储到db字段.
或者我们可以直接将dict字符串存储到DB而无需序列化.
由于我们需要将字符串转换为python数据,因此通过分别使用pickle.loads和exec,两种方法都很容易实现.
那应该是首选的?为什么?是因为exec比pickle慢得多吗?还是其他一些原因?
谢谢.
Ale*_*lli 11
或者我们可以直接将dict字符串存储到DB而无需序列化.
没有"dict字符串"这样的东西.有很多方法可以将字典序列化为字符串; 你可能会想到repr
,可能就像eval
恢复字典一样(你提到exec
,但这简直荒谬:你会执行什么声明......?我认为你可能意味着eval
).它们是不同的序列化方法及其权衡,在许多情况下,权衡往往倾向于酸洗(cPickle
对于速度,协议-1
意味着"你能做的最好",通常).
性能肯定是一个问题,例如,在您存储的大小方面......:
$ python -c 'import cPickle; d=dict.fromkeys(range(99), "banana"); print len(repr(d))'
1376
$ python -c 'import cPickle; d=dict.fromkeys(range(99), "banana"); print len(cPickle.dumps(d,-1))'
412
Run Code Online (Sandbox Code Playgroud)
...为什么每次序列化像这样的字典时,你想要存储1.4 KB而不是0.4 KB? - - )
编辑:因为有人建议Json,值得指出的是,json在这里需要1574个字节 - 比笨重的repr更笨!
至于速度......
$ python -mtimeit -s'import cPickle; d=dict.fromkeys(range(99), "chocolate")' 'eval(repr(d))'
1000 loops, best of 3: 706 usec per loop
$ python -mtimeit -s'import cPickle; d=dict.fromkeys(range(99), "chocolate")' 'cPickle.loads(cPickle.dumps(d, -1))'
10000 loops, best of 3: 70.2 usec per loop
Run Code Online (Sandbox Code Playgroud)
...为什么要花10倍的时间?支付这么高的价格有什么好处呢?
编辑:json需要2.7 毫秒 - 比cPickle慢近四十倍.
然后有一般性 - 并不是每个可序列化的对象都可以使用repr和eval正确地进行往返,而酸洗则更为通用.例如:
$ python -c'def f(): pass
d={23:f}
print d == eval(repr(d))'
Traceback (most recent call last):
File "<string>", line 3, in <module>
File "<string>", line 1
{23: <function f at 0x241970>}
^
SyntaxError: invalid syntax
Run Code Online (Sandbox Code Playgroud)
VS
$ python -c'import cPickle
def f(): pass
d={"x":f}
print d == cPickle.loads(cPickle.dumps(d, -1))'
True
Run Code Online (Sandbox Code Playgroud)
编辑:在往返方面,json甚至不如repr.
因此,比较两种序列化方法(酸洗与repr/eval),我们看到:酸洗方式更为通用,它可以提高10倍,并占用数据库中3倍的空间.
您为repr/eval设想了哪些补偿优势?
顺便说一下,我看到一些答案提到了安全性,但这不是一个真正的观点:酸洗也是不安全的(eval不可信任字符串的安全问题可能更明显,但是对不可信任的字符串进行破坏也是不安全的,尽管以更微妙和更暗的方式).
编辑:json更安全.这是否值得在规模,速度和普遍性方面付出巨大代价,这是一个值得深思的权衡.在大多数情况下,它不会.
归档时间: |
|
查看次数: |
3614 次 |
最近记录: |