Этот пример задает класс, который изменяет поведение индексации по умолчанию путем реализации subsref
и subsasgn
методы. Класс также реализует преобразование и сложение типов путем реализации double
метод конвертера и plus
способ.
Цель проекта класса состоит в том, чтобы:
Позволяет вам обрабатывать объект класса как числовой массив
Иметь возможность содержать нечисловые и числовые данные в объекте класса
Класс имеет три свойства:
Data
- числовые тестовые данные
Description
- описание тестовых данных
Date
- был проведен тест даты
Предположим, что у вас есть следующие случайные данные (randi
):
d = randi(9,3,4)
d = 8 9 3 9 9 6 5 2 2 1 9 9
Создайте образец класса:
obj = MyDataClass(d,'Test001')
obj = MyDataClass with properties: Data: [3x4 double] Description: 'Test001' Date: [2012 1 7 9 32 34.5190]
Аргументы конструктора передают значения для Data
и Description
свойства. clock
функция присваивает значение Date
свойство из конструктора. Этот подход захватывает информацию о времени и дате создания каждого образца.
Вот предварительное описание кода без subsref
, subsasgn
double
, и plus
методы.
classdef MyDataClass properties Data Description end properties (SetAccess = private) Date end methods function obj = MyDataClass(data,desc) if nargin > 0 obj.Data = data; end if nargin > 1 obj.Description = desc; end obj.Date = clock; end end end
Реализуйте subsref
метод для поддержки индексации по умолчанию и специализированного типа.
Индексированное поведение ссылок по умолчанию для скалярных объектов:
obj.Data(2,3)
ans = 5
И добавить функциональность для индекса в Data
свойство с выражением, подобным этому оператору:
obj(2,3)
Если вы переопределяете '()'
индексация для поддержки доступа к Data
свойство, вы не можете создать массивы MyDataClass
объекты и использование '()'
индексация для доступа к отдельным объектам. Ссылаться можно только на скалярные объекты.
Для достижения целей проекта subsref
метод должен обрабатывать все типы индексации. The subsref
метод:
Вызывает builtin
subsref
функция для '.'
индексация
Возвращает ошибку для '{}'
индексация
Определяет собственную версию '()'
индексация.
Результат: obj(i)
эквивалентно obj.Data(i)
.
function sref = subsref(obj,s) % obj(i) is equivalent to obj.Data(i) switch s(1).type case '.' sref = builtin('subsref',obj,s); case '()' if length(s) < 2 sref = builtin('subsref',obj.Data,s); else sref = builtin('subsref',obj,s); end case '{}' error('MYDataClass:subsref',... 'Not a supported subscripted reference') end end
Чтобы поддержать эквивалентное поведение индексированной ссылки с индексированным назначением, реализуйте subsasgn
способ.
Поддержка индексированного назначения по умолчанию:
obj.Data(2,3) = 9;
Добавьте функциональные возможности для присвоения значений Data
свойство с выражением, подобным этому оператору:
obj(2,3) = 9;
Как и subsref
метод, subsasgn
метод:
Вызывает builtin
subsasgn
функция для '.'
индексация
Возвращает ошибку для '{}'
индексация
Определяет собственную версию '()'
индексация.
substruct
функция переопределяет структуру индексных и индексных индексов, которую MATLAB® переходит к subsref
и subsasgn
.
function obj = subsasgn(obj,s,val) if isempty(s) && isa(val,'MyDataClass') obj = MyDataClass(val.Data,val.Description); end switch s(1).type case '.' obj = builtin('subsasgn',obj,s,val); case '()' if length(s)<2 if isa(val,'MyDataClass') error('MyDataClass:subsasgn',... 'Object must be scalar') elseif isa(val,'double') % Redefine the struct s to make the call: obj.Data(i) snew = substruct('.','Data','()',s(1).subs(:)); obj = subsasgn(obj,snew,val); end end case '{}' error('MyDataClass:subsasgn',... 'Not a supported subscripted assignment') end end
Во-первых, реализуйте double
метод, который преобразует объект в массив типа double. Путем реализации double
метод конвертера, возможно добавить MyDataClass
объект другому классу объекта. Однако другой класс должен реализовать double
метод, который также возвращает массив типа double. Для получения дополнительной информации о преобразовании типов см. раздел «Преобразователи объектов».
Разрешить прямое сложение Data
значения свойств путем реализации plus
способ. Реализация plus
метод позволяет использовать +
оператор для сложения MyDataClass
объекты.
Поскольку метод plus реализует сложение путем добавления двойных массивов, MATLAB:
Примените правила сложения при добавлении MyDataClass
объекты
Возвращает ошибки для любого условия, которое может вызвать ошибки в числовом сложении по умолчанию. Для примера размерности несоответствие.
The plus
метод использует double
метод для преобразования объекта в числовые значения перед выполнением сложения:
function a = double(obj) a = obj.Data; end
function c = plus(obj,b) c = double(obj) + double(b); end
Для примера, plus
метод позволяет добавить скалярное число к объекту Data
массив.
Вот значения Data
, отображаемый с использованием индексированной ссылки:
obj(:,:)
ans = 8 9 3 9 9 6 9 2 2 1 9 9
Добавить 7
к массиву, содержащемуся в Data
свойство:
obj + 7
ans = 15 16 10 16 16 13 16 9 9 8 16 16
Это определение для MyDataClass
включает в себя end
метод индексирования, обсуждаемый в конце как индекс объекта. посторонний
classdef MyDataClass % Example for "A Class with Modified Indexing" properties Data Description end properties (SetAccess = private) Date end methods function obj = MyDataClass(data,desc) % Support 0-2 args if nargin > 0 obj.Data = data; end if nargin > 1 obj.Description = desc; end obj.Date = clock; end function sref = subsref(obj,s) % obj(i) is equivalent to obj.Data(i) switch s(1).type case '.' sref = builtin('subsref',obj,s); case '()' if length(s)<2 sref = builtin('subsref',obj.Data,s); else sref = builtin('subsref',obj,s); end case '{}' error('MyDataClass:subsref',... 'Not a supported subscripted reference') end end function obj = subsasgn(obj,s,val) if isempty(s) && isa(val,'MyDataClass') obj = MyDataClass(val.Data,val.Description); end switch s(1).type case '.' obj = builtin('subsasgn',obj,s,val); case '()' % if length(s)<2 if isa(val,'MyDataClass') error('MyDataClass:subsasgn',... 'Object must be scalar') elseif isa(val,'double') snew = substruct('.','Data','()',s(1).subs(:)); obj = subsasgn(obj,snew,val); end end case '{}' error('MyDataClass:subsasgn',... 'Not a supported subscripted assignment') end end function a = double(obj) a = obj.Data; end function c = plus(obj,b) c = double(obj) + double(b); end function ind = end(obj,k,n) szd = size(obj.Data); if k < n ind = szd(k); else ind = prod(szd(k:end)); end end end end