课后作业

2024/1/13

# 第十一课

# 1. 编写一个 C++程序,创建并自定义初始化一个m x n的二维整数数组(mn都小于或等于10)。找出数组中的最大元素及其所在的行和列。

自定义二维数组,不需要输入

// 自定义示例:(题解不可同示例相同)
int matrix[3][3] = {
    {1, 2, 3},
    {4, 5, 6},
    {7, 8, 9}
};
// 输出:
最大元素是 9,位于第 3 行第 3 列。
  • 历史解析

    • 数组越界for 循环中,ij 的循环条件设置为 i <= 3j <= 3这是不正确的,因为数组的索引应该从 02。所以正确的条件应该是 i < 3j < 3
    • 多余的循环:内部的 k 循环是多余的。你只需要比较 maxc[i][j]high 的值即可,不需要额外的循环。
    • 判断逻辑错误: 当前的循环判断并未找出数组中的最大元素,仅仅是不断循环后单纯的判断high与最里层循环k的最终值,即只是单纯的比较19(还是在maxc[0][0]=1的情况下)
    • 自行检查错误:当程序打印后应按题目要求更新示例数组尝试查看是否符合说明,当将maxc[2][2]或任意一项更新为更大的数时,程序依旧打印9
  • 参考答案

#include <iostream>
using namespace std;
int main(){
    int maxc[3][3] = {
        {1, 2, 3},
        {4, 15, 6},
        {7, 8, 9}
    };
    int high = maxc[0][0];
    int endi = 0, endj = 0;
    for (int i = 0; i < 3; i++) {
        for (int j = 0; j < 3; j++) {
            if (maxc[i][j] > high) {
                high = maxc[i][j];
                endi = i;
                endj = j;
            }
        }
    }
    cout << "最大元素是 " << high << ",位于第 " << (endi + 1) << " 行第 " << (endj + 1) << " 列" << endl;
    return 0;
}

# 2. 编写一个 C++程序,创建并自定义初始化一个m x n的二维整数数组(mn都小于或等于10)。计算并输出每一行元素的总和以及每一列元素的总和。

自定义二维数组,不需要输入

// 自定义示例:(题解不可同示例相同)
int matrix[2][3] = {
    {1, 2, 3},
    {4, 5, 6}
};
// 输出:1 的总和: 62 的总和: 151 的总和: 52 的总和: 73 的总和: 9
  • 历史解析

    • 运行错误:程序运行报错,完成程序编写后应至少自行运行检查一次
    • 数组定义和初始化错误:在定义数组maxc时,元素列表之间应该用逗号分隔
    • 数组越界:循环中数组的索引超出了其定义的范围。对于一个2x3数组,有效的索引是matrix[0][0]matrix[1][2]
    • 计算逻辑错误:行和列的总和计算不正确。对于行总和,应遍历每一行的所有列;对于列总和,应遍历每一列的所有行
    • 打印格式:建议用cout,避免发生format错误
  • 参考答案

#include <iostream>
using namespace std;
int main() {
    int matrix[2][3] = {
        {1, 2, 3},
        {4, 5, 6}
    };
    // 计算每一行的总和
    for (int i = 0; i < 2; ++i) {
        int rowSum = 0;
        for (int j = 0; j < 3; ++j) {
            rowSum += matrix[i][j];
        }
        cout << "行 " << i + 1 << " 的总和: " << rowSum << endl;
    }
    // 计算每一列的总和
    for (int j = 0; j < 3; ++j) {
        int colSum = 0;
        for (int i = 0; i < 2; ++i) {
            colSum += matrix[i][j];
        }
        cout << "列 " << j + 1 << " 的总和: " << colSum << endl;
    }
    return 0;
}

# 3. 编写一个 C++程序,创建一个n x n的整数矩阵,并初始化它。然后计算并输出这个矩阵主对角线(从左上到右下)和副对角线(从右上到左下)上的元素之和。假设n是一个小于或等于10的正整数。

自定义二维数组,不需要输入

// 自定义示例:(题解不可同示例相同)
int matrix[4][4] = {
    {1, 2, 3, 4},
    {5, 6, 7, 8},
    {9, 10, 11, 12},
    {13, 14, 15, 16}
};
// 输出:
主对角线之和: 34
副对角线之和: 34
  • 解析

    • 主对角线之和计算
      • 主对角线是指矩阵从左上角到右下角的那条对角线
      • 在一个n x n的矩阵中,主对角线上的元素都是那些行索引和列索引相等的元素,即元素matrix[i][i],其中i是从 0n-1的索引
      • 在此程序中,n4,所以我们需要计算matrix[0][0], matrix[1][1], matrix[2][2], 和 matrix[3][3]
      • 循环中使用mainDiagonalSum += matrix[i][i];做这个计算
    • 副对角线之和计算
      • 副对角线是指矩阵从右上角到左下角的那条对角线
      • 在一个n x n的矩阵中,副对角线上的元素是那些行索引和列索引之和等于n-1的元素,即元素matrix[i][n-1-i]
      • 在此程序中,对于 4x4 的矩阵,需要计算的是matrix[0][3], matrix[1][2], matrix[2][1], 和 matrix[3][0]
      • 循环中使用secondaryDiagonalSum += matrix[i][3 - i];做这个计算
  • 参考答案

