题目简述:有若干个炸弹,给出炸弹的坐标(x,y)以及爆炸半径r,若一个炸弹在另外一个炸弹的爆炸半径r之内的时候,就会引爆它,求引爆一个炸弹的前提下,最多可以引爆多少个炸弹。
这是一题图论题目,用邻接表来解答,每个邻接表里面放着与之能引爆的邻接炸弹,然后使用dfs或者bfs来求解
DFS
var maximumDetonation = function (bombs) {
let len = bombs.length
let graph = Array.from({ length: len }, () => [])
// 构建邻接表
for (let i = 0; i < len; ++i) {
for (let j = 0; j < len; ++j) {
let [x1, y1, r1] = bombs[i]
let [x2, y2, r2] = bombs[j]
let dist = (x2 - x1) ** 2 + (y2 - y1) ** 2
// j 在 i的爆炸半径之内,则放入邻接表
if (dist <= r1 ** 2) {
graph[i].push(j)
}
}
}
// dfs 来进行遍历
var dfs = function (i, visited) {
visited[i] = true
let count = 1
// 从当前引爆的炸弹的邻接表中来进行遍历
for (let n of graph[i]) {
// 没有引爆过的,则进行引爆,然后进行计数
if (!visited[n]) {
// 引爆邻接的炸弹
count += dfs(n, visited)
}
}
return count
}
let maxBombs = 0
// 遍历每一个炸弹(从每个炸弹都开始,计算每一种情况
for (let i = 0; i < len; ++i) {
// 对于每一次迭代的 i 而言,都是一次全行的爆炸之旅
// 所以要重新初始化 visited 数组
let visited = Array(len).fill(false)
maxBombs = Math.max(maxBombs, dfs(i, visited))
}
return maxBombs
};
BFS
var maximumDetonation = function (bombs) {
let len = bombs.length
let graph = Array.from({ length: len }, () => [])
// 构建邻接表
for (let i = 0; i < len; ++i) {
for (let j = 0; j < len; ++j) {
let [x1, y1, r1] = bombs[i]
let [x2, y2, r2] = bombs[j]
let dist = (x2 - x1) ** 2 + (y2 - y1) ** 2
// j 在 i的爆炸半径之内,则放入邻接表
if (dist <= r1 ** 2) {
graph[i].push(j)
}
}
}
// bfs 来进行遍历
var bfs = function (i) {
// 记录是否被引爆
let visited = Array(len).fill(false)
visited[i] = true
let queue = [i]
let count = 0
while (queue.length) {
// 取出最前面的节点
let node = queue.shift()
// 队列有多大,就能引爆多少个,所以在这里 计数
count++
// 找到邻接炸弹
for (let n of graph[node]) {
// 没有引爆过的邻接炸弹,放入队列之中等待引爆
if (!visited[n]) {
visited[n] = true
queue.push(n)
}
}
}
return count
}
let maxBombs = 0
// 遍历每一个炸弹(从每个炸弹都开始,计算每一种情况
for (let i = 0; i < len; ++i) {
maxBombs = Math.max(maxBombs, bfs(i))
}
return maxBombs
};