diff --git a/problems/kamacoder/0126.骑士的攻击astar.md b/problems/kamacoder/0126.骑士的攻击astar.md index 2d0481ec..1cdba07d 100644 --- a/problems/kamacoder/0126.骑士的攻击astar.md +++ b/problems/kamacoder/0126.骑士的攻击astar.md @@ -375,6 +375,131 @@ for _ in range(n): ### Javascript +```js +class MinHeap { + constructor() { + this.val = [] + } + push(val) { + this.val.push(val) + if (this.val.length > 1) { + this.bubbleUp() + } + } + bubbleUp() { + let pi = this.val.length - 1 + let pp = Math.floor((pi - 1) / 2) + while (pi > 0 && this.val[pp][0] > this.val[pi][0]) { + ;[this.val[pi], this.val[pp]] = [this.val[pp], this.val[pi]] + pi = pp + pp = Math.floor((pi - 1) / 2) + } + } + pop() { + if (this.val.length > 1) { + let pp = 0 + let pi = this.val.length - 1 + ;[this.val[pi], this.val[pp]] = [this.val[pp], this.val[pi]] + const min = this.val.pop() + if (this.val.length > 1) { + this.sinkDown(0) + } + return min + } else if (this.val.length == 1) { + return this.val.pop() + } + + } + sinkDown(parentIdx) { + let pp = parentIdx + let plc = pp * 2 + 1 + let prc = pp * 2 + 2 + let pt = pp // temp pointer + if (plc < this.val.length && this.val[pp][0] > this.val[plc][0]) { + pt = plc + } + if (prc < this.val.length && this.val[pt][0] > this.val[prc][0]) { + pt = prc + } + if (pt != pp) { + ;[this.val[pp], this.val[pt]] = [this.val[pt], this.val[pp]] + this.sinkDown(pt) + } + } +} + +const moves = [ + [1, 2], + [2, 1], + [-1, -2], + [-2, -1], + [-1, 2], + [-2, 1], + [1, -2], + [2, -1] +] + +function dist(a, b) { + return ((a[0] - b[0])**2 + (a[1] - b[1])**2)**0.5 +} + +function isValid(x, y) { + return x >= 1 && y >= 1 && x < 1001 && y < 1001 +} + +function bfs(start, end) { + const step = new Map() + step.set(start.join(" "), 0) + const q = new MinHeap() + q.push([dist(start, end), start[0], start[1]]) + + while(q.val.length) { + const [d, x, y] = q.pop() + // if x and y correspond to end position output result + if (x == end[0] && y == end[1]) { + console.log(step.get(end.join(" "))) + break; + } + for (const [dx, dy] of moves) { + const nx = dx + x + const ny = dy + y + if (isValid(nx, ny)) { + const newStep = step.get([x, y].join(" ")) + 1 + const newDist = dist([nx, ny], [...end]) + const s = step.get([nx, ny].join(" ")) ? + step.get([nx, ny]) : + Number.MAX_VALUE + if (newStep < s) { + q.push( + [ + newStep + newDist, + nx, + ny + ] + ) + step.set([nx, ny].join(" "), newStep) + } + } + } + } +} + +async function main() { + const rl = require('readline').createInterface({ input: process.stdin }) + const iter = rl[Symbol.asyncIterator]() + const readline = async () => (await iter.next()).value + const n = Number((await readline())) + + // find min step + for (let i = 0 ; i < n ; i++) { + const [s1, s2, t1, t2] = (await readline()).split(" ").map(Number) + bfs([s1, s2], [t1, t2]) + } +} + +main() +``` + ### TypeScript ### PhP