Django BinaryField检索为内存位置?

时间:2015-12-13 18:06:21

标签: python django database python-3.x binary

我用以下代码编写了一个简短的单元测试:

my_object = MyObject()
my_object.data = b'12345'

my_object.save()
saved_object = MyObject.objects.first()

assert saved_object.data == my_object.data

其中MyObject定义为:

class MyObject(models.Model):
    data = models.BinaryField(default=None)

我希望断言传递,因为我只是保存一些字节数据然后检索它。但是,我最终得到了:

AssertionError: assert <memory at 0x10e2abc48> == b'12345'

我猜这与直接将字节串保存到二进制字段有关。另一方面,保存成功后似乎很奇怪。而且我有点难以找到Django的BinaryField的一些很好的例子用法。任何人都可以向我解释这里发生了什么或者我做错了什么?非常感谢。

1 个答案:

答案 0 :(得分:4)

Django将BinaryField的内容规范化为缓冲区。在Python2中,Python3中的buffermemoryview是特定的。

您可以在源代码中看到:

在Python2 buffer中没有实现比较逻辑,这就是你的断言失败的原因:

Python 2.7.11
>>> m = buffer(b'hello')
>>> m == b'hello'
False
>>> bytes(m) == b'hello'
True

然而,它确实实现了切片和长度等其他操作:

>>> len(m)
5
>>> m[1:]
'ello'

在Python 3中,故事要好得多,因为它实现了所有预期的操作:

Python 3.5.1
>>> m = memoryview(b'hello')
>>> m
<memory at 0x109e8b108>
>>> bytes(m)
b'hello'
>>> m == b'hello'
True
>>> bytes(m) == b'hello'
True
>>> len(m)
5
>>> m[1:]
<memory at 0x109e8b1c8>

我不确定Django之所以这样做,但我的猜测是效率。缓冲区在处理内存方面效率更高。例如,当您进行切片时,它可以重用相同的内存,而不是分配更多的内存。

相关问题