Этот пример задает класс, который изменяет поведение индексации значения по умолчанию путем реализации 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
метод должен обработать все типы индексации. 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); return 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
метод конвертера, возможно добавить MyDataClass
возразите против другого класса объекта. Однако другой класс должен реализовать double
метод, который также возвращает массив, удваивается. Для получения дополнительной информации о преобразовании типов см. Преобразователи объектов.
Позвольте прямое сложение Data
значения свойств путем реализации plus
метод. Реализация plus
метод включает использование +
оператор для сложения MyDataClass
объекты.
Поскольку плюс метод реализует сложение путем добавления двойных массивов, MATLAB:
Примените правила сложения при добавлении MyDataClass
объекты
Возвращает ошибки для любого условия, которое может вызвать ошибки в числовом сложении по умолчанию. Например, несоответствие размерности.
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); return 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