​​​【收录 Hello 算法】10.4 哈希优化策略

news2024/11/21 11:01:43

目录

10.4   哈希优化策略

10.4.1   线性查找:以时间换空间

10.4.2   哈希查找:以空间换时间


10.4   哈希优化策略

在算法题中,我们常通过将线性查找替换为哈希查找来降低算法的时间复杂度。我们借助一个算法题来加深理解。

Question

给定一个整数数组 nums 和一个目标元素 target ,请在数组中搜索“和”为 target 的两个元素,并返回它们的数组索引。返回任意一个解即可。

10.4.1   线性查找:以时间换空间

考虑直接遍历所有可能的组合。如图 10-9 所示,我们开启一个两层循环,在每轮中判断两个整数的和是否为 target ,若是,则返回它们的索引。

线性查找求解两数之和

图 10-9   线性查找求解两数之和

代码如下所示:

two_sum.c

/* 方法一:暴力枚举 */
int *twoSumBruteForce(int *nums, int numsSize, int target, int *returnSize) {
    for (int i = 0; i < numsSize; ++i) {
        for (int j = i + 1; j < numsSize; ++j) {
            if (nums[i] + nums[j] == target) {
                int *res = malloc(sizeof(int) * 2);
                res[0] = i, res[1] = j;
                *returnSize = 2;
                return res;
            }
        }
    }
    *returnSize = 0;
    return NULL;
}

此方法的时间复杂度为 𝑂(𝑛2) ,空间复杂度为 𝑂(1) ,在大数据量下非常耗时。

10.4.2   哈希查找:以空间换时间

考虑借助一个哈希表,键值对分别为数组元素和元素索引。循环遍历数组,每轮执行图 10-10 所示的步骤。

  1. 判断数字 target - nums[i] 是否在哈希表中,若是,则直接返回这两个元素的索引。
  2. 将键值对 nums[i] 和索引 i 添加进哈希表。

<1><2><3>

two_sum_hashtable_step3

图 10-10   辅助哈希表求解两数之和

实现代码如下所示,仅需单层循环即可:

two_sum.c

/* 哈希表 */
typedef struct {
    int key;
    int val;
    UT_hash_handle hh; // 基于 uthash.h 实现
} HashTable;

/* 哈希表查询 */
HashTable *find(HashTable *h, int key) {
    HashTable *tmp;
    HASH_FIND_INT(h, &key, tmp);
    return tmp;
}

/* 哈希表元素插入 */
void insert(HashTable *h, int key, int val) {
    HashTable *t = find(h, key);
    if (t == NULL) {
        HashTable *tmp = malloc(sizeof(HashTable));
        tmp->key = key, tmp->val = val;
        HASH_ADD_INT(h, key, tmp);
    } else {
        t->val = val;
    }
}

/* 方法二:辅助哈希表 */
int *twoSumHashTable(int *nums, int numsSize, int target, int *returnSize) {
    HashTable *hashtable = NULL;
    for (int i = 0; i < numsSize; i++) {
        HashTable *t = find(hashtable, target - nums[i]);
        if (t != NULL) {
            int *res = malloc(sizeof(int) * 2);
            res[0] = t->val, res[1] = i;
            *returnSize = 2;
            return res;
        }
        insert(hashtable, nums[i], i);
    }
    *returnSize = 0;
    return NULL;
}

此方法通过哈希查找将时间复杂度从 𝑂(𝑛2) 降至 𝑂(𝑛) ,大幅提升运行效率。

由于需要维护一个额外的哈希表,因此空间复杂度为 𝑂(𝑛) 。尽管如此,该方法的整体时空效率更为均衡,因此它是本题的最优解法

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1700160.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

LINGO:存贮问题

存贮模型中的基本概念 模型&#xff1a; 基本要素&#xff1a; &#xff08;1&#xff09;需求率&#xff1a;单位时间内对某种物品的需求量&#xff0c;用D表示。 &#xff08;2&#xff09;订货批量&#xff1a;一次订货中&#xff0c;包含某种货物的数量&#xff0c;用 Q表…

AI网络爬虫-从当当网批量获取图书信息

工作任务和目标&#xff1a;用户输入一个图书名称&#xff0c;然后程序自动从当当网批量获取图书信息 查看相关元素在源代码中的位置&#xff1a; 第一步&#xff1a;在deepseek中输入提示词&#xff1a; 你是一个Python爬虫专家&#xff0c;一步步的思考&#xff0c;完成以下…

Linux定时计划

定时计划 一、计划任务种类 突发性&#xff1a;临时决定只执行一次的任务 at&#xff1a;处理执行一次任务就结束定时性&#xff1a;每隔一定时间需要重复执行此命令 crontab&#xff1a;指定任务&#xff0c;按照设定的周期一直循环执行二、作用 定时任务可以用于自动备份…

AI办公自动化:用kimi批量将word文档部分文件名保存到Excel中

文件夹中有很多个word文档&#xff0c;现在只要英文部分的文件名&#xff0c;保存到一个Excel文件中。 可以在kimi中输入提示词&#xff1a; 你是一个Python编程专家&#xff0c;要完成一个编写Python脚本的任务&#xff0c;具体步骤如下&#xff1a; 打开文件夹&#xff1a;…

51单片机-实机演示(LED,呼吸,蜂鸣器)

一&#xff0c;LED点灯 #include "REG52.H"sbit LED P0^0;void main() {LED 1;while (1){} }控制P00输出。 烧录 重启 再换个引脚插入的位置。 二&#xff0c;蜂鸣器 代码&#xff0c;和烧录步骤同上。 只需要换一下&#xff0c;引脚位置即可 三&#xff0c;呼…

jmeter之MD5加密接口请求教程

前言&#xff1a; 有时候在项目中&#xff0c;需要使用MD5加密的方法才可以登录&#xff0c;或者在某一个接口中遇到 登录获取token后才可以进行关联&#xff0c;下面介绍下遇到的常见使用 一、第一种方法&#xff1a;使用jmeter自带的函数助手digest 选择工具&#xff0c;选择…

ssm整合教程

目录 写在前面 目录结构 添加依赖 web.xml jdbc.properties spring.xml mybatis.xml springmvc.xml pom.xml额外配置 last&#xff1a;写个测试样例看看整合成功没。 User.java UserDao.java(接口) UserController.java UserService.java UserServiceImpl.java …

人工智能在鼻咽癌领域的最新应用|【医学AI·论文速递·05-27】

小罗碎碎念 2024-05-27&#xff5c;文献速递 接下来打算把人工智能在主流癌种治疗中的应用&#xff0c;每天和大家做一期推送&#xff0c;方便大家了解各自领域最新的一个进展。 因为小罗的课题是鼻咽癌相关的&#xff0c;所以这一期推文就先从人工智能在鼻咽癌中最新的应用开…

MyBatis框架的使用:mybatis介绍+环境搭建+基础sql的使用+如何使用Map传入多个参数+返回多个实体用List或者Map接收+特殊sql的使用

MyBatis框架的使用&#xff1a;mybatis介绍环境搭建基础sql的使用如何使用Map传入多个参数返回多个实体用List或者Map接收特殊sql的使用 一、MyBatis介绍1.1 特性1.2 下载地址1.3 和其它持久层技术对比 二、搭建环境2.1配置maven2.2 创建mybatis配置文件2.3 搭建测试环境 三、基…

【CTF Web】CTFShow web7 Writeup(SQL注入+PHP+进制转换)

web7 1 阿呆得到最高指示&#xff0c;如果还出问题&#xff0c;就卷铺盖滚蛋&#xff0c;阿呆心在流血。 解法 注意到&#xff1a; <!-- flag in id 1000 -->拦截很多种字符&#xff0c;连 select 也不给用了。 if(preg_match("/\|\"|or|\||\-|\\\|\/|\\*|\…

宿舍管理系统代码详解(操作界面)

目录 一、前端代码 1.样式展示 2.代码详解 <1>主页面列表部分 &#xff08;1&#xff09;template部分 &#xff08;2&#xff09;script部分 <2>新增页面 &#xff08;1&#xff09;template部分 &#xff08;2&#xff09;script部分 <3>修改页面…

C++初阶学习第九弹——探索STL奥秘(四)——vector的深层挖掘和模拟实现

string&#xff08;上&#xff09;&#xff1a;C初阶学习第六弹——探索STL奥秘&#xff08;一&#xff09;——标准库中的string类-CSDN博客 string&#xff08;下&#xff09;&#xff1a;C初阶学习第七弹——探索STL奥秘&#xff08;二&#xff09;——string的模拟实现-CS…

访问tomcat的webapps下war包,页面空白

SpringBootvue前后端分离项目&#xff0c;Vue打包到SpringBoot中 常见问题 错误一&#xff1a;war包访问页面空白 前提&#xff1a;项目在IDEA里配置tomcat可以启动访问项目 但是&#xff0c;打成war包拷贝到tomcat webapps下能启动却访问不了&#xff0c;页面显示空白 原…

孜然多程序授权系统V2.0开源

源码介绍 孜然一款多程序授权系统&#xff0c;支持自定义权限价格/新增程序配置等支持自动生成授权代码在线签到在线充值多支付接口IP/域名云黑文章系统&#xff08;富文本编辑器&#xff09;卡密功能一键云黑&#xff08;挂个大马/一键黑页/一键删库/一键删源码&#xff09; …

linux 阿里云服务器安装ImageMagick和php扩展imagick

操作系统版本 Alibaba Cloud Linux 3.2104 LTS 64位 # 1.安装ImageMagick yum install -y ImageMagick ImageMagick-devel # 没有pecl要先安装pecl 和头文件 sudo yum install php-devel # 2.pecl 安装扩展 pecl install imagick #寻找所有php.ini文件 find / -name php.…

基于EV54Y39A PIC-IOT WA的手指数量检测功能开发(MPLAB+ADC)

目录 项目介绍硬件介绍项目设计开发环境及工程参考总体流程图硬件基本配置光照传感器读取定时器检测逻辑 功能展示项目总结 &#x1f449; 【Funpack3-2】基于EV54Y39A PIC-IOT WA的手指数量检测功能开发 &#x1f449; Github: EmbeddedCamerata/PIC-IOT_finger_recognition 项…

42-5 应急响应之日志分析

一、Windows 系统日志排查 1)日志概述 在 Windows 2000 专业版、Windows XP 和 Windows Server 2003 中: 系统日志的位置为 C:\WINDOWS\System32\config\SysEvent.evt安全性日志的位置为 C:\WINDOWS\System32\config\SecEvent.evt应用程序日志的位置为 C:\WINNT\System32\c…

在Windows中安装Redis

一、下载Redis github链接&#xff1a;https://github.com/redis-windows/redis-windows/releases 二、安装 解压后点击start.bat文件即可启动服务 新开一个cmd窗口进入安装了Redis的文件夹输入redis-cli.exe -h 127.0.0.1 -p 6379连接Redis&#xff0c;见如下结果便是成功&…

第六节:带你全面理解vue3 浅层响应式API: shallowRef, shallowReactive, shallowReadonly

前言 前面两章,给大家讲解了vue3中ref, reactive,readonly创建响应式数据的API, 以及常用的计算属性computed, 侦听器watch,watchEffect的使用 其中reactive, ref, readonly创建的响应式数据都是深层响应. 而本章主要给大家讲解以上三个API 对应的创建浅层响应式数据的 API,…