找出整型数组中占比超过一半的数 | 青训营X豆包MarsCode 技术训练营

3 阅读5分钟

AI刷题实践记录与工具使用分析

在现代学习过程中,AI刷题工具以其独特的功能逐渐成为学生提升解题能力的利器。其中,“个性化题目推荐”功能尤其突出,能够根据学生的薄弱环节和学习进度动态调整题目内容,为学生提供更精准的学习体验。本文通过一道典型的数组问题——寻找超过一半次数的数字,剖析AI刷题工具在学习过程中的独特价值,探讨其如何帮助学习者提升算法理解与实践能力。


功能亮点:个性化题目推荐

个性化推荐功能是AI刷题工具的核心之一,通过对用户的刷题记录进行分析,工具能够动态调整推荐题目,帮助用户在最短时间内弥补知识盲区。以下是其独特价值的具体体现:

  1. 针对性训练
    学生在学习中往往面临题目难度与自身能力不匹配的问题。AI工具通过分析用户在某类题目上的表现,精准推荐适合当前水平的题目,让学生在巩固基础的同时逐步挑战更高难度。
  2. 学习效率提升
    个性化推荐避免了盲目刷题的低效问题,将学习重点聚焦在用户尚未掌握的知识点上,减少时间浪费。例如,在算法学习中,AI工具能够识别用户对特定算法(如摩尔投票算法)的掌握程度,并推荐相关题目进行练习。
  3. 进阶学习路径
    随着用户能力的提升,AI工具能够动态调整题目范围,从简单到复杂逐步引导用户深入理解问题的本质。这种渐进式的推荐机制对培养解题思维至关重要。

刷题实践:寻找超过一半次数的数字

以下通过一道经典的数组问题展开实践,分析AI刷题工具如何帮助学习者高效掌握算法核心。


问题描述

已知在一个数组中,有一个数字的出现次数超过了数组总长度的一半。要求找到这个数字。
例如:

  • 输入:[1, 3, 8, 2, 3, 1, 3, 3, 3],输出:3
  • 输入:[5, 5, 5, 1, 2, 5, 5],输出:5

问题分析

这道题的关键在于高效找到一个出现次数超过一半的数字(即“众数”)。常规方法包括计数统计,但对于大规模数组来说,这种方法的时间和空间复杂度较高。更高效的解法是利用摩尔投票算法,它能够在线性时间和常量空间内完成问题。


摩尔投票算法

核心思想:

  • 众数的出现次数比其他所有数字的总和还多,因此可以通过“抵消”的方式找到众数。

  • 步骤:

    1. 使用一个变量candidate记录候选众数,初始化为空。

    2. 使用一个计数器count记录候选众数的权重,初始为0

    3. 遍历数组:

      • count为0,则更新candidate为当前数字,并将count置为1。
      • 若当前数字等于candidate,则将count加1。
      • 若当前数字不等于candidate,则将count减1。
    4. 遍历结束后,candidate即为众数。


代码实现与解析

以下是摩尔投票算法的C++实现:

#include <iostream>
#include <vector>
using namespace std;

int findMajorityElement(vector<int>& array) {
    int candidate = 0, count = 0;

    // 第一遍遍历找出候选众数
    for (int num : array) {
        if (count == 0) {
            candidate = num;
            count = 1;
        } else if (num == candidate) {
            count++;
        } else {
            count--;
        }
    }

    // 第二遍遍历验证候选众数是否超过一半
    count = 0;
    for (int num : array) {
        if (num == candidate) {
            count++;
        }
    }

    return count > array.size() / 2 ? candidate : -1; // 返回众数或-1表示无解
}

int main() {
    vector<int> array1 = {1, 3, 8, 2, 3, 1, 3, 3, 3};
    vector<int> array2 = {5, 5, 5, 1, 2, 5, 5};
    vector<int> array3 = {9, 9, 9, 9, 8, 9, 8, 8};

    cout << findMajorityElement(array1) << endl; // 输出 3
    cout << findMajorityElement(array2) << endl; // 输出 5
    cout << findMajorityElement(array3) << endl; // 输出 9

    return 0;
}

代码详细解析

  1. 第一遍遍历:确定候选众数

    • 遍历数组时,通过计数器count记录当前候选众数的权重。
    • count降为0时,更新候选众数为当前数字。
  2. 第二遍遍历:验证候选众数

    • 遍历数组,统计候选众数的出现次数。
    • 若出现次数超过数组长度的一半,则返回候选众数;否则返回-1
  3. 时间复杂度:

    • 第一遍遍历: O(n),线性时间找到候选众数。
    • 第二遍遍历: O(n),验证候选众数。
    • 总复杂度: O(n)。
  4. 空间复杂度:

    • 仅使用常量空间记录候选众数和计数器,空间复杂度为O(1)。

实践总结与个人思考

在实践过程中,AI刷题工具通过逐步引导学习者理解摩尔投票算法的原理和实现,帮助我在以下方面取得了显著进步:

  1. 算法思维的构建

    • 在学习初期,我倾向于直接使用暴力计数法,但工具推荐了摩尔投票算法,并通过详尽解析让我认识到抵消思想的高效性。
  2. 渐进式题目训练

    • 工具从简单的统计问题(如求众数)逐步引导我解决进阶问题(如验证众数是否唯一),帮助我在学习中循序渐进。
  3. 代码优化与反馈

    • 在提交代码后,工具给出了关于代码可读性和边界条件处理的优化建议。例如,工具提示在返回结果时需处理“无解”情况(如-1)。
  4. 学习效率提升

    • 通过针对性推荐,工具让我将注意力集中在未掌握的知识点上,例如摩尔投票算法的应用场景和时间复杂度优化技巧。

结论与展望

AI刷题工具的个性化推荐功能不仅提升了学习效率,还帮助学习者构建了系统的算法思维。通过本题的实践,我深刻认识到高效算法的重要性,以及AI工具在辅助学习中的巨大潜力。未来,随着AI技术的不断发展,刷题工具将更加智能化,为学习者提供更具针对性和适应性的学习体验,推动算法学习向更高层次迈进。