python - pickle 不可 pickle 的对象

标签 python pygame pickle save savestate

我正在用 pygame 制作一个绘图程序,我想在其中为用户提供一个选项来保存程序的确切状态,然后在稍后重新加载它。 在这一点上,我保存了我的全局字典的副本,然后遍历, pickle 每个对象。 pygame 中有一些对象不能被 pickle ,但可以转换成字符串并以这种方式 pickle 。我的代码已设置为执行此操作,但其中一些不可拾取的对象是通过引用获取的。换句话说,它们不在全局字典中,但它们被全局字典中的对象引用。我想在这个递归中 pickle 它们,但我不知道如何告诉 pickle 返回遇到问题的对象,更改它,然后再次尝试 pickle 它。我的代码真的很乱,如果有不同的、更好的方法来做我想做的事情,请告诉我。


surfaceStringHeader = 'PYGAME.SURFACE_CONVERTED:'
imageToStringFormat = 'RGBA'
def save_project(filename=None):
    assert filename != None, "Please specify path of project file"
    pickler = pickle.Pickler(file(filename,'w'))
    for key, value in globals().copy().iteritems():
        #There's a bit of a kludge statement here since I don't know how to 
        #access module type object directly
        if type(value) not in [type(sys),type(None)]   and \
        key not in ['__name__','value','key']          and \
        (key,value) not in pygame.__dict__.iteritems() and \
        (key,value) not in sys.__dict__.iteritems()    and \
        (key,value) not in pickle.__dict__.iteritems(): 
        #Perhaps I should add something to the above to reduce redundancy of
        #saving the program defaults?
            #Refromat unusable objects:
            if type(value)==pygame.Surface:
                valueString = pygame.image.tostring(value,imageToStringFormat)
                widthString = str(value.get_size()[0]).zfill(5)
                heightString = str(value.get_size()[1]).zfill(5)
                formattedValue = surfaceStringHeader+widthString+heightString+valueString
            else:
                formattedValue = value

            try:
                pickler.dump((key,formattedValue))
            except Exception as e:
                print key+':' + str(e)

def open_project(filename=None):
    assert filename != None, "Please specify path to project file"
    unpickler = pickle.Unpickler(file(filename,'r'))
    haventReachedEOF = False
    while haventReachedEOF:
        try:
            key,value = unpickler.load()
            #Rework the unpicklable objects stored 
            if type(value) == str and value[0:25]==surfaceStringHeader:
                value = pygame.image.frombuffer(value[36:],(int(value[26:31]),int(value[31:36])),imageToStringFormat)
            sys.modules['__main__'].__setattr__(key,value)
        except EOFError:
            haventReachedEOF = True

最佳答案

简而言之:不要这样做。

对应用程序中的所有内容进行 picking 是一件很麻烦的事情,而且很可能会导致问题。从您的程序中获取您需要的数据并以适当的数据格式手动存储它,然后通过从该数据创建您需要的东西来加载它。

关于python - pickle 不可 pickle 的对象,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13691185/

相关文章:

python - 如果我使用派生类,我可以 "pickle local objects"吗?

python - 如果两个字典的值/键对匹配,则用另一个字典的值替换列表对象字典值

python - 使用猫头鹰 :Class prefix with rdflib and xml serialization

python - 使用 python 多处理管道

python - “bool”对象不可调用

python - 在 pygame 中使用player.jump 玩家仅跳跃一次

python - 从空 pickle 文件中解泡 Python 字典时出现 EOFerror

Python -c bash swtich 换行符

python - AttributeError: 'pygame.math.Vector2' 对象没有属性

python - 将 python 对象写入磁盘而不加载到内存中?