Вот что я использую. Вы можете использовать более сжатую форму, которая принимает аргумент скалярного размера.
r = repmat(MyClass, 0);
Обратите внимание, что вы не объявляете переменную как имеющую тип; это по-прежнему просто значение, содержащееся в переменной, имеющей тип.
Это будет работать как со старым стилем, так и с новыми классами MCOS. Если вы используете все новые классы стилей, gnovice «empty ()» кажется хорошей идеей.
Если вы чувствуете себя продвинутым, есть еще один вариант, который я включил для полноты картины.
Вы также можете обработать это в subsasgn для ваших объектов, по крайней мере, для старого класса Matlab. Если вы выполняете индексированное присвоение унифицированной переменной с помощью определенного пользователем объекта на RHS («правая сторона»), вызывается подсегмент для этого класса, при этом LHS входит как [] (пустое двойное значение). Если у вас есть специальная форма конструктора, которая позволяет вам создавать пустой объект без вызова repmat для объекта, вы можете поддержать это, чтобы пользователям не приходилось предварительно распределять свои переменные с объектами вашего класса.
В вашем подсистеме:
function obj = subsasgn(obj, S, B)
...
s = S(1);
...
switch s.type
case '()'
% Handle dispatch on LHS autovivification
if isnumeric(obj) && isa(B, mfilename('class'))
% Must use special ctor to preallocate
obj = feval(class(B), mxdims(size(B)));
end
Затем в вашем конструкторе создайте форму вызова бэкдора для создания пустых пространств, благословляя предварительно перепрограммированные структуры.
function MyClass(varargin) %constructor
SuperClasses = { }; % if you inherit, fill this in
if nargin == 1 && isa(varargin{1}, 'mxdims')
% special backdoor to support preallocation without repmat
s = repmat(DataStructure, msize(varargin{1})); % built-in repmat called on plain struct
out = class(s, mfilename, SuperClasses{:});
return;
end
...
Класс @mxdims - это специальный класс, который вам нужно создать, который содержит вектор размера и служит маркером для вызова этой формы бэкдора. Метод msize () возвращает вектор размера, который он представляет.
Если вы определяете MyClass так, чтобы он поддерживал это, вы можете просто выполнить «s (1) = MyClass» без предварительного выделения s. Однако вы не можете использовать "s (end + 1)"; "end" работает только с заранее выделенными значениями.
Это сложная область для работы в Matlab. Работа с подсистемой типов и подобной системой типов может приводить к множеству мелких ошибок, включая segfaults. Поступая таким образом, вы получите более «полное» поведение для ваших пользовательских объектов. Но это связано с работой и хрупкостью, и вам, вероятно, лучше придерживаться «repmat (class, 0)» или «empty ()».
person
Andrew Janke
schedule
07.04.2010