"Математика и алгоритмы". Выпуск 4.
Обратимся теперь непосредственно к реализации численных методов решения
систем линейных алгебраических уравнений.
Для начала рассмотрим самый простой в реализации метод Гаусса.
Вот соответствующая часть кода (некоторые куски программы выброшены, например
функции выделения памяти):
float *x; // Вектор решений
float **m1; // Матрица коэффициентов
float b; // Вектор свободных членов
/ необходимо выделить память под массивы */
// теперь обнуляем массивы
for (i=0;i<m;i++) x[i]=0;
for (i=0;i<m;i++)
for (j=0;j<0;j++)
m1[i][j]=0;
for (i=0;i<m;i++) b[i]=0;
// заносим матрицу коэффициентов
m1[0][0] = 1; m1[0][1] = 2; m1[0][2] = 0; m1[0][3] = 0;
m1[1][0] = 0; m1[1][1] = 1; m1[1][2] = 2; m1[1][3] = 0;
m1[2][0] = 0; m1[2][1] = 0; m1[2][2] = 1; m1[2][3] = 2;
m1[3][0] = 0; m1[3][1] = 0; m1[3][2] = 0; m1[3][3] = 1;
// вектор совбодных членов
b[0]=5;
b[1]=8;
b[2]=11;
b[3]=4.1;
for (i=0;i<m;i++)
// Прямой ход
// Смещение индексов на -1 (от счетчика цикла к индексу матрицы)
for (i=1;i<=(m-1);i++)
for (j=i+1;j<=m;j++)
{ m1[j-1][i-1]=-m1[j-1][i-1]/m1[i-1][i-1];
for (k=(i+1);k<=m;k++)
m1[j-1][k-1]=m1[j-1][k-1]+m1[j-1][i-1]*m1[i-1][k-1];
b[j-1]=b[j-1]+m1[j-1][i-1]*b[i-1];
}
// Обратный ход
x[m-1]=b[m-1]/m1[m-1][m-1];
for (i=(m-1);i>=1;i--)
{ h=b[i-1];
for (j=(i+1);j<=m;j++)
h=h-x[j-1]*m1[i-1][j-1];
x[i-1]=h/m1[i-1][i-1];
}
for (i=0;i<m;i++)
cout << "\n x[" << i << "] = " << x[i];
float csumm = 0;
cout << "\n Нестыковка по уравнениям: ";
for (i=0;i<m;i++)
{ cout << "\n EQ#" << i <<": ";
csumm = 0;
for (j=0;j<m;j++) csumm = csumm + m1[i][j]*x[j];
cout << csumm-b[i];
}
Примерно так можно реализовать метод Гаусса. Отмечу, что это далеко не оптимальная
программа. Но она достаточно понятна, так как не использует различные
программистские "хитрости".