If you have a big dictionary, you may not want to have
to load the whole thing to get access to modify a key.
Metakit provides an easy solution to this, if you use
it to emulate a dictionary.
import meta_dict
file='test_dict.mk'
a_dict={'a':'b',1:2}
print 'starting with'
for i in a_dict:
print i,a_dict[i]
#convert dictionary to a meta_kit based dictionary
meta_dict.meta_save(a_dict,file)
#write to meta_kit based dictionary
m_dict=meta_dict.meta_load(file=file,write=1)
#change a member
m_dict[1]=5
#add a member
m_dict['c']='d'
#end writing
m_dict.close()
#read-only metakit based dictionary
m2_dict=meta_dict.meta_load(file=file)
print 'ending with'
for i in m2_dict:
print i,m2_dict[i]
_________________
Gives you output:
starting with
a b
1 2
ending with
a b
1 5
c d
#meta_dict.py -- version 0.1 John Nielsen
from __future__ import generators
import metakit,marshal,time
#in place update
#make copy of most current data, lock it
#update pieces
class meta_load:
def __init__(self,file='',tbl='',write=''):
if not tbl: tbl='table0'
if write:
self.db = metakit.storage(file,1)
self.tbl=self.db.getas('%s[k:S,v:B]'%(tbl))
else:
self.db = metakit.storage(file,0)
self.tbl=self.db.view(tbl)
self._set_keys()
def _set_keys(self):
self.cur_dict={}
#get "keys"
loc=0
for i in self.tbl:
self.cur_dict[i.k]=loc
loc+=1
def close(self):
self.db.commit()
self.db = None
def has_key(self, k):
return k in self.cur_dict
def keys(self):
return self.cur_dict.keys()
def get(self,key,default=None):
try:
return self.__getitem__(key)
except:
return default
def items(self):
return list(self.iteritems())
def values(self):
return list(self.itervalues())
def __len__(self):
return len(self.cur_dict.keys())
def __getitem__(self,k):
'''import to define'''
if k in self.cur_dict:
#row_num=self.tbl.find(k=k)
row_num=self.cur_dict[k]
return marshal.loads(self.tbl[row_num].v)
else:
raise KeyError, k
def iterkeys(self):
for key in self.keys():
yield key
def __iter__(self):
return self.iterkeys()
def iteritems(self):
# yield children
for k in self.iterkeys():
v=self.__getitem__(k)
yield (k,v)
def __repr__(self):
return '{meta dict}'
def __str__(self):
return self.__repr__()
def setdefault(self,key,default=None):
try:
return self.__getitem__(key)
except:
self.__setitem__(key)
return default
def update(self,d):
for k,v in d.items():
self.__setitem__(k, v)
def popitem(self):
try:
k, v = self.iteritems().next()
del self[k]
return k, v
except StopIteration:
raise KeyError, "meta_dict is empty"
def __setitem__(self, k, v):
if k in self.cur_dict:
row_num=self.cur_dict[k]
self.tbl[row_num].v=marshal.dumps(v)
else:
self.tbl.append(k=str(k),
v=marshal.dumps(v))
#reload keys into memory
self._set_keys()
def __delitem__(self, key):
raise NotImplementedError
def __hash__(self):
raise TypeError, "meta_dict is unhashable"
def meta_save(data,file,tbl=''):
if not tbl: tbl='table0'
db = metakit.storage(file,1)
tbl = db.getas('%s[k:S,v:B]'%(tbl))
for k in data:
tbl.append(k=str(k),v=marshal.dumps(data[k]))
db.commit()
if __name__=='__main__':
file='test_dict.mk'
#convert dictionary to a meta_kit based dictionary
a_dict={'a':'b',1:2}
meta_save(a_dict,file)
#write to meta_kit based dictionary
m_dict=meta_load(file=file,write=1)
#change a member
m_dict[1]=5
#add a member
m_dict['c']='d'
m_dict.close()
#read metakit based dictionary
m2_dict=meta_load(file=file)
for i in m2_dict:
print i,m2_dict[i]
__________________________________
Do you Yahoo!?
New Yahoo! Photos - easier uploading and sharing.
http://photos.yahoo.com/
_____________________________________________
Metakit mailing list - [EMAIL PROTECTED]
http://www.equi4.com/mailman/listinfo/metakit