Этот пример реализует класс, чтобы представлять полиномы на языке MATLAB®. Конструктивные требования:
Поведение класса значения — полиномиальный объект должен вести себя как числовые переменные MATLAB, когда скопировано и передано функциям.
Специализированное отображение и индексация
Объекты могут быть скаляром только. Специализация отображения и функциональности индексации устраняет нормальное поведение массивов.
Арифметические операции
Двойной конвертер, упрощающий использование полиномиального объекта с существующими функциями MATLAB, которые принимают числовые входные параметры.
DocPolynom
Члены классаОпределение класса задает свойство для хранения данных и задает папку (@DocPolynom
) это содержит определение класса.
Следующая таблица обобщает свойства, заданные для DocPolynom
класс.
DocPolynom
Class Properties
Имя | Класс | Значение по умолчанию | Описание |
---|---|---|---|
|
|
| Вектор с полиномиальными коэффициентами [самый высокий порядок... самый низкоуровневый] |
Следующая таблица обобщает методы для DocPolynom
класс.
DocPolynom
Методы класса
Имя | Описание |
---|---|
| Конструктор класса |
| Преобразует |
| Создает отформатированное отображение |
| Определяет, как MATLAB отображает |
| Позволяет вам задать значение для независимой переменной как индекс, получить доступ |
| Сложение реализаций |
| Вычитание реализаций |
| Умножение реализаций |
DocPolynom
КлассСледующие примеры иллюстрируют основное использование DocPolynom
класс.
Создайте DocPolynom
объекты представлять следующие полиномы. Аргумент к функции конструктора содержит полиномиальные коэффициенты и.
p1 = DocPolynom([1 0 -2 -5])
p1 = x^3 - 2*x - 5
p2 = DocPolynom([2 0 3 2 -7])
p2 = 2*x^4 + 3*x^2 + 2*x - 7
Найдите корни полинома путем передачи коэффициентов roots
функция.
roots(p1.coef)
ans = 2.0946 + 0.0000i -1.0473 + 1.1359i -1.0473 - 1.1359i
Добавьте эти два полинома p1
и p2
.
MATLAB вызывает plus
метод задан для DocPolynom
класс, когда вы добавляете два DocPolynom
объекты.
p1 + p2
ans = 2*x^4 + x^3 + 3*x^2 - 12
DocPolynom
Резюме классаПример кода | Обсуждение |
---|---|
classdef DocPolynom
| Класс значения, который реализует тип данных для полиномов. |
properties coef end | Вектор с полиномиальными коэффициентами [самый высокий порядок... самый низкоуровневый] |
methods | Для получения общей информации о методах, см. Обычные Методы |
function obj = DocPolynom(c) if nargin > 0 if isa(c,'DocPolynom') obj.coef = c.coef; else obj.coef = c(:).'; end end end | Конструктор класса создает использование объектов:
Смотрите конструктора DocPolynom |
function obj = set.coef(obj,val) if ~isa(val,'double') error('Coefficients must be doubles') end ind = find(val(:).'~=0); if ~isempty(ind); obj.coef = val(ind(1):end); else obj.coef = val; end end | Метод установки для
|
function c = double(obj) c = obj.coef; end | Преобразуйте |
function str = char(obj) if all(obj.coef == 0) s = '0'; str = s; return else d = length(obj.coef)-1; s = cell(1,d); ind = 1; for a = obj.coef; if a ~= 0; if ind ~= 1 if a > 0 s(ind) = {' + '}; ind = ind + 1; else s(ind) = {' - '}; a = -a; ind = ind + 1; end end if a ~= 1 || d == 0 if a == -1 s(ind) = {'-'}; ind = ind + 1; else s(ind) = {num2str(a)}; ind = ind + 1; if d > 0 s(ind) = {'*'}; ind = ind + 1; end end end if d >= 2 s(ind) = {['x^' int2str(d)]}; ind = ind + 1; elseif d == 1 s(ind) = {'x'}; ind = ind + 1; end end d = d - 1; end end str = [s{:}]; end | Преобразуйте y = f (x) |
function disp(obj) c = char(obj); if iscell(c) disp([' ' c{:}]) else disp(c) end end | Перегрузка Для получения информации об этом коде смотрите Перегрузку disp для DocPolynom |
function dispPoly(obj,x) p = char(obj); e = @(x)eval(p); y = zeros(length(x)); disp(['y = ',p]) for k = 1:length(x) y(k) = e(x(k)); disp([' ',num2str(y(k)),... ' = f(x = ',... num2str(x(k)),')']) end end | Возвратите выполненное выражение с отформатированным выводом. Использование выход Для получения информации об этом коде смотрите Отображение Выполненное Выражение |
function b = subsref(a,s) switch s(1).type case '()' ind = s.subs{:}; b = polyval(a.coef,ind); case '.' switch s(1).subs case 'coef' b = a.coef; case 'disp' disp(a) otherwise if length(s)>1 b = a.(s(1).subs)(s(2).subs{:}); else b = a.(s.subs); end end otherwise error('Specify value for x as obj(x)') end end | Переопределите индексированную ссылку для Для получения информации об этом коде смотрите, Переопределяют Индексируемую Ссылку |
function r = plus(obj1,obj2) obj1 = DocPolynom(obj1); obj2 = DocPolynom(obj2); k = length(obj2.coef) - length(obj1.coef); zp = zeros(1,k); zm = zeros(1,-k); r = DocPolynom([zp,obj1.coef] + [zm,obj2.coef]); end function r = minus(obj1,obj2) obj1 = DocPolynom(obj1); obj2 = DocPolynom(obj2); k = length(obj2.coef) - length(obj1.coef); zp = zeros(1,k); zm = zeros(1,-k); r = DocPolynom([zp,obj1.coef] - [zm,obj2.coef]); end function r = mtimes(obj1,obj2) obj1 = DocPolynom(obj1); obj2 = DocPolynom(obj2); r = DocPolynom(conv(obj1.coef,obj2.coef)); end end | Задайте три арифметических оператора:
Для получения информации об этом коде смотрите, Задают Арифметические операторы. Для получения общей информации об определении операторов, см. Перегрузку операторов |
end end |
|
DocPolynom
КонструкторСледующей функцией является DocPolynom
конструктор класса, который находится в файле @DocPolynom/DocPolynom.m
:
methods function obj = DocPolynom(c) if isa(c,'DocPolynom') obj.coef = c.coef; else obj.coef = c(:).'; end end end
Это возможно ко всему DocPolynom
конструктор с двумя различными аргументами:
Входным параметром является DocPolynom
объект — Если вы вызываете функцию конструктора с входным параметром, который уже является DocPolynom
объект, конструктор возвращает новый DocPolynom
объект с теми же коэффициентами как входной параметр. isa
функционируйте проверки на этот вход.
Входной параметр является вектором коэффициентов — Если входным параметром не является DocPolynom
объект, конструктор пытается изменить значения в вектор и присвоить их coef
свойство.
coef
метод набора свойств ограничивает значения свойств, удваивается. Смотрите Удаляют Несоответствующие Коэффициенты для описания метода набора свойств.
Использование в качестве примера DocPolynom
конструктор является оператором:
p = DocPolynom([1 0 -2 -5]) p = x^3 - 2*x -5
Этот оператор создает экземпляр DocPolynom
класс с заданными коэффициентами. Обратите внимание на то, что отображение объекта показывает эквивалентный полином с помощью синтаксиса языка MATLAB. DocPolynom
класс реализует это отображение с помощью disp
и char
методы класса.
Программное обеспечение MATLAB представляет полиномы как векторы-строки, содержащие коэффициенты, упорядоченные убывающими степенями. Нули в векторе коэффициентов представляют условия, которые выпадают из полинома. Начальные нули, поэтому, могут быть проигнорированы при формировании полинома.
Некоторый DocPolynom
методы класса используют длину вектора коэффициентов, чтобы определить степень полинома. Полезно, поэтому, удалить начальные нули из вектора коэффициентов так, чтобы его длина представляла истинное значение.
DocPolynom
класс хранит вектор коэффициентов в свойстве, которое использует метод установки удалить начальные нули из заданных коэффициентов прежде, чем установить значение свойства.
methods function obj = set.coef(obj,val) if ~isa(val,'double') error('Coefficients must be doubles') end ind = find(val(:).'~=0); if ~isempty(ind); obj.coef = val(ind(1):end); else obj.coef = val; end end end
DocPolynom
Объекты к другим типамDocPolynom
класс задает два метода, чтобы преобразовать DocPolynom
объекты к другим классам:
double
— Преобразует в двойной числовой тип, таким образом, функции могут выполнить математические операции на коэффициентах.
char
— Преобразует в символы, используемые к формату вывода для отображения в командном окне
Двойной метод конвертера для DocPolynom
класс просто возвращает вектор коэффициентов:
methods function c = double(obj) c = obj.coef; end end
Для DocPolynom
объект p
:
p = DocPolynom([1 0 -2 -5]);
оператор:
c = double(p)
возвращается:
c= 1 0 -2 -5
который имеет класс double
:
class(c) ans = double
char
метод производит char
вектор, который представляет полином, отображенный как степени x
. char
возвращенный вектор является синтаксически правильным выражением MATLAB.
char
метод использует массив ячеек, чтобы собрать char
векторные компоненты, которые составляют отображенный полином.
disp
метод использует char
метод, чтобы отформатировать DocPolynom
объект для отображения. evalPoly
метод использует char
создать выражение MATLAB, чтобы оценить.
Пользователи DocPolynom
объекты вряд ли вызовут char
или disp
методы непосредственно, но эти методы включают DocPolynom
класс, чтобы вести себя как другие классы данных в MATLAB.
Вот char
метод.
methods function str = char(obj) if all(obj.coef == 0) s = '0'; str = s; return else d = length(obj.coef)-1; s = cell(1,d); ind = 1; for a = obj.coef; if a ~= 0; if ind ~= 1 if a > 0 s(ind) = {' + '}; ind = ind + 1; else s(ind) = {' - '}; a = -a; ind = ind + 1; end end if a ~= 1 || d == 0 if a == -1 s(ind) = {'-'}; ind = ind + 1; else s(ind) = {num2str(a)}; ind = ind + 1; if d > 0 s(ind) = {'*'}; ind = ind + 1; end end end if d >= 2 s(ind) = {['x^' int2str(d)]}; ind = ind + 1; elseif d == 1 s(ind) = {'x'}; ind = ind + 1; end end d = d - 1; end end str = [s{:}]; end end
disp
для DocPolynomОбеспечить более полезное отображение DocPolynom
объекты, этот класс перегрузки disp
в определении класса.
Этот disp
метод использует char
метод, чтобы произвести текстовое представление полинома, который это затем отображает на экране.
char
метод возвращает массив ячеек или символьный '0'
если коэффициенты являются всем нулем.
methods function disp(obj) c = char(obj); if iscell(c) disp([' ' c{:}]) else disp(c) end end end
disp
МетодОператор:
p = DocPolynom([1 0 -2 -5])
создает DocPolynom
объект. Поскольку оператор не отключен с точкой с запятой, получившийся вывод отображен на командной строке:
p = x^3 - 2*x - 5
char
метод конвертера формирует выражение MATLAB для полинома, представленного DocPolynom
объект. dispPoly
метод выполняет выражение, возвращенное char
метод с заданным значением для x
.
methods function dispPoly(obj,x) p = char(obj); e = @(x)eval(p); y = zeros(length(x)); disp(['y = ',p]) for k = 1:length(x) y(k) = e(x(k)); disp([' ',num2str(y(k)),... ' = f(x = ',... num2str(x(k)),')']) end end end
Создайте DocPolynom
объект p
:
p = DocPolynom([1 0 -2 -5])
p = x^3 - 2*x - 5
Оцените полином в x
равняйтесь трем значениям, [3 5 9]
:
dispPoly(p,[3 5 9])
y = x^3 - 2*x - 5 16 = f(x = 3) 110 = f(x = 5) 706 = f(x = 9)
DocPolynom
класс переопределяет индексированную ссылку, чтобы поддержать использование объектов, представляющих полиномы. В DocPolynom
класс, преобразованная в нижний индекс ссылка на объект вызывает оценку полинома со значением независимой переменной, равной индексу.
Например, учитывая следующий полином:
Создайте DocPolynom
объект p
:
p = DocPolynom([1 0 -2 -5])
p = x^3 - 2*x - 5
Следующее преобразованное в нижний индекс выражение оценивает значение полинома в x = 3
и в x = 4
, и возвращает получившиеся значения:
p([3 4])
ans = 16 51
Переопределите значение по умолчанию преобразованное в нижний индекс ссылочное поведение путем реализации subsref
метод.
Если класс задает subsref
метод, MATLAB вызывает этот метод для объектов этого класса каждый раз, когда преобразованная в нижний индекс ссылка происходит. subsref
метод должен задать все индексируемые ссылочные поведения, не только конкретный случай, который вы хотите изменить.
DocPolynom
subsref
метод реализует следующие поведения:
p(x = [a1...an])
— Оцените полином в x = a
.
p.coef
— Доступ к coef
значение свойства
p.disp
— Отобразите полином как выражение MATLAB, не присваивая выход.
obj = p.method(args)
— Используйте запись через точку, чтобы вызвать аргументы методов и возвратить модифицированный объект.
obj = p.method
— Используйте запись через точку, чтобы вызвать методы без аргументов и возвратить модифицированный объект.
subsref
Детали реализацииsubsref
метод перегружается subsref
функция.
Например, рассмотрите вызов polyval
функция:
p = DocPolynom([1 0 -2 -5]) p = x^3 - 2*x - 5 polyval(p.coef,[3 5 7]) ans = 16 110 324
polyval
функция требует:
Полиномиальные коэффициенты
Значения независимой переменной, в которой можно оценить полином
polyval
функция возвращает значение f(x)
в этих значениях. subsref
вызовы polyval
через операторы:
case '()' ind = s.subs{:}; b = polyval(a.coef,ind);
При реализации subsref
поддерживать вызов метода с аргументами с помощью записи через точку, оба type
и subs
поля структуры содержат несколько элементов.
subsref
метод реализует всю преобразованную в нижний индекс ссылку явным образом, как показывают в следующем листинге кода.
methods function b = subsref(a,s) switch s(1).type case '()' ind = s.subs{:}; b = polyval(a.coef,ind); case '.' switch s(1).subs case 'coef' b = a.coef; case 'disp' disp(a) otherwise if length(s)>1 b = a.(s(1).subs)(s(2).subs{:}); else b = a.(s.subs); end end otherwise error('Specify value for x as obj(x)') end end end
Несколько арифметических операций значимы на полиномах. DocPolynom
класс реализует эти методы:
Метод и синтаксис | Реализованный оператор |
---|---|
| Сложение |
| Вычитание |
| Умножение матриц |
При перегрузке арифметических операторов рассмотрите типы данных, которые необходимо поддержать. plus
минус,
, andmtimes
методы заданы для DocPolynom
класс, чтобы обработать сложение, вычитание и умножение на DocPolynom
— DocPolynom
и DocPolynom
'double'
комбинации операндов.
+
ОператорЕсли любой p
или q
DocPolynom
объект, это выражение:
p + q
Генерирует вызов функционального @DocPolynom/plus
, если другой объект не имеет более высокого приоритета.
Следующий метод перегружает plus
(+
) оператор для DocPolynom
класс:
methods function r = plus(obj1,obj2) obj1 = DocPolynom(obj1); obj2 = DocPolynom(obj2); k = length(obj2.coef) - length(obj1.coef); zp = zeros(1,k); zm = zeros(1,-k); r = DocPolynom([zp,obj1.coef] + [zm,obj2.coef]); end end
Вот то, как функция работает:
Убедитесь, что обоими входными параметрами является DocPolynom
объекты так, чтобы выражения такой как
p + 1
это вовлекает обоих DocPolynom
и double
, работайте правильно.
Доступ к этим двум векторам коэффициентов и, при необходимости, заполняет одного из них с нулями, чтобы сделать обоих той же длиной. Фактическое сложение является просто векторной суммой этих двух векторов коэффициентов.
Вызовите DocPolynom
конструктор, чтобы создать правильно типизированный объект, который является результатом добавления полиномов.
Define -
ОператорРеализуйте minus
оператор-
) использование того же подхода как plus
(+
оператор.
minus
метод вычисляет p
Q
. Доминирующим аргументом должен быть DocPolynom
объект.
methods function r = minus(obj1,obj2) obj1 = DocPolynom(obj1); obj2 = DocPolynom(obj2); k = length(obj2.coef) - length(obj1.coef); zp = zeros(1,k); zm = zeros(1,-k); r = DocPolynom([zp,obj1.coef] - [zm,obj2.coef]); end end
*
ОператорРеализуйте mtimes
метод, чтобы вычислить продукт p*q
. mtimes
метод реализует умножение матриц, поскольку умножение двух полиномов является сверткой (conv
) из их векторов коэффициентов:
methods function r = mtimes(obj1,obj2) obj1 = DocPolynom(obj1); obj2 = DocPolynom(obj2); r = DocPolynom(conv(obj1.coef,obj2.coef)); end end
Учитывая DocPolynom
объект:
p = DocPolynom([1 0 -2 -5]);
Следующие две арифметических операции вызывают DocPolynom
plus
и mtimes
методы:
q = p+1; r = p*q;
произвести
q = x^3 - 2*x - 4 r = x^6 - 4*x^4 - 9*x^3 + 4*x^2 + 18*x + 20