在C中通过引用传递二维数组

我需要家庭作业问题的帮助。

作业的描述是:

使用参考调用方法在C中设计程序,该方法生成由一个学期内给出的M个学生和N个测验组成的class级的成绩统计。 测验都具有相同的权重,每个测验中的分数不超过10分。 程序执行时,程序将按指示的顺序执行以下操作:

  1. 要求用户在键盘上键入学生数M和测验数N,其中M代表行数,N代表二维数组中的列数x [M] [N] of浮点数字。
  2. 要求用户在键盘上键入数组x [M] [N]的所有元素的值。
  3. 在控制台上显示输入的数组元素值的M行和N列。
  4. 在控制台上生成并显示一维数组p [M]的元素,其中该数组p [M]的每个元素代表M个学生中每个学期的平均成绩。
  5. 在控制台上生成并显示一维数组q [N]的元素,其中q [N]的每个元素代表N个测验中每个类中的平均等级。
  6. 在整个学期中,在控制台上生成并显示整个class级的平均成绩z。

这是我到目前为止所做的代码:

#include  #define students 300 #define quizzes 20 void averageGradeOfStudents(int M, int N, float p[], float *xPtr); float averageGradeOfClass(); float averageGradeOfWholeClass(); int main() { int M, N; float x[students][quizzes]; printf("Enter the number students (Maximum: 300): "); scanf_s("%d", &M); printf("\nEnter the number of Quizzes (Maximum: 20): "); scanf_s("%d", &N); for (int i = 0; i < M; i++) { for (int k = 0; k < N; k++) { printf("Enter the grade for student %d, Quiz %d: ", i, k); scanf_s("%f", &x[i][k]); } } printf("\n--------------------------------------------------------------------------------\n\n"); for (int k = 1; k <= N; k++) { printf("\t\tQuiz%d", k); } for (int i = 0; i < M; i++) { printf("\nStudent%d Grades: ", i); for (int k = 0; k < N; k++) { printf("%.2f\t\t", x[i][k]); } } printf("\n\n\n--------------------------------------------------------------------------------\n\n"); float p[students]; averageGradeOfStudents(M, N, p, &x[0][0]); float q[quizzes]; float z; getchar(); return 0; } void averageGradeOfStudents(int M, int N, float p[], float *xPtr) { float grade[students]; for (int i = 0; i < M; i++) { for (int k = 0; k < N; k++) { grade[i] += *(xPtr + i); } } for (int k = 0; k < M; k++) { p[k] = grade[k] / N; printf("The average grade of student%d is: %.2f\n\n", k, p[k]); } } float averageGradeOfClass() { } float averageGradeOfWholeClass() { } 

我遇到的问题是我无法找到一种方法来单独对数组的每一行求和。

你的任务进展非常好。 获得完整的代码和工作令人耳目一新。 在我们达到平均水平之前,有一些事情会有所帮助。 首先,始终是好的做法, 初始化你的变量 。 对于数组尤其如此,因为它可以防止意外尝试从未初始化的值读取,并且在字符数组的情况下可以为第一个副本提供自动的空终止 (只要您只复制size-1个字符) )。

  int M = 0, N = 0; float x[students][quizzes] = {{ 0 }}; float p[students] = {0}; float q[quizzes] = {0}; float z = 0; 

传递数组始终是一个问题领域。 传递声明为2D数组的数组时,必须将数组的宽度作为函数参数的一部分传递:

 void averageGradeOfStudents (int M, int N, float p[], float xPtr[][quizzes]); 

然后你可以通过传递数组本身来简单地调用函数。

  averageGradeOfStudents (M, N, p, x); 

注意:当作为函数参数传递时,任何数组的第一级间接转换为指针,但这是后续问题的主题。但是,为了您的参考,您的函数声明也可以正确编写为):

 void averageGradeOfStudents (int M, int N, float p[], float (*xPtr)[quizzes]); 

现在接近你的平均值,你很接近,你只需要通过改变你索引xPtr的方式(并初始化grade的值)来对每个学生的元素求和:

 void averageGradeOfStudents (int M, int N, float p[], float xPtr[][quizzes]) { float grade[M]; /* initialize variable length array to 0 */ for (int i = 0; i < M; i++) grade[i] = 0; /* sum of grades for each student */ for (int i = 0; i < M; i++) { for (int k = 0; k < N; k++) { grade[i] += xPtr[i][k]; } } printf ("The average grades for the students are:\n\n"); for (int k = 0; k < M; k++) { p[k] = grade[k] / N; printf(" student[%3d] is: %6.2f\n", k, p[k]); } } 

在完整代码中使用它的一个简单示例可能是:

 #include  #define students 300 #define quizzes 20 void averageGradeOfStudents (int M, int N, float p[], float (*xPtr)[quizzes]); int main (void) { /* good habit -- always initialize your variables */ int M = 0, N = 0; float x[students][quizzes] = {{ 0 }}; float p[students] = {0}; printf("Enter the number students (Maximum: 300): "); scanf ("%d", &M); printf("\nEnter the number of Quizzes (Maximum: 20): "); scanf ("%d", &N); for (int i = 0; i < M; i++) { for (int k = 0; k < N; k++) { printf("Enter the grade for student %d, Quiz %d: ", i, k); scanf("%f", &x[i][k]); } } printf("\n--------------------------------------------------------------------------------\n\n"); printf (" "); for (int k = 1; k <= N; k++) { printf(" Quiz%-2d", k); } putchar ('\n'); for (int i = 0; i < M; i++) { printf("\n Student[%3d] Grades: ", i); for (int k = 0; k < N; k++) { printf(" %6.2f", x[i][k]); } } printf("\n\n--------------------------------------------------------------------------------\n\n"); averageGradeOfStudents (M, N, p, x); /* getchar(); */ return 0; } void averageGradeOfStudents (int M, int N, float p[], float (*xPtr)[quizzes]) { float grade[M]; /* initialize variable length array to 0 */ for (int i = 0; i < M; i++) grade[i] = 0; /* sum of grades for each student */ for (int i = 0; i < M; i++) { for (int k = 0; k < N; k++) { grade[i] += xPtr[i][k]; } } printf ("The average grades for the students are:\n\n"); for (int k = 0; k < M; k++) { p[k] = grade[k] / N; printf(" student[%3d] is: %6.2f\n", k, p[k]); } putchar ('\n'); } 

使用/输出

 $ ./bin/studentavg Enter the number students (Maximum: 300): 3 Enter the number of Quizzes (Maximum: 20): 3 Enter the grade for student 0, Quiz 0: 8 Enter the grade for student 0, Quiz 1: 9 Enter the grade for student 0, Quiz 2: 8 Enter the grade for student 1, Quiz 0: 9 Enter the grade for student 1, Quiz 1: 9 Enter the grade for student 1, Quiz 2: 10 Enter the grade for student 2, Quiz 0: 7 Enter the grade for student 2, Quiz 1: 8 Enter the grade for student 2, Quiz 2: 9 -------------------------------------------------------------------------------- Quiz1 Quiz2 Quiz3 Student[ 0] Grades: 8.00 9.00 8.00 Student[ 1] Grades: 9.00 9.00 10.00 Student[ 2] Grades: 7.00 8.00 9.00 -------------------------------------------------------------------------------- The average grades for the students are: student[ 0] is: 8.33 student[ 1] is: 9.33 student[ 2] is: 8.00 

注意:我已将scanf_s更改为我的系统的scanf ,您需要将其更改回来。 如果您还有其他问题,请与我们联系。

在你知道M和N的值之前我不会声明数组。所以main的第一部分如下所示。 (这也允许您转储studentsquizzes常量。)并始终检查库函数的返回值。

 int main( void ) { int M, N; printf("Enter the number students (Maximum: 300): "); if ( scanf_s("%d", &M) != 1 || M > 300 ) { printf( "Whatever\n" ); exit( 1 ); } printf("\nEnter the number of Quizzes (Maximum: 20): "); if ( scanf_s("%d", &N) != 1 || N > 20 ) { printf( "Sigh...\n" ); exit( 1 ); } float x[M][N]; // ... } 

将数组传递给函数时,可以使用数组表示法。 并且您可以省略数组的第一个维度。 所以以下两个函数声明都是有效的

 void averageGradeOfStudents(int M, int N, float p[M], float x[M][N]); void averageGradeOfStudents(int M, int N, float p[], float x[][N]); 

在function内部,存在一些问题

  • grade[i]在使用之前未初始化(这应该导致编译器警告)
  • 每个grade[i]应该是N个等级的平均值(用k而不是i
  • 你不需要grade数组,因为你已经拥有了p数组

这是我将如何编写函数(我更改了索引名称以保持我的行和列清晰)

 void averageGradeOfStudents(int M, int N, float p[], float x[][N]) { for (int row = 0; row < M; row++) { p[row] = 0; // initialize the sum to zero for (int col = 0; col < N; col++) { p[row] += x[row][col]; // update the sum with each test result } p[row] /= N; // convert the sum to the average } for (int row = 0; row < M; row++) { printf("The average grade of student%d is: %.2f\n\n", row, p[row]); } } 

并且应该调用该函数

 averageGradeOfStudents(M, N, p, x); 

对数组求和是一个相当普遍的习语:

 double sumArray(double arr[], int arrLen) { int i; double sum = 0.0; for (i = 0; i < arrLen; i++) sum += arr[i]; return sum; } 

这对一维数组求和,但请记住,数组x每一行都是一维数组。

 int avg=0; int sum=0; for (int i = 0; i < M; i++) { for (int k = 0; k < N; k++) { printf("Enter the grade for student %d, Quiz %d: ", i, k); scanf("%f", &x[i][k]); sum=sum+x[i][k] } }avg=sum/M; 

为了得到平均值,你必须总结...尝试这可能会帮助你