• 编程竞赛之哈希算法应用


    题目描述一

    给定一个严格递增序列A和一个正整数k,在序列A中寻找两个数a、b,使得a+b = k。问有多少对a、b满足条件。注:a、b和b、a算作同一对注:使用hash法实现输入描述第一行两个正整数n、k (1

    输入

    5 6 1 2 4 5 6

    输出

    2

    解释

    1 + 5 = 6、2 + 4 = 6,因此有两对

     题目思路

    1. 首先建立一个哈希表(数组)h,用于记录序列A中每个数的出现次数。
    2. 初始化满足条件的数对数量ans为0。
    3. 遍历序列A中的每个数a,对于每个a,判断是否存在另一个数b=k-a,并且b在哈希表h中出现过。
      • 如果存在,则将ans增加h[b](即b的出现次数),表示有h[b]个数对满足条件。
    4. 输出ans,表示满足条件的a和b的对数。

     

     代码:

    1. #include
    2. using namespace std;
    3. int main()
    4. {
    5. int n, k;
    6. cin >> n >> k;
    7. int h[1000001] = {0}; // 哈希表,用于记录每个数的出现次数
    8. int ans = 0;
    9. for(int i=0; i
    10. {
    11. int num;
    12. cin >> num;
    13. int complement = k - num; // 寻找与当前数配对的数
    14. if(complement >= 0 && h[complement] > 0) // 若配对数存在且出现过
    15. {
    16. ans += h[complement]; // 将配对数的出现次数加到结果中
    17. }
    18. h[num]++; // 将当前数记录到哈希表中
    19. }
    20. cout << ans;
    21. return 0;
    22. }

    以输入 "5 6 1 2 4 5 6" 为例,其中5表示序列A的元素个数,6表示给定的和,后面的数字表示序列A中的元素。经过计算,得到两个满足条件的数对:1+5=6和2+4=6,因此输出结果为2。

    题目描述二 

    给定一个包含n个正整数的集合S1,再给定一个包含m个正整数的集合S2,求两个集合的差集,即S1 — S2。

    输入描述

    第一行两个正整数n、m (1

    输出描述

    按升序输出集合Si和S2的差集。结果之间用空格隔开,行末不允许有多余的空格。

    样例1

    54125682467输出

    158

    解释:从集合Si中去掉集合S2中存在的整数2和6,还剩下(1,5,8)

     

    1. 首先定义一个bool类型的哈希表hashtable,大小为MAXN (10001)。用于记录集合S1中的元素是否存在。
    2. 使用for循环读取集合S1的n个成员,并将对应的hashtable[x]设置为true,表示元素x存在于集合S1中。
    3. 使用for循环读取集合S2的m个成员,并将对应的hashtable[x]设置为false,如果元素x在集合S1中存在,则会被标记为false,表示元素x不属于差集。
    4. 使用一个flag变量控制输出格式,初始值为true。
    5. 使用for循环遍历hashtable数组,如果hashtable[i]为true,则输出i,同时将flag设置为false,表示已经输出了至少一个元素。
    6. 输出结束,返回0。

    代码

    1. #include
    2. using namespace std;
    3. const int MAXN = 10001;
    4. bool hashtable[MAXN] = {false};
    5. int main()
    6. {
    7. int n, m, x;
    8. cin >> n >> m; // 输入集合S1和集合S2的成员数目
    9. for(int i = 0; i < n; i++)
    10. {
    11. cin >> x; // 读取集合S1的成员
    12. hashtable[x] = true; // 将对应的哈希表元素设为true,表示该元素存在于集合S1中
    13. }
    14. for(int i = 0; i < m; i++)
    15. {
    16. cin >> x; // 读取集合S2的成员
    17. hashtable[x] = false; // 将对应的哈希表元素设为false,表示该元素不存在于集合S1中(即属于差集)
    18. }
    19. bool flag = true;
    20. for(int i = 0; i < MAXN; i++)
    21. {
    22. if(hashtable[i]) // 如果哈希表中的元素为true,则输出
    23. {
    24. if(!flag)
    25. {
    26. cout << ' ';
    27. }
    28. cout << i;
    29. flag = false; // 标记已经输出了至少一个元素
    30. }
    31. }
    32. return 0;
    33. }

     

  • 相关阅读:
    vmware16.2内部win7联网
    【单片机】14-I2C通信之EEPROM
    springMvc48-返回json数据
    Elastic Stack 8.10:更简单的跨集群搜索和身份验证等等
    B站Java面试失利,多次复习文档后找到原因
    Linux用户管理指南:创建、删除、权限、最佳实践,全面掌握用户管理技巧
    unocss+vite+vue3初使unocss
    vue 封装一个Dialog组件
    【Redis场景5】集群秒杀优化-分布式锁
    修改node_modules中安装的依赖(如第三方ui组件样式)并在下次安装时保留
  • 原文地址:https://blog.csdn.net/2201_75867204/article/details/132645390