Making a class similar to that one in the example I attached arguments to the class instance like so
function t = train (m, F_z, F_b, varargin)
...
t.m = m; % total mass of train [kg]
t.F_z = F_z; % ...
...
t = class (t, "train");
Getting the fieldnames works
>> t1 = train(100, 150000, 200000);
...
>> fieldnames(t1)
ans =
{
[1,1] = m
[2,1] = F_z
...
But how do I access these? Apparently it's not
>> t1.m
error: invalid index for class
>> getfield(t1, 'm')
error: invalid index for class
error: called from
...
If I leave out the line t = class (t, 'train');
at the end of function t = train (m...
in @train/train.m
these things all seem to work fine... But then its a struct
and not a class
You can do this in two ways. You can define a method to retrieve it (easy), or you set up subsref
(subscript reference) (hard).
To define a method, simply create @train/m.m
with:
function r = m ()
r = t.m;
endfunction
To set up subscripting, then create @train/subsref.m
with:
function r = subsref (val, idx)
if (strcmp (idx.type, ".") && strcmp (idx.subs, "m"))
r = val.m;
endif
endfunction
This will allow you to access only the field m
. To give access to any of the properties within your class, you can simply do:
function r = subsref (val, idx)
r = subsref (struct (val), idx);
endfunction
To allow access to a subset of properties, you can:
function r = subsref (val, idx)
if (strcmp (idx.type, ".") && any (strcmp (idx.subs, {"m", "f2", "F_z"})))
r = val.(idx.subs{1});
endif
endfunction
But subsref
controls all indexing, not only when accessing it as a structure. You could allow people to index the object (maybe you have a wagon class, and indexing the train returns them). The function looks a bit weird at start (just like subsasgn
(subscript assignment)) but can be quite useful. You could do:
function r = subsref (val, idx)
if (strcmp (idx.type, ".") && strcmp (idx.subs, "m"))
r = val.m;
elseif (strcmp (idx.type, "()"))
r = val.wagons(idx.subs{:});
endif
endfunction