🥳前端算法面试--贪心算法只求解多区间--说几句心里话吧

今天分享的内容是如何用贪心算法,在固定范围内找到更多子区间

问题描述

现在有多个子区间,区间的范围是从 n 到 m,请在这些区间中,找出最多不相互覆盖的子区间

javascript 复制代码
const data = [
	[6, 8],
	[2, 4],
	[3, 5],
	[1, 5],
	[5, 9],
	[8, 10],
];

data 是一个二维数组,其中可以找到的最多,不冲突的子区间是:

javascript 复制代码
const spaces = [ [ 2, 4 ], [ 6, 8 ], [ 8, 10 ] ];

思路分析

寻找最多区间的问题,就要请出我们今天的主角了--贪心算法

贪心算法是一种在许多情况下都可以有效解决问题的算法。它的基本思想是每次选择当前最优的解,即局部最优解。贪心算法的求解过程是每次选择当前最优的解,直到满足终止条件。

贪心顾名思义,就是只顾眼前的利益,只顾着眼前能看见的最优。虽然不好听,但是解决当前的问题却再合适不过了。

对于当前的问题,可以先将各个区间按照左端点排序,然后找下一个区间,要求和当前区间不相互覆盖,并且区间范围最小。为什么?因为这样可以使剩下的空白区间范围足够大,可以容纳更多的子区间。优先最短,构成局部最优,这就是贪心思想。

说是这么说,看起来挺简单的,但是按照上面的描述来写代码却不容易。可以换个思路:

对区间的右端点进行升序排序,每加入一个线段,然后选择后面一个或者多个右端点相同的区间,然后在选中区间内选择左端点最大的那一条,也就是区间最小的。如果加入以后不会跟之前的区间不会相互覆盖,那么就加入,否则就继续判断后面的区间

很简单吧,来看看代码咋写

代码实现

javascript 复制代码
//倒序插入
const insertOrder = (array, value) => {
	for (let i = 0; i < array.length; i++) {
		if (value[0] >= array[i][0]) {
			array[i].splice(i, 0, value);
			return;
		}
	}
	array.push(value);
};

// 找到最多的区间
// table是区间表
const findManySpace = (table) => {
	table = table.sort((a, b) => a[1] - b[1]);

	const res = [];
	for (let i = 0; i < table.length; i++) {
		let tempArray = [];
		let j = i;
		// 找到相同右端点的区间
		for (; j < table.length; j++) {
			// 倒序插入
			if (table[i][1] == table[j][1]) insertOrder(tempArray, table[j]);
			else break;
		}
		i = j - 1;

		// res初始可能为空,就不考虑区间覆盖的问题
		if (res.length == 0) {
			res.push(tempArray[0]);
			continue;
		}

		// 遍历,找到第一个不覆盖的区间
		for (let i = 0; i < tempArray.length; i++) {
			if (tempArray[i][0] >= res[res.length - 1][1]) {
				res.push(tempArray[i]);
				break;
			}
		}
	}

	console.log(res);
};

代码的思路,也就入上面描述中所讲的一样,代码就不做详细解释了。

其中有两个需要注意的地方,提一下

  1. 为了能够快速地在相同右端点的区间中,找到最大左端点的区间,可以采用有序插入的方式,这样就不用再对 tempArray 排序了
  2. 在找到若干个相同右端点的区间后,需要修改 i 的值,表示 i 前面的区间已经被考虑过了。下一轮循环直接从 i 后面的区间开始

测试代码

javascript 复制代码
findManySpace(data);
// [ [ 2, 4 ], [ 6, 8 ], [ 8, 10 ] ]

输出正确

总结

本篇文章分享的是一道非常经典的区间求解问题,主要采用的策略是贪心算法。思路很简单,代码也很简单,难的是,如果不看答案之前,这道题根本做不出来....我在说我自己

说句题外话,写完这篇文章,我已经在算法和数据结构专题上分享了 50 余篇文章了,感觉仍在基础打转。数据结构是基础不假,但会了数据结构绝对不代表会算法,算法是解题方法,像数学题目一样,知识是知识,题目是题目,学会了知识,不代表会做题目。而且题目的解法,技巧是另一个层面的东西。

到现在,本专栏分享的数据结构涵盖了大学本科要求的所有数据,从数组,链表,到二叉树,二叉搜索树,多叉树,AVL 平衡树,B 树,(红黑树暂时没有), 图,集合,堆,hash表,分享的算法有排序算法,贪心算法,回溯算法,动态规划,对于浩如烟海的算法问题,这点很不够看。

刚去力扣试了试身手,结果被杀得卸甲归田...我还是在说我自己

难道要进入做一道会一道,不做就不会的怪圈么...给自己打了一个问号❓

题外话说完了,有问题可以评论区留言哦。我每天都会分享一篇算法小练习,喜欢就点赞+关注吧

相关推荐
Jay Kay22 分钟前
GVPO:Group Variance Policy Optimization
人工智能·算法·机器学习
Epiphany.55634 分钟前
蓝桥杯备赛题目-----爆破
算法·职场和发展·蓝桥杯
Ticnix36 分钟前
ECharts初始化、销毁、resize 适配组件封装(含完整封装代码)
前端·echarts
纯爱掌门人39 分钟前
终焉轮回里,藏着 AI 与人类的答案
前端·人工智能·aigc
twl43 分钟前
OpenClaw 深度技术解析
前端
崔庆才丨静觅1 小时前
比官方便宜一半以上!Grok API 申请及使用
前端
星光不问赶路人1 小时前
vue3使用jsx语法详解
前端·vue.js
YuTaoShao1 小时前
【LeetCode 每日一题】1653. 使字符串平衡的最少删除次数——(解法三)DP 空间优化
算法·leetcode·职场和发展
天蓝色的鱼鱼1 小时前
shadcn/ui,给你一个真正可控的UI组件库
前端
茉莉玫瑰花茶1 小时前
C++ 17 详细特性解析(5)
开发语言·c++·算法