MATLAB: Is calling a superclass constructor after a use of the object not allowed

classclass treeconstructordesignobject-orientedoodoopsubclasssuperclasssuperclass constructor

I have a subclass "subclass" of two classes "classA" and "classB", which are in turn subclasses of "superclass". Here is the class tree:
The superclass has two properties x and y. The classes "classA" and "classB" each do something special to initialize x and y, respectively. Then I want "subclass" to call both the "classA" and "classB" constructors to initialize x and y simultaneously. But the way the classes are built, I run into a snag.
Here are the definitions of the classes:
superclass.m:
classdef superclass
%% PROPERTIES
properties
x;
y;
end
%% METHODS
methods
function obj = superclass(x,y)
% Initialize the properties
obj.x = x;
obj.y = y;
end
end
end
classA.m:
classdef classA < superclass
%% PROPERTIES
properties
a;
end
%% METHODS
methods
% Constructor


function obj = classA(a,y,z)
x = a*z;
obj@superclass(x,y);
obj.a = a;
obj.z = z;
end
end
end
classB.m:
classdef classB < superclass
%% PROPERTIES
properties
b;
end
%% METHODS
methods
% Constructor
function obj = classB(x,b,z)
y = z+b;
obj@superclass(x,y);
obj.b = b;
obj.z = z;
end
end
end
subclass.m:
classdef subclass < classA & classB
%% METHODS
methods
% Constructor
function obj = subclass(a,b,z)
obj@classA(a,0,z);
obj@classB(obj.x,b,z); % Why is this not allowed and how do I work around that
% without redoing the calculations done in classes "classA" and "classB"?
end
end
end
This gives the following error message:
"A constructor call to superclass classB appears after the object is used, or after a return."
A couple of questions:
1) Why is calling a superclass constructor after a use of the object not allowed?
2) How do I work around that without redoing the calculations done in classA and classB? I feel like I might to redesign the class hierarchy. But it just bugs me that it can't be done like above.
I use Matlab R2019a on Windows 10.

Best Answer

I can only speculate as to why it would not be allowed, but I assume there are hazards in using an object that is not finished being constructed...like feeding a baby that is only half way through being born, or driving a car that’s only half assembled.
Below is how I would re-implement. In your original design, it doesn't make sense to me that the classB constructor should have to set x if it has already been set in classA.
classdef superclass
%% PROPERTIES
properties
x;
y;
end
end
classdef classA < superclass
%% PROPERTIES
properties
a
end
properties (Access=private)
z
end
%% METHODS
methods
% Constructor


function obj = classA(a,z,y)
obj.x = a*z;
obj.a = a;
obj.z = z;
if nargin>2
obj.y=y;
end
end
end
end
classdef classB < superclass
%% PROPERTIES
properties
b
end
properties (Access=private)
z
end
%% METHODS
methods
% Constructor
function obj = classB(b,z,x)
obj.y = z+b;
obj.b = b;
obj.z = z;
if nargin>2
obj.x=x;
end
end
end
end
classdef subclass < classA & classB
%% METHODS
methods
% Constructor
function obj = subclass(a,b,z)
obj@classA(a,z); %set x but not y
obj@classB(b,z); %set y but not x
end
end
end