#include <iostream>
using namespace std;
int main() {
    int matrix[4][4] = {
        {1, 2, 3, 4},
        {5, 6, 7, 8},
        {9, 10, 11, 12},
        {13, 14, 15, 16}
    };
    int mainDiagonalSum = 0, secondaryDiagonalSum = 0;
    for (int i = 0; i < 4; ++i) {
        mainDiagonalSum += matrix[i][i];
        secondaryDiagonalSum += matrix[i][3 - i];
    }
    cout << "主对角线之和: " << mainDiagonalSum << endl;
    cout << "副对角线之和: " << secondaryDiagonalSum << endl;
    return 0;
}

# 4. 编写一个 C++程序,完成以下任务:

    1. 定义一个字符数组 char myArray[10]; 并使用字符初始化数组,使其包含 "Hello"。
    1. 使用循环输出数组 myArray 的每个字符。
    1. 更改 myArray 中的第三个字符('l')为 'x',然后再次输出整个数组。
// 输出示例
H e l l o
H e x l o
  • 历史解析

    • 运行错误:程序运行报错,完成程序编写后应至少自行运行检查一次
    • 字符数组的初始化:当初始化字符数组时,应使用单引号 ' ' 而非双引号 " ", 因为双引号用于字符串字面量,而单引号用于单个字符。数组 mychar 中包含超过5个字符Hello!,但题目只要求包含 Hello
    • 循环输出数组:循环条件应该是遍历数组的有效长度,即字符串 Hello 的长度,抑或是数组长度,而非固定的 18。没有必要定义j我们可以直接循环数组内容打印。检查 if(i == "") 是无效的,因为 i 是整数,不能与空字符串比较。
    • 修改数组中的字符: 要将第三个字符(索引为 2)更改为 x,应该使用单引号
  • 参考答案

#include <iostream>
using namespace std;
int main() {
    const int n=10;
    char myArray[n] = "Hello";
    // 输出数组的每个字符
    for (int i = 0; i<n; i++) {
        cout << myArray[i] << ' ';
    }
    cout << "\n";
    myArray[2] = 'x'; // 更改第三个字符为 'x'
    // 再次输出修改后的数组
    for (int i = 0; i<n; i++) {
        cout << myArray[i] << ' ';
    }
    cout << "\n";
    return 0;
}
// 利用结束符
#include <iostream>
using namespace std;
int main() {
    char myArray[10] = {'H', 'e', 'l', 'l', 'o', '\0'}; // 初始化数组,包含字符串 "Hello" 和结束符 '\0'
    // 输出数组的每个字符
    for (int i = 0; myArray[i] != '\0'; i++) {
        cout << myArray[i] << ' ';
    }
    cout << "\n";
    myArray[2] = 'x'; // 更改第三个字符为 'x'
    // 再次输出修改后的数组
    for (int i = 0; myArray[i] != '\0'; i++) {
        cout << myArray[i] << ' ';
    }
    cout << "\n";
    return 0;
}

# 5. 编写一个 C++程序,执行以下操作:

    1. 使用 string 类型定义一个字符串 str,并初始化为 "Welcome to C++ !"。
    1. 输出字符串 str 的长度。
    1. str 中的 "C++" 替换为 "Java"。
    1. 输出修改后的字符串 str

提示:使用 string 类型的 find 方法可以查找字符串位置, replace 方法可以更改字符串中的特定部分,

// 输出示例
字符串的长度: 16
修改后的字符串: Welcome to Java !
  • 历史解析

    • 字符串的初始化:题目要求Welcome to C++ !,你定义的Welcome to C++!,初始变量错误,导致字符串的长度错误,方法没问题
    • 替换字符串:在使用 replace 方法时,你直接替换了从索引 11 开始的 3个字符。这种方法在当前的情境下有效,更好的方法是使用 find 方法来确定 C++ 的确切位置。如果字符串 str 发生变化,这种方法仍然有效
    • 字符串输出:没必要创建新的字符串 latestStrreplace 方法会修改原字符串 str,所以可以直接输出 str
  • 参考答案

#include <iostream>
#include <string>
using namespace std;
int main() {
    string str = "Welcome to C++!";
    int length = str.length();
    cout << "字符串的长度: " << length << endl;
    // size_t 是 C++ 中的一种无符号整数类型,用于表示对象的大小或索引
    size_t pos = str.find("C++");
    // 在 C++ 中,string::npos 是一个常量,用于表示 string 类中某些函数(如 find)返回的特殊值,
    // 它表示没有找到指定的子字符串或字符
    // 这个常量实际上是 string 类的最大可能长度,通常定义为 -1,
    // (-1 但这不是一个安全的假设。在一些架构或编译器中,这种转换可能导致不同的结果,甚至可能是一个很大的正整数),
    // 但由于它是无符号类型,所以它表现为最大的无符号值。
    if (pos != string::npos) {
        // replace 方法会修改原字符串 str,所以可以直接输出 str
        str.replace(pos, 3, "Java");
    }
    cout << "修改后的字符串: " << str << endl;
    return 0;
}
// 尝试打印 int pos = str.find("test"); pos值
// 可以发现为 -1 因为 str 中没有 "test" 且使用 int 定义进行了隐式转换
// 注意会受不同的编译器影响,故此建议使用 size_t & string::npos 写法
// 故此也可通过以下方式求解(仅作了解)
    int pos = str.find("C++");
    if (pos != -1) {
        // ...code
    }
上次更新: 2024-10-19 10:01:51