#1
by Serdol » 7年前
http://kazuhirokazu.org/2014/01/13/c%E8 ... %E3%82%8B/
上記サイトをほぼそのまま使って逆行列の計算を行おうとしたところ、
{2, 4, -2, -4, 1, 0, 0, 0},
{-6, -12, 12, 24, 0, 1, 0, 0},
{4, 2, 2, -4, 0, 0, 1, 0},
{2, -4, -2, 4, 0, 0, 0, 1}};
でうまく逆行列が出力されません。(サイトの数値をそのまま使った場合はうまくいきました)
以下のように出力されます。
1.000000 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00
-1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00
0.000000 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00
-1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00
出力を付け足した以外は特に何も変えていないのですが、なぜか入力例が変わった途端に上手くいきません
原因を調べたところpivotの値がループの2周目からおかしいということはわかりましたが、なぜなのかわかりません。
よろしくお願いします。
ほとんどサイトのままですが、一応ソースを載せておきます
コード:
#include <stdio.h>
#define N 4
int main(void)
{
double M[N][N * 2] ={
{2, 4, -2, -4, 1, 0, 0, 0},
{-6, -12, 12, 24, 0, 1, 0, 0},
{4, 2, 2, -4, 0, 0, 1, 0},
{2, -4, -2, 4, 0, 0, 0, 1}};
double mul;
double pivot;
int i,j,k,n;
// 対角成分が1で正規化された階段行列を作る
for (i = 0; i < N; ++i)
{
// 対角成分の選択、この値で行成分を正規化
pivot = M[i][i];
for (j = 0; j < N * 2; ++j)
{
M[i][j] = (1 / pivot) * M[i][j];
}
// 階段行列を作る為に、現在の行より下の行につ
// i列目の成分が0になるような基本変形をする
for (k = i + 1; k < N; ++k)
{
mul = M[k][i];
for (n = i; n < N * 2; ++n)
{
M[k][n] = M[k][n] - mul * M[i][n];
}
}
}
// 下から上に向かって変数に代入して、左側について
for (i = N - 1; i > 0; --i)
{
for (k = i - 1; k >= 0; --k)
{
mul = M[k][i];
for (n = i; n < N * 2; ++n)
{
M[k][n] = M[k][n] - mul * M[i][n];
}
}
}
for( i = 0; i<N;i++) {
for(j=0;j<2*N;j++) {
printf(" %f",M[i][j]);
}
printf("\n");
}
return 0;
}
http://kazuhirokazu.org/2014/01/13/c%E8%A8%80%E8%AA%9E%E3%81%A7%E9%80%86%E8%A1%8C%E5%88%97%E3%82%92%E6%B1%82%E3%82%81%E3%82%8B/
上記サイトをほぼそのまま使って逆行列の計算を行おうとしたところ、
{2, 4, -2, -4, 1, 0, 0, 0},
{-6, -12, 12, 24, 0, 1, 0, 0},
{4, 2, 2, -4, 0, 0, 1, 0},
{2, -4, -2, 4, 0, 0, 0, 1}};
でうまく逆行列が出力されません。(サイトの数値をそのまま使った場合はうまくいきました)
以下のように出力されます。
1.000000 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00
-1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00
0.000000 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00
-1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00 -1.#IND00
出力を付け足した以外は特に何も変えていないのですが、なぜか入力例が変わった途端に上手くいきません
原因を調べたところpivotの値がループの2周目からおかしいということはわかりましたが、なぜなのかわかりません。
よろしくお願いします。
ほとんどサイトのままですが、一応ソースを載せておきます
[code]
#include <stdio.h>
#define N 4
int main(void)
{
double M[N][N * 2] ={
{2, 4, -2, -4, 1, 0, 0, 0},
{-6, -12, 12, 24, 0, 1, 0, 0},
{4, 2, 2, -4, 0, 0, 1, 0},
{2, -4, -2, 4, 0, 0, 0, 1}};
double mul;
double pivot;
int i,j,k,n;
// 対角成分が1で正規化された階段行列を作る
for (i = 0; i < N; ++i)
{
// 対角成分の選択、この値で行成分を正規化
pivot = M[i][i];
for (j = 0; j < N * 2; ++j)
{
M[i][j] = (1 / pivot) * M[i][j];
}
// 階段行列を作る為に、現在の行より下の行につ
// i列目の成分が0になるような基本変形をする
for (k = i + 1; k < N; ++k)
{
mul = M[k][i];
for (n = i; n < N * 2; ++n)
{
M[k][n] = M[k][n] - mul * M[i][n];
}
}
}
// 下から上に向かって変数に代入して、左側について
for (i = N - 1; i > 0; --i)
{
for (k = i - 1; k >= 0; --k)
{
mul = M[k][i];
for (n = i; n < N * 2; ++n)
{
M[k][n] = M[k][n] - mul * M[i][n];
}
}
}
for( i = 0; i<N;i++) {
for(j=0;j<2*N;j++) {
printf(" %f",M[i][j]);
}
printf("\n");
}
return 0;
}
[/code]