I have the following situation (here a bit simplified):
class MyClass():
tables = dict
matrices = dict
def __init__(self, table_A, table_B=None, A=None, B=None)
self.tables = {'A': table_A, 'B': table_B}
self.matrices = {'A': A, 'B': B}
Now do not want my matrices to able to be set manually. Therefore my approach was to simply set them protected.
class MyClass():
tables = dict
_matrices = dict
def __init__(self, table_A, table_B=None, A=None, B=None)
self.tables = {'A': table_A, 'B': table_B}
self._matrices = {'A': A, 'B': B}
@property
def matrices(self):
# Getter function of the matrices attribute.
return self._matrices
@matrices.setter
def matrices(self, value):
raise AttributeError('The matrices of the model cannot be set manually!')
If I now initalize an instance myclass of the MyClass class it results in the following situation:
myclass.matrices = 3
(raises my AttributeError from the setter method - this is what I want)
myclass.matrices['A'] = 3
(no warning, just does what I wrote - I would like to avoid this!)
What should I do in a situation like this in your opinion?
I already thought of two workarounds:
extend my number of attributes, have single attributes for each former dict entry (_matrix_A, _matrix_B) and loose the advantage of the stucture given by the dict.
write an additional class MatrixClass and amending my base class MyClass
_A = np.Array
_B = np.Array
def __init__(self, A, B):
self._A = A
self._B = B
@property
def A(self):
# Getter function of the A attribute.
return self._A
@A.setter
def A(self, dictionary):
raise AttributeError('The matrix A cannot be set manually.')
class MyClass():
tables = dict
_matrices = MatrixClass
def __init__(self, table_A, table_B=None, A=None, B=None)
self.tables = {'A': table_A, 'B': table_B}
self._matrices = MatrixClass(A, B)
@property
def matrices(self):
# Getter function of the matrices attribute.
return self._matrices
@matrices.setter
def matrices(self, value):
raise AttributeError('The matrices of the model cannot be set manually!')```
What would you recommend to be a kind of pretty solution to this? Thank you!
You could use the library frozendict
which provides a immutable dictionnary. I would have done something like this :
pip install frozendict
from frozendict import frozendict
class MyClass():
def __init__(self, A=None, B=None):
self._matrices = frozendict({'A': A, 'B': B})
@property
def matrices(self):
# Getter function of the matrices attribute.
return self._matrices
@matrices.setter
def matrices(self, value):
raise AttributeError('The matrices of the model cannot be set manually!')
Then, if I try to change the value of key A
in matrices
, like :
c = MyClass()
c.matrices["A"] = 2
... an error will be raised:
TypeError: 'frozendict' object doesn't support item assignment