Ich versuche, einen Weg zu finden, dict
Werte in ein class
eingekapselt zu setzen, zum Beispiel __getattr__
ich mit dem internen dict
Wert zurückgeben kann jedoch die __setattr__
auch genannt wird, wenn Attribute vorhanden ist, meine Implementierung hässlich machen. Das folgende Beispiel ist vereinfacht meine eigentliche Klasse erbt von einem Subject
class
(dem Thema des Beobachter Muster)Gegenstück von __getattr__
ich so etwas wie dies zu erreichen versuchen:
obj = Example()
obj.username = 'spidername' # all OK username is a key in the internal dict
# but company is not a key in the internal dict so
obj.company = 'ABC' # will raise AttributeError
, und ich fragen, ob es eine ist besserer Weg, als die Art, wie ich unten tue:
class Example(object):
def __init__(self, table=None):
self._fields = {}
self._table = table
def _set_fields(self):
"""
this method will be implemented by
subclasses and used to set fields names and values
i.e.
self._field['username'] = Field(default='unknown', is_primary=False)
"""
raise NotImplementedError
def __getattr__(self, name):
"""
great this method is only called when "name"
is not an attribute of this class
"""
if name in self._fields:
return self._fields[name].value
return None
def __setattr__(self, name, value):
"""
not so great, this method is called even for
attributes that exists in this class
is there a better way to do the following?
this can be in __init__, but its still ugly
"""
attribs = ['_fields', '_table']
if name in attribs:
super(Example, self).__setattr__(name, value)
else:
if name in self._fields:
self._fields[name].value = value
else:
raise AttributeError
EDIT: angepasst Kommentar in Code, missin Anführungszeichen hinzugefügt
Eine Nebenbemerkung: Es gibt bereits viele gute Python-Bibliotheken für die Object Relational Mapping (ORM), zum Beispiel SQLAlchemy; wenn das das ist, was du versuchst zu tun. –
danke, ja ich weiß, es gibt auch Storm und SQLObject, die ich kenne. aber ich mag etwas einfacher und das ist mein eigenes. – andrea