exponenta event banner

Методы конструктора классов

Назначение методов конструктора классов

Метод конструктора - это специальная функция, создающая экземпляр класса. Обычно методы конструктора принимают входные аргументы для назначения данных, хранящихся в свойствах, и возврата инициализированного объекта.

Базовый пример см. в разделе Создание простого класса.

Классы MATLAB ®, явно не определяющие конструкторы классов, имеют метод конструктора по умолчанию. Этот метод возвращает объект класса, который создан без входных аргументов. Класс может определить метод конструктора, который переопределяет конструктор по умолчанию. Явно определенный конструктор может принимать входные аргументы, инициализировать значения свойств, вызывать другие методы и выполнять другие операции, необходимые для создания объектов класса.

Основная структура методов конструктора

Методы конструктора можно структурировать в три основных раздела:

  • Предварительная инициализация - вычислить аргументы для конструкторов суперкласса.

  • Инициализация объекта - вызовите конструкторы суперкласса.

  • Постинициализация - выполнение любых операций, связанных с подклассом, включая ссылку и назначение объекту, вызов методов класса, передачу объекта функциям и т. д.

Этот код иллюстрирует основные операции, выполняемые в каждом разделе:

classdef ConstructorDesign < BaseClass1
   properties
      ComputedValue
   end
   methods
      function obj = ConstructorDesign(a,b,c)
         
         %% Pre Initialization %%
         % Any code not using output argument (obj)
         if nargin == 0
            % Provide values for superclass constructor
            % and initialize other inputs
            a = someDefaultValue;
            args{1} = someDefaultValue;
            args{2} = someDefaultValue;
         else
            % When nargin ~= 0, assign to cell array,
            % which is passed to supclass constructor
            args{1} = b;
            args{2} = c;
         end
         compvalue = myClass.staticMethod(a);
         
         %% Object Initialization %%
         % Call superclass constructor before accessing object
         % You cannot conditionalize this statement
         obj = obj@BaseClass1(args{:});
         
         %% Post Initialization %%
         % Any code, including access to object
         obj.classMethod(arg);
         obj.ComputedValue = compvalue;
         ...
      end
   ...
   end
...
end

Вызовите конструктор, как и любую функцию, передавая аргументы и возвращая объект класса.

obj = ConstructorDesign(a,b,c);

Руководство для конструкторов

  • Конструктор имеет то же имя, что и класс.

  • Конструктор может возвращать несколько аргументов, но первым выводом должен быть созданный объект.

  • Если не требуется назначать выходной аргумент, можно очистить переменную объекта в конструкторе (см. раздел Подавленный выходной объект).

  • При создании конструктора класса убедитесь, что он может вызываться без входных аргументов. См. раздел Требование к конструктору входных аргументов.

  • Если конструктор выполняет явный вызов конструктора суперкласса, этот вызов должен происходить до любой другой ссылки на построенный объект и не может происходить после return заявление.

  • Вызовы конструкторов суперкласса не могут быть условными. Нельзя помещать вызовы построения суперкласса в циклы, условия, коммутаторы, функции try/catch или вложенные функции. Дополнительные сведения см. в разделе Отсутствие условных вызовов конструкторов суперкласса.

Конструктор по умолчанию

Если класс не определяет конструктор, MATLAB предоставляет конструктор по умолчанию, который не принимает аргументов и возвращает скалярный объект, свойства которого инициализируются значениями по умолчанию. Конструктор по умолчанию, предоставленный MATLAB, также вызывает все конструкторы суперкласса без аргументов или с любым аргументом, переданным конструктору подкласса по умолчанию.

Если подкласс не определяет конструктор, конструктор по умолчанию передает свои входные данные конструктору прямого суперкласса. Это поведение полезно, когда нет необходимости в подклассе для определения конструктора, но конструктор суперкласса требует входных аргументов.

Когда определять конструкторы

Определите метод конструктора для инициализации объекта, которую не может выполнить конструктор по умолчанию. Например, при создании объекта класса требуется следующее:

  • Входные аргументы

  • Инициализация состояния объекта, например значений свойств, для каждого экземпляра класса

  • Вызов конструктора суперкласса со значениями, определенными конструктором подкласса

Связанная информация

Сведения о построении перечислений см. в разделе Последовательность вызова конструктора класса перечисления.

Сведения о создании массивов объектов в конструкторе см. в разделе Создание массивов объектов.

Если создаваемый класс является подклассом, MATLAB вызывает конструктор каждого класса суперкласса для инициализации объекта. Неявные вызовы конструктора суперкласса выполняются без аргументов. Если конструкторам суперкласса требуются аргументы, вызовите их из конструктора подкласса явным образом. См. раздел Последовательность управления вызовами конструктора

Инициализация объектов в конструкторе

Методы конструктора возвращают инициализированный объект в качестве выходного аргумента. Выходной аргумент создается при выполнении конструктора перед выполнением первой строки кода.

Например, следующий конструктор может назначить значение свойства объекта A как первый оператор, поскольку объект obj уже назначен экземпляру MyClass.

function obj = MyClass(a,b,c)
   obj.A = a;
   ...
end

Можно вызвать другие методы класса из конструктора, так как объект уже инициализирован.

Конструктор также создает объект, свойства которого имеют значения по умолчанию - пустые ([]) или значение по умолчанию, указанное в блоке определения свойства.

Например, этот конструктор оперирует входными аргументами для назначения значения Value собственность.

function obj = MyClass(a,b,c)
   obj.Value = (a + b) / c;
   ...
end

Ссылка на объект в конструкторе

При инициализации объекта, например, путем назначения значений свойствам, используйте имя выходного аргумента для ссылки на объект в конструкторе. Например, в следующем коде выходной аргумент имеет значение obj и объект является ссылочным как obj:

% obj is the object being constructed
function obj = MyClass(arg)
   obj.propert1 = arg*10;
   obj.method1;
   ...
end

Дополнительные сведения об определении значений свойств по умолчанию см. в разделе Значения свойств по умолчанию.

Нет требования к конструктору входных аргументов

Существуют случаи, когда конструктор должен быть вызван без входного аргумента:

  • При загрузке объектов в рабочую область, если класс ConstructOnLoad атрибут имеет значение true, load функция вызывает конструктор класса без аргументов.

  • При создании или расширении массива объектов таким образом, чтобы не всем элементам задавались конкретные значения, конструктор класса вызывается без аргументов для заполнения неопределенных элементов (например, x(10,1) = MyClass(a,b,c);). В этом случае конструктор вызывается один раз без аргументов для заполнения пустых элементов массива (x(1:9,1)) с копиями этого объекта.

Если входные аргументы отсутствуют, конструктор создает объект, используя только значения свойств по умолчанию. Рекомендуется добавить проверку нулевых аргументов к конструктору класса, чтобы предотвратить ошибку при возникновении любого из этих двух случаев:

function obj = MyClass(a,b,c)
   if  nargin > 0
      obj.A = a;
      obj.B = b;
      obj.C = c;
      ...
   end
end

Способы обработки конструкторов суперкласса см. в разделе Основная структура методов конструктора.

Конструкторы подкласса

Конструкторы подкласса могут явно вызывать конструкторы суперкласса для передачи аргументов конструктору суперкласса. Конструктор подкласса должен указать эти аргументы в вызове конструктора суперкласса и использовать выходной аргумент конструктора для формирования вызова. Ниже приведен синтаксис:

classdef MyClass < SuperClass
   methods
      function obj = MyClass(a,b,c,d)
         obj@SuperClass(a,b);
         ...
      end
   end
end

Конструктор подкласса должен выполнять все вызовы конструкторов суперкласса перед любыми другими ссылками на объект (obj). Это ограничение включает назначение значений свойств или вызов обычных методов классов. Кроме того, конструктор подкласса может вызывать конструктор суперкласса только один раз.

Только ссылки на указанные суперклассы

Если classdef не указывает класс как суперкласс, конструктор не может вызвать конструктор суперкласса с таким синтаксисом. То есть конструктор подкласса может вызывать только прямые конструкторы суперкласса, перечисленные в classdef линия.

classdef MyClass < SuperClass1 & SuperClass2

MATLAB вызывает все незакрепленные конструкторы в порядке слева направо, в котором они указаны в classdef линия. MATLAB не передает аргументы с этими вызовами.

Нет условных вызовов конструкторов суперкласса

Вызовы конструкторов суперкласса должны быть безусловными. Для данного суперкласса может быть только один вызов. Инициализируйте суперклассную часть объекта путем вызова конструкторов суперкласса перед использованием объекта (например, для назначения значений свойств или вызова методов классов).

Чтобы вызвать конструктор суперкласса с различными аргументами, зависящими от некоторого условия, создайте массив аргументов ячейки и выполните один вызов конструктора.

Например, Cube конструктор класса вызывает суперкласс Shape использование конструктором значений по умолчанию при Cube конструктор вызывается без аргументов. Если Cube конструктор вызывается с четырьмя входными аргументами, затем передается upvector и viewangle к конструктору суперкласса:

classdef Cube < Shape
   properties
      SideLength = 0
      Color = [0 0 0]
   end
   methods
      function cubeObj = Cube(length,color,upvector,viewangle)
         % Assemble superclass constructor arguments
         if nargin == 0
            super_args{1} = [0 0 1];
            super_args{2} = 10;
         elseif nargin == 4
            super_args{1} = upvector;
            super_args{2} = viewangle;
         else
            error('Wrong number of input arguments')
         end

         % Call superclass constructor
         cubeObj@Shape(super_args{:});

         % Assign property values if provided
         if nargin > 0 
            cubeObj.SideLength = length;
            cubeObj.Color = color;
         end
         ...
      end
   ...
   end
end

Ноль или больше аргументов суперкласса

Чтобы поддерживать синтаксис, вызывающий конструктор суперкласса без аргументов, предоставьте этот синтаксис явно.

Предположим, в случае Cube пример класса, все значения свойств в Shape суперкласс и Cube подкласс имеет значения по умолчанию, указанные в определениях классов. Затем можно создать экземпляр Cube без указания аргументов для конструкторов суперкласса или подкласса.

Вот как вы можете реализовать это поведение в Cube конструктор:

methods
   function cubeObj = Cube(length,color,upvector,viewangle)
      % Assemble superclass constructor arguments
      if nargin == 0 
         super_args = {};
      elseif nargin == 4
         super_args{1} = upvector;
         super_args{2} = viewangle;
      else
         error('Wrong number of input arguments')
      end

      % Call superclass constructor
      cubeObj@Shape(super_args{:});

      % Assign property values if provided
      if nargin > 0 
         cubeObj.SideLength = length;
         cubeObj.Color = color;
      end
   ...
   end
end

Подробнее о подклассах

Сведения о создании подклассов см. в разделе Конструирование конструкторов подклассов.

Неявный вызов унаследованного конструктора

MATLAB передает аргументы неявно из конструктора подкласса по умолчанию конструктору суперкласса. Такое поведение исключает необходимость реализации метода конструктора для подкласса только для передачи аргументов конструктору суперкласса.

Например, для следующего конструктора класса требуется один входной аргумент (a datetime объект), который конструктор назначает CurrentDate собственность.

classdef BaseClassWithConstr
   properties
      CurrentDate datetime
   end
   methods
      function obj = BaseClassWithConstr(dt)
         obj.CurrentDate = dt;
      end
   end        
end

Предположим, что создается подкласс BaseClassWithConstr, но подкласс не требует явного метода конструктора.

classdef SubclassDefaultConstr < BaseClassWithConstr
   ...
end

Можно создать объект SubclassDefaultConstr путем вызова конструктора по умолчанию с аргументом суперкласса:

obj = SubclassDefaultConstr(datetime);

Сведения о конструкторах подкласса см. в разделах Конструкторы подкласса и Конструктор по умолчанию.

Ошибки при построении класса

Для классов дескрипторов MATLAB вызывает delete при возникновении ошибки в следующих условиях:

  • Ссылка на объект присутствует в коде до ошибки.

  • Раннее return присутствует в коде перед ошибкой.

MATLAB вызывает delete метод на объекте, delete для любых объектов, содержащихся в свойствах, и delete методов для любых инициализированных базовых классов.

В зависимости от того, когда возникает ошибка, MATLAB может вызвать деструктор класса до полного создания объекта. Поэтому класс delete методы должны иметь возможность работать с частично построенными объектами, которые могут иметь значения не для всех свойств. Дополнительные сведения см. в разделе Поддержка уничтожения частично построенных объектов.

Сведения о том, как уничтожаются объекты, см. в разделе Дескриптор деструктора классов.

Объект вывода подавлен

Можно подавить назначение экземпляра класса ans если в вызове конструктора не назначена выходная переменная. Этот метод полезен для приложений, создающих окна графического интерфейса, которые удерживаются на построенных объектах. Этим приложениям не требуется возвращать объект.

Использовать nargout чтобы определить, был ли конструктор вызван с выходным аргументом. Например, конструктор класса для MyApp класс очищает переменную объекта, obj, при вызове без назначения выходных данных:

classdef MyApp
   methods
      function obj = MyApp
         ...
         if nargout == 0
            clear obj
         end
      end
      ...
   end
end

Если конструктор класса не возвращает объект, MATLAB не запускает meta.class InstanceCreated событие.

Связанные темы