【发布时间】:2016-07-29 07:29:01
【问题描述】:
我正在编写代码来读取文件并将数字存储在数组中。代码本身正在工作,但数字没有正确存储在数组中,因此,我没有得到所需的输出。这是我的代码:
/* code to solve a nxn system using the Gauss-Seidel method */
#include <stdio.h>
#include <math.h>
#include <stdlib.h>
#include <malloc.h>
#define MAX_DIM 100
#define MAX_ITER 500
#define TOLERANCE 1.e-6
void gauss_seidel(double **a, double b[], double x[], int n);
void main()
{
int i, j, n;
int violation_counter, answer;
double sum;
/* read in data */
n = MAX_DIM + 1;
FILE *inf, *onf;
char fileName[256];
printf("Enter file Name: ");
scanf("%s", fileName);
inf = fopen(fileName, "r");
if(inf != NULL){
while (n > MAX_DIM) {
fscanf(inf, "%d", &n);
}
int *violation_rows = (int *)malloc(sizeof(int) * n);
double **a = (double **)malloc(sizeof(double *) * n);
double *b = (double *)malloc(sizeof(double) * n);
double *x = (double *)malloc(sizeof(double) * n);
for(i = 0; i < n; ++i){
a[i] = (double *)malloc(sizeof(double) * n);
}
for (i = 0; i < n; i++) {
for (j = 0; j < n; j++) {
fscanf(inf, "%lf", &a[i][j], sizeof(a[i][j]));
printf("%.2lf ", a[i][j]);
}
fscanf(inf, "%lf", &b[i], sizeof(b[i]));
printf("-> %.2lf\n", b[i]);
}
printf("\n");
/* test the convergence criterion */
violation_counter = 0;
for (i = 0; i < n; i++) {
sum = 0.0;
for (j = 0; j < n; j++)
if (i != j)
sum = sum + fabs(a[i][j]);
if (fabs(a[i][i]) < sum) {
violation_rows[violation_counter] = i;
violation_counter = violation_counter + 1;
}
if (a[i][i] == 0.0) {
printf("Found diagonal element equal to zero; rearrange equations; exiting ...\n");
exit(0);
}
}
if (violation_counter > 0) {
printf("The Gauss-Seidel convergence criterion is violated in %d rows out of %d\n", violation_counter, n);
printf("Specifically, it was violated in rows:\n");
for (i = 0; i < violation_counter; i++)
printf("%d ", violation_rows[i]);
printf("\n");
printf("Enter 1 if you want to continue; any other number to abort : ");
scanf("%d", &answer);
if (answer != 1)
exit(1);
printf("Check results carefully\n\n");
}
/* initialize the solution vector -- initial guesses */
for (i = 0; i < n; i++) {
fscanf(inf, "%lf", &x[i], sizeof(x[i]));
printf("x[%d] = %.2lf\n", i, x[i]);
}
fclose(inf);
/* solve the system */
gauss_seidel(a, b, x, n);
/* output solution */
printf("Enter file Name: ");
scanf("%s", fileName);
onf = fopen(fileName, "w");
for (i = 0; i < n; i++)
fprintf(onf, "x[%d]=%f\n", i, x[i]);
fprintf(onf, "\n");
fclose(onf);
}
else{
printf("Can not open %s to read\n", fileName);
}
return;
}
代码的输出未正确存储数字。比如我的文本文件如下:
4
2 -1 0 0
-1 3 -2 0
0 -2 5 -3
0 0 -3 3
1
1.5
2.5
1.5
0
0
0
0
我得到的结果是
2 -1 0 0 -> -1
3 -2 0 0 -> -2
5 -3 0 0 -> -3
3 1 1.5 2.5 -> 1.5
以及对角收敛误差。是什么导致文件无法正确存储?
编辑:4x4 行之后的数字(第三块中的四个:1、1.5、2.5、1.5)应该位于箭头的另一侧。
【问题讨论】:
-
sizeof调用中的sizeof参数应该做什么?它们是多余的。 -
我认为您有嵌套错误。您应该首先使用嵌套循环读取所有
a[j][i],然后在单独的循环中读取所有b[i]。您在阅读a[j][i]的同一个 lop 中阅读了b[i],但输入文件似乎没有这样组织。 (除非是误解了输入格式。) -
@MOehm 我认为它们可能会帮助定义每行的大小,以便代码知道何时中断。另外,您是否建议为
b[i]使用完全独立的for循环? -
打开警告,您将了解到不需要
sizeof参数。 Plainfscanf是一个比较粗糙的扫描功能;要扫描的数据大小必须通过大小修饰符给出,在您的情况下,%lf中的l。 -
是的,我建议一个单独的循环。流是按行排列的,从左到右。您的代码必须以相同的方式读取数据。我还建议将打印与扫描分开并扫描所有内容,包括前面的
x。