experiment 4

一、实验目的

  1. 能正确使用C语言定义、初始化、访问、输入/输出一维/二维数组
  2. 能正确使用数组作为函数参数
  3. 针对具体问题场景,能灵活用数组组织数据,设计算法编程解决实际问题

二、实验准备

实验前,请复习第5章以下内容:

  1. C语法规则:数组(一维/二维)的定义、初始化、访问
  2. C语法规则:数组作为函数参数时,函数的定义、声明、调用语法
  3. 冒泡排序算法

三、实验内容

1. 实验任务1

验证性实验。验证数组的特性:类型相同、有序存放。
在C开发环境下,输入如下程序。结合运行结果,理解代码、回答问题。
task1.c

task1.c

SHOW CODE

#include <stdio.h>
#define N 4
#define M 2

void test1() {
    int x[N] = {1, 9, 8, 4};          
    int i;

    // 输出数组x占用的内存字节数
    printf("sizeof(x) = %d\n", sizeof(x));

    // 输出每个元素的地址、值 
    for (i = 0; i < N; ++i)
        printf("%p: %d\n", &x[i], x[i]);

    // 输出数组名x对应的值 
	printf("x = %p\n", x); 
}

void test2() {
    int x[M][N] = {{1, 9, 8, 4}, {2, 0, 4, 9}};
    int i, j;

    // 输出二维数组x占用的内存字节数
    printf("sizeof(x) = %d\n", sizeof(x));

    // 输出每个元素的地址、值 
    for (i = 0; i < M; ++i)
        for (j = 0; j < N; ++j)
            printf("%p: %d\n", &x[i][j], x[i][j]);
    printf("\n");

    // 输出二维数组名x, 以及,x[0], x[1]的值
    printf("x = %p\n", x);
    printf("x[0] = %p\n", x[0]);
    printf("x[1] = %p\n", x[1]);
    printf("\n");
}

int main() {
    printf("测试1: int型一维数组\n");
    test1();

    printf("\n测试2: int型二维数组\n");
    test2();

    return 0;
}

//预览结果如图所示
QQ拼音截图20251110162532
问题一:连续存放且相同
问题二:按行连续存放;相同;4*4=16个字节;含义是二维数组中一行元素所占的内存字节数。

2. 实验任务2

验证性实验。验证一维数组作为函数参数的用法。
在C开发环境下,输入如下程序。结合运行结果,理解代码、回答问题。

task2.c

SHOW CODE


#include <stdio.h>
#define N 100

// 函数声明
void input(int x[], int n);
double compute(int x[], int n);

int main() {
    int x[N];
    int n, i;
    double ans;

    while(printf("Enter n: "), scanf("%d", &n) != EOF) {
        input(x, n);            // 函数调用
        ans = compute(x, n);    // 函数调用
        printf("ans = %.2f\n\n", ans);
    }

    return 0;
}

// 函数定义
void input(int x[], int n) {
    int i;

    for(i = 0; i < n; ++i)
        scanf("%d", &x[i]);
}

// 函数定义
double compute(int x[], int n) {
    int i, high, low;
    double ans;

    high = low = x[0];
    ans = 0;

    for(i = 0; i < n; ++i) {
        ans += x[i];

        if(x[i] > high)
            high = x[i];
        else if(x[i] < low)
            low = x[i];
    }

    ans = (ans - high - low)/(n-2);

    return ans;
}

//预览结果如图所示
QQ拼音截图20251110164125
问题一:void input(int x[],int n)中x[]和n是形参;input(x,n)中x和n是实参。
问题二:函数  input  的功能:通过循环遍历数组,接收用户输入的  n  个整数,将其存入数组  x  中
函数  compute  的功能:先计算数组所有元素的总和,同时找出数组中的最大值  high  和最小值  low ;然后用总和减去最大值和最小值,再除以  n-2 ,得到去掉最大值和最小值后的平均值,并返回该平均值。

3. 实验任务3

验证性实验。验证二维数组作为函数参数的用法。
在C开发环境下,输入如下程序。结合运行结果,理解代码、回答问题。

task3.c

SHOW CODE

#include <stdio.h>
#define N 100
// 函数声明
void output(int x[][N], int n);
void init(int x[][N], int n, int value);

int main() {
    int x[N][N];
    int n, value;

    while(printf("Enter n and value: "), scanf("%d%d", &n, &value) != EOF) {
        init(x, n, value);  // 函数调用
        output(x, n);       // 函数调用
        printf("\n");
    }

    return 0;
}

// 函数定义
void output(int x[][N], int n) {
    int i, j;

    for(i = 0; i < n; ++i) {
        for(j = 0; j < n; ++j)
            printf("%d ", x[i][j]);
        printf("\n");
    }
}

// 函数定义
void init(int x[][N], int n, int value) {
    int i, j;

    for(i = 0; i < n; ++i)
        for(j = 0; j < n; ++j)
            x[i][j] = value;
}

//预览效果如图所示
QQ拼音截图20251110164705
问题一:output(int x[][N], int n)中,int x[][N], int n为形参;output(x, n)中,x和n是实参
问题二:不能,二维数组的列不能省略
问题三: 函数  output  的功能:通过嵌套循环遍历二维数组的前  n  行  n  列,逐行打印数组中的元素,每行元素打印后换行。
函数  init  的功能:通过嵌套循环遍历二维数组的前  n  行  n  列,将所有元素赋值为指定的  value (即初始化二维数组的前  n×n  个元素为  value )

4. 实验任务4

编写程序,计算一组数据中值。
中值在统计学中定义如下:
一组数据集有序排序后,如果数据集个数是奇数,中值就是排序后位于正中间的那个数值;如果数据集个数是偶
数,排序后中值就是中间两个数均值。
例如:
{1, 2, 3, 4, 5}中值是3
{1, 2, 3, 4, 5, 6}中值是(3+4)/2 = 3.5
具体要求如下:
设计函数 median ,实现:计算n个整数的中值,并返回中值
设计函数 input , 实现: 从键盘录入n个整数
在 main 函数中编写主体代码逻辑:调用函数 input 完成数据录入,调用 median 获取中值,打印输出中值。

task4

SHOW CODE

#include <stdio.h>
#define N 100

// 函数声明
void input(int x[],int n);
double median(int x[],int n);

int main() {
    int x[N];
    int n;
    double ans;

    while(printf("Enter n: "), scanf("%d", &n) != EOF) {
        input(x, n);        // 函数调用
        ans = median(x, n); // 函数调用
        printf("ans = %g\n\n", ans);
    }

    return 0;
}

// 函数定义
void input(int x[],int n)
{
	int i;
	for(i=0;i<n;++i)
	scanf("%d",&x[i]);	
}

double median(int x[],int n){

int i,j,temp;
for(i=0;i<n-1;++i)
{
  for(j=0;j<n-1-i;++j)
   {
  
if(x[j]>x[j+i])
   {
	temp = x[j];
	x[j]=x[j+1];
	x[j+1]=temp;
    }
  }
}
if(n%2!=0){
	return (double)x[n/2];	
}
else{
	
    return (x[n/2-1]+x[n/2])/2.0;
}
}

//预览效果如图所示
image

5. 实验任务5

编写程序,实现数值阵列处理。具体要求如下:
设计、编写函数 rotate_to_right ,实现将一个n×n (n <= 100)的方阵,按列循环右移。最右边一列数据绕回
左边。image

在 main 中编写主体代码:输出原始方阵,调用 rotate_to_right 按列循环右移,输出变换后方阵。

task5.c:

SHOW CODE

#include <stdio.h>
#define N 100

// 函数声明
void input(int x[][N], int n);
void output(int x[][N], int n);
// 函数rotate_to_right声明
void  rotate_to_right(int x[][N],int n) ;
// ×××

int main() {
    int x[N][N];
    int n;

    printf("输入n: "); 
    scanf("%d", &n);
    input(x, n);

    printf("原始矩阵:\n");
    output(x, n);

    // 函数rotate_to_right调用
    rotate_to_right(x,n) ;

    printf("变换后矩阵:\n");
    output(x, n);

    return 0;
}

// 函数定义
// 功能: 输入一个n*n的矩阵x
void input(int x[][N], int n) {
    int i, j;
    
    for (i = 0; i < n; ++i) {
        for (j = 0; j < n; ++j)
            scanf("%d", &x[i][j]);
    }
}

// 函数定义
// 功能: 输出一个n*n的矩阵x
void output(int x[][N], int n) {
    int i, j;

    for (i = 0; i < n; ++i) {
        for (j = 0; j < n; ++j)
            printf("%4d", x[i][j]);

        printf("\n");
    }
}

// 函数rotate_to_right定义
// 功能: 把一个n*n的矩阵x,每一列向右移, 最右边一列绕回左边
// 实现列循环右移
 void rotate_to_right(int x[][N], int n) {
     int i;
     int last_col[N];
     int j;
     for (i = 0; i < n; ++i) {
         last_col[i] = x[i][n-1];
     }
     // 列右移
     for (j = n-1; j > 0; --j) {
         for (i = 0; i < n; ++i) {
             x[i][j] = x[i][j-1];
         }
     }
     // 最右列放最左列
     for (i = 0; i < n; ++i) {
         x[i][0] = last_col[i];
     }
 }

//预览效果如图所示

image

6. 实验任务6

编写程序,实现进制转换。具体要求如下:
编写函数 dec_to_n ,实现把十进制整数x转换成n进制输出。(n限定取2, 8, 16)
在 main 函数中编写主体代码逻辑:从键盘输入n,调用 dec_to_n ,把十进制整数转换成二进制、八进制、十
六进制输出。
不使用格式符%o, %x

task.6

SHOW CODE

#include <stdio.h>
#define N 100

// 函数声明
void dec_to_n(int x, int n);

int main() {
    int x;
    while (printf("输入十进制整数:"), scanf("%d", &x) != EOF) {
        dec_to_n(x, 2);   // 转二进制
        dec_to_n(x, 8);   // 转八进制
        dec_to_n(x, 16);  // 转十六进制
        printf("\n");
    }
    return 0;
}

// 函数定义:十进制转n进制(n=2,8,16)
void dec_to_n(int x, int n) {
    int remainder, i = 0;
    int result[N]; 
    int temp = x;  

    while (temp != 0) {
        remainder = temp % n;
        result[i++] = remainder;
        temp = temp / n;
    }

    printf("%d转%d进制:", x, n);
    int j;
    for ( j = i - 1; j >= 0; j--) {
 
        if (n == 16 && result[j] >= 10) {
            printf("%c", 'A' + result[j] - 10);
        } else {
            printf("%d", result[j]);
        }
    }
    printf("\n");
}

//预览结果如下
image

7. 实验任务7

编程判断魔方矩阵。
魔方矩阵定义如下:
魔方矩阵,是一个n×n(n为奇数)的方阵。其元素值为1, 2, 3, 4, ...,n
这些元素在矩阵中的位置要确保方阵每行、每列、每条对角线上的和都相等。
程序编写要求如下:
设计、编写函数is_magic,用于判断一个n阶方阵是否为魔方矩阵,如果是,返回1; 否则,返回0
在main中编写主体代码逻辑
输入n
// xxx 23
调用函数input从键盘输入n阶方阵x
调用函数output输出n阶方阵x
调用函数is_magic判断n阶方阵x

task 7

SHOW CODE

#include <stdio.h>
#define N 100

// 函数声明
void input(int x[][N], int n);
void output(int x[][N], int n);
int is_magic(int x[][N], int n); // 补充is_magic声明

int main() {
    int x[N][N];
    int n;

    while(printf("输入n:"), scanf("%d", &n) != EOF) {
        printf("输入方阵:\n");
        input(x, n);
        printf("输出方阵:\n");
        output(x, n);
        
        if(is_magic(x, n))
            printf("是魔方矩阵\n\n");
        else
            printf("不是魔方矩阵\n\n");
    }
    return 0;
}

// 输入n阶方阵
void input(int x[][N], int n) {
    int i, j;
    for (i = 0; i < n; ++i) {
        for (j = 0; j < n; ++j)
            scanf("%d", &x[i][j]);
    }
}

// 输出n阶方阵
void output(int x[][N], int n) {
    int i, j;
    for (i = 0; i < n; ++i) {
        for (j = 0; j < n; ++j)
            printf("%d ", x[i][j]);
        printf("\n");
    }
}

// 判断是否为魔方矩阵
int i,j;
int is_magic(int x[][N], int n) {
    if (n % 2 == 0) return 0;

    int target_sum = n * (n * n + 1) / 2;
  
    for (i = 0; i < n; ++i) {
        int row_sum = 0;
        for ( j = 0; j < n; ++j) {
            row_sum += x[i][j];
        }
        if (row_sum != target_sum) return 0;
    }

    for ( j = 0; j < n; ++j) {
        int col_sum = 0;
        for ( i = 0; i < n; ++i) {
            col_sum += x[i][j];
        }
        if (col_sum != target_sum) return 0;
    }

    int diag1_sum = 0;
    for (i = 0; i < n; ++i) {
        diag1_sum += x[i][i];
    }
    if (diag1_sum != target_sum) return 0;

    int diag2_sum = 0;
    for (i = 0; i < n; ++i) {
        diag2_sum += x[i][n - 1 - i];
    }
    if (diag2_sum != target_sum) return 0;

    int exist[N*N + 1] = {0}; 
    for (i = 0; i < n; ++i) {
        for (j = 0; j < n; ++j) {
            int val = x[i][j];
            if (val < 1 || val > n*n || exist[val]) {
                return 0;
            }
            exist[val] = 1;
        }
    }

    return 1; 
}

//预览效果如图所示
![image](https://img2024.cnblogs.com/blog/3708066/202511/3708066-20251116183024408-500863713.png)
posted @ 2025-11-16 18:33  Luckynar  阅读(3)  评论(0)    收藏  举报