酸洗相互引用的物体

时间:2014-10-02 17:58:39

标签: python pickle

我有三个Python类,StudentEventStudentEvent

为简单起见:

class Student:
    def __init__(self, id):
        self.id = id

class Event:
    def __init__(self, id):
       self.id = id
       self.studentevents = []

class StudentEvent:
    def __init__(self, student, event, id):
        self.student = student
        self.event = event
        self.id = id

我有几千到几百万个这些类的实例,我把它放到我可以阅读和分析的词典中。阅读和创建对象需要花费大量时间,因此我想将它们分成3个词典,students_dictevents_dictstudentevents_dict

所以,很好,我可以做到。但是,如果我以后取消词典,studentevents_dict中的学生和事件将不会引用Students中的Eventsstudents_dictevents_dict,对吗?

如果我稍后修改对象,例如,填充StudentEvents对象中关联的Event列表,那可能会有问题,因为StudentEvent引用的事件不会是Event中具有相同ID的events_dict

1 个答案:

答案 0 :(得分:2)

正确。如果你需要保留对象之间的指针关系,你必须在一个元组中将它们一起腌制。在这里,我使用dill代替pickle,但效果应该相同。这适用于类实例(如图所示),dicts或其他。

>>> class A:
...   def __init__(self, b):
...     self.b = b
... 
>>> class B:
...   pass
... 
>>> import dill
>>>           
>>> b = B()
>>> a = A(b)
>>> 
>>> f = open('_sed', 'wb')
>>> dill.dump(({1:a},{2:b}), f)
>>> f.close()

然后......

Python 2.7.8 (default, Jul 13 2014, 02:29:54) 
[GCC 4.2.1 Compatible Apple Clang 4.1 ((tags/Apple/clang-421.11.66))] on darwin
Type "help", "copyright", "credits" or "license" for more information.
>>> import dill
>>> f = open('_sed', 'rb')
>>> t = dill.load(f)
>>> f.close()
>>> t
({1: <__main__.A instance at 0x10906a440>}, {2: <__main__.B instance at 0x10906a830>})
>>> t[0][1].b
<__main__.B instance at 0x10906a830>