реклама на сайте
подробности

 
 
> Расчет обратной матрицы, Программа на Delphi
Andbiz
сообщение Oct 2 2011, 19:25
Сообщение #1


Местный
***

Группа: Свой
Сообщений: 447
Регистрация: 16-11-08
Из: Украина, Донецк
Пользователь №: 41 684



Здравствуйте! Столкнулся по учебе с написанием программы, которая делает различные операции с матрицами (умножение, деление, вычитание, транспонирование и т.д.). Все операции сделал, кроме одной - обратная матрица.

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

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

det:=1.0;
// начинаю прямой ход Гаусса
for k:=1 to n do
begin
det:=det*A[k,k]; //вычисление определителя
for j:=k+1 to n do
begin
A[k,j]:=A[k,j]/A[k,k];
end;
for i:=k+1 to n do //начало вложенного цикла
for j:=k+1 to m do
begin
r:=A[k,j]*A[i,k];
A[i,j]:=A[i,j]-r;
end;
end;
// Делаю транспонирование матрицы
begin
for i:=1 to n do
for j:=1 to m do
D[i,j]:=A[j,i];
for i:=1 to n do
for j:=1 to m do
C[i,j]:=(1/det)*D[i,j];
begin
for i:=1 to n do
for j:=1 to m do
StringGrid_C.Cells[j-1,i-1]:=FloatToStr(C[i,j]) // вношу полученное значение в матрицу С
end;
end;


Красным отмечен участок, который я неправильно написал. Я просто транспонировал матрицу (заменил строки столбцами) и разделил каждый элемент на определитель, но это оказалось неправильным расчетом.

Вот пример расчета обратной матрицы.
Прикрепленное изображение


Здесь находят так называемые миноры, которые и образуют обратную матрицу.
В интернете много примеров расчета обратных матриц на паскале, но я не могу их понять и поэтому решил писать свою программу. Определитель посчитан, нужно разобраться как находить миноры, а потом их уже домножать как в примере на -1 в степени суммы индексов и делить на определитель, расположив в новой матрице.
В интернете это описывают так:
Цитата
"Создадим массив для хранения союзной матрицы. Думаю нужно создать цикл в цикле (перебор всех членов матрицы). можно создать еще один, временный массив в котором будем хранить минор. ну и все опять же вызываем функцию по нахождению определителя и вписываем результат в союзную матрицу."

Как написать код, чтобы найти эти миноры?

P.S.
Я знаю, что в Delphi есть функции, которые позволяют рассчитывать матрицы более проще, но мне хочется разобраться с минорами.
Go to the top of the page
 
+Quote Post
 
Start new topic
Ответов
Andbiz
сообщение Oct 3 2011, 18:10
Сообщение #2


Местный
***

Группа: Свой
Сообщений: 447
Регистрация: 16-11-08
Из: Украина, Донецк
Пользователь №: 41 684



Подредактировал программу. Сейчас ее код имеет следующий вид:

Код
              
                         begin
                         det:=1;
                         // начинаю прямой ход Гаусса
                         for k:=1 to n do
                         begin
                              det:=det*A[k,k]; //вычисление определителя
                              for j:=k+1 to n do
                              begin
                                   A[k,j]:=A[k,j]/A[k,k];
                              end;
                              for i:=k+1 to n do //начало вложенного цикла
                              for j:=k+1 to m do
                              begin
                              r:=A[k,j]*A[i,k];
                              A[i,j]:=A[i,j]-r;
                              end;
                         end;
                         Edit1.Text:=FloatToStr(det);
                         // Создаю союзную матрицу D
                         begin
                              for i:=1 to n do  // начинаю цикл обхода всех строк и столбиков матрицы А
                              for j:=1 to m do
                              begin
                                   l:=1;
                                   p:=1;
                                   for i_1:=1 to n do // начинаю второй цикл обхода матрицы А, в котором будут отсеиваться одна строчка и один столбик
                                   for j_1:=1 to m do
                                       if (i_1<>i) and (j_1<>j)  // отсеиваю элементы, которые находятся в столбике или строчке рассматриваемого элемента матрицы
                                       then
                                           begin
                                           D[l,p]:=A[i_1,j_1]; // вношу соответствующий элемент в временную матрицу D
                                           p:=p+1;  // прибавляю 1 к индексу столбика матрицы D
                                           if(p>(m-1)) // проверяю индекс столбика на крайнее значение, если оно больше (n-1) исходной таблицы, то перехожу на новую строку
                                           then
                                           begin
                                           p:=1;  // при начале новой строки столбик приравниваю единице
                                           l:=l+1;  // и на одну строчку опускаюсь вниз, прибавив к l единицу
                                           end;
                                           end;
                                               begin
                                               if (n-1)=1 then det_1:=D[1,1]  // если матрица еденичная, то определитель определить легком
                                               else
                                               if (n-1)=2 then det_1:=(D[1,1]*D[2,2]-D[1,2]*D[2,1])  // если матрица имеет размерность 2*2, то определитель можно найти по следующей формуле
                                               else
                                                    begin
                                                    det_1:=1;
                                                    // начинаю прямой ход Гаусса
                                                    for k:=1 to n-1 do
                                                        begin
                                                        det_1:=det_1*D[k,k];  //вычисление определителя
                                                        for p:=k+1 to n-1 do
                                                            begin
                                                                 D[k,p]:=D[k,p]/D[k,k];
                                                            end;
                                                            for l:=k+1 to n-1 do  //начало вложенного цикла
                                                            for p:=k+1 to m-1 do
                                                            begin
                                                                 r:=D[k,p]*D[l,k];
                                                                 D[l,p]:=D[l,p]-r;
                                                            end;
                                                        end;
                                                    end;
                                                        C[i,j]:=(power((-1),(i+j))*det_1)/det; // рассчитываю соответствующий элемент матрицы С
                                                        StringGrid_C.Cells[i-1,j-1]:=FloatToStr(C[i,j])  // вношу рассчитанный элемент в матрицу
                                               end;


Но расчет все равно не правильный. По поводу строчки C[i,j]:=((i+j)*ln(-1)*det_1)/det; находящейся вне цикла - не вижу, как она находится вне цикла... Проверяю через отладчик - строчка каждый раз после цикла присваивает элементам матрицы новые значения. Единственный их недостаток - значения неправильные.

Прикрепленное изображение


Определитель исходной матрицы Det находится верно и вроде как циклы в отладчике правильно проходят, но программа почему-то работает не так, как нужно. Что-то в ней не так...
Go to the top of the page
 
+Quote Post



Reply to this topicStart new topic
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 29th July 2025 - 16:45
Рейтинг@Mail.ru


Страница сгенерированна за 0.01425 секунд с 7
ELECTRONIX ©2004-2016