I want to create a 'mini-database'. I want to have one file with lots of variables, and be able to take those variables from the file, while also being able to add variables to the file? For example, lets suppose this is the 'mini-db':
hello = ['a', 'b', 'c']
world = ['d', 'e', 'f']
foo = ['g', 'h', 'i']
and from a different file, I would like to say something like:
print MiniDB.hello[0]
So basically access the variable. Also, I would need to write variables INTO the file. so something like this:
MiniDB.bar = ['j', 'k', 'l']
How can I do this?
shelve
is the easiest way to do this. Mind the concurrency restrictions though.
This may not be what you are looking for, but this class allows storing program settings. You load it with default settings that represent the variables you need and embed dictionaries to generate namespaces. It is not perfect, but tries to allow multiple database definitions to coexist with each other while ensuring data types do not change. It has a limited field of usage but may act as the solution you require.
import copy
import pprint
import pickle
################################################################################
class _Interface:
def __init__(self, default, database=None):
self.__default = default
if database is None:
self.__database = copy.deepcopy(default)
else:
self.__database = database
def __repr__(self):
return pprint.pformat(self.__database)
def __getattr__(self, name):
attr = self.__default[name]
if isinstance(attr, dict):
return _Interface(attr, self.__database[name])
raise AttributeError(name)
def __setattr__(self, name, value):
if name in {'_Interface__default', '_Interface__database'}:
super().__setattr__(name, value)
else:
raise AttributeError(name)
def __getitem__(self, name):
item = self.__default[name]
if isinstance(item, dict):
raise KeyError(name)
return self.__database[name]
def __setitem__(self, name, value):
item = self.__default[name]
if isinstance(value, type(item)):
self.__database[name] = value
else:
raise TypeError(type(value))
################################################################################
class Registry(_Interface):
@property
def __database(self):
return self._Interface__database
def load(self, path):
with open(path, 'rb') as file:
data = pickle.load(file)
self.__merge(data, self.__database)
@classmethod
def __merge(cls, source, sink):
for key, value in source.items():
if key not in sink:
sink[key] = value
elif isinstance(value, type(sink[key])):
if isinstance(value, dict):
cls.__merge(value, sink[key])
else:
sink[key] = value
def save(self, path):
with open(path, 'wb') as file:
pickle.dump(self.__database, file)
################################################################################
file1 = Registry({'hello': ['a', 'b', 'c'],
'world': ['d', 'e', 'f'],
'foo': ['g', 'h', 'i'],
'namespace': {'j': 0,
'k': 1,
'm': '2',
'n': '3'}})
file2 = Registry({'hello': ['a', 'b', 'c'],
'world': ['d', 'e', 'f'],
'foo': ['g', 'h', 'i'],
'namespace': {'j': '4',
'k': '5',
'm': '6',
'n': '7'},
'bar': []})
file1['hello'][0] = 'z'
file1.save('mini.db')
file2.load('mini.db')
file2['bar'].extend(['j', 'k', 'l'])
print(file2)
print(file2.namespace['k'])
print(file2.namespace['m'])
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.