简体   繁体   中英

i dump a self-define class object by pickle,but sometimes i can not load it back

i build a toy distributed DB. the transaction of this db is like this:

class Handle(object):
def __init__(self,fragment_no,table,key,data):
    self.fragment_no=fragment_no
    self.data=data
    self.table=table
    self.key=key
def __setstate__(self,state):
    self.fragment_no,self.table,self.key,self.data=state
def __getstate__(self):
    return (self.fragment_no,self.table,self.key,self.data)
class Transaction(object):
def __init__(self,fragment_no,t_id,tran_type="a"):
    self.t_id=t_id
    self.fragment_no=fragment_no
    self.t_handles=[]
    self.checksum=""
    self.tran_type=tran_type
def add_handle(self,handle):
    self.t_handles.append(handle)
def compute_checksum(self):
    self.checksum=""
def test_checksum(self):
    return True
def is_valiad(self):
    pass
def __setstate__(self,state):
    self.t_id,self.t_handles,self.fragment_no,self.tran_type,self.checksum=state
def __getstate__(self):
    return (self.t_id,self.t_handles,self.fragment_no,self.tran_type,self.checksum)
class RemoteTransaction(Transaction):
"""
state consist of:
    cordinator:begin,ask,commit(abort),end
    particapant:begin,replayed,end
"""
def __init__(self,dbt_id,fragment_no=0,t_id=0,tran_type="a"):
    Transaction.__init__(self, fragment_no, t_id, tran_type)
    self.state="begin"
    self.dbt_id=dbt_id
def set_data(self,fragment_no,t_id):
    self.fragment_no=fragment_no
    self.t_id=t_id
def __setstate__(self,state):
    self.state,self.dbt_id,self.t_id,self.t_handles,self.fragment_no,self.tran_type,self.checksum=state
def __getstate__(self):
    return (self.state,self.dbt_id,self.t_id,self.t_handles,self.fragment_no,self.tran_type,self.checksum)    

and at the commit part the code is

f=open("./"+str(self.port)+"/database/"+str(tran.fragment_no)+"/journal/"+str(tran.t_id),"wb")
pickle.dump(tran,f)
f.close()
file=open("./"+str(self.port)+"/database/"+str(tran.fragment_no)+"/journal/"+str(tran.t_id),'rb')
c=pickle.load(file)

sometimes this code work. but when the transaction has two handle this part of code may break here is the state of transaction when it breakdown,(i use print(tran. getstate () func)):

(1, [<Journal.transaction.Handle object at 0x03D3F7D0>, <Journal.transaction.Handle object at 0x03D3F950>], 1, 'a', '')

the error is that: faultString: str: :state is not a dictionary

Your __getstate__ method is returning a tuple, not a dictionary. That is most likely your issue here. While you can have a custom __getstate__ and __setstate__ which use a tuple, by default Python uses dictionaries for the state (specifically, it returns self.__dict__ ).

So if you have older objects pickled (before your __getstate__ ) they would have stored __dict__ instead of your tuple.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM