- 问题描述
init给定图的初始化,mMap值为0表示无障碍,1表示有障碍。
add,增加的加油站station,加油可以行驶init的mRange距离。
然后求最短距离,mFrom到mTo(对应add函数的mId)。
下面是
我写的算法,还能优化吗?一只超时。
import java.util.*;
class UserSolution
{
class Node implements Comparator<Node> {
int id;
int x;
int y;
int dist;
public Node() {}
public Node(int id, int dist) {
this.id = id;
this.dist = dist;
}
public Node(int id, int x, int y) {
this.id = id; // -1 白色, -2 灰色(障碍物)
this.x = x;
this.y = y;
}
public Node(int id, int x, int y, int dist) {
this.id = id;
this.x = x;
this.y = y;
this.dist = dist;
}
@Override
public int compare(Node o1, Node o2) {
return o1.dist - o2.dist;
}
}
int n;
int[][] graph;
HashMap<Integer, Node> nodeMap = new HashMap<>();
HashMap<Integer, ArrayList<Node>> adjTable = new HashMap<>();
int range;
int[] dx = new int[]{1, -1, 0, 0};
int[] dy = new int[]{0, 0, 1, -1};
void init(int N, int mRange, int mMap[][])
{
this.n = N;
this.graph = new int[n][n];
nodeMap.clear();
adjTable.clear();
this.range = mRange;
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
if (mMap[i][j] == 0) {
graph[i][j] = -1;
continue;
}
if (mMap[i][j] == 1) {
graph[i][j] = -2;
}
}
}
}
void add(int mID, int mRow, int mCol)
{
Node insertNode = new Node(mID, mRow, mCol);
nodeMap.put(mID, insertNode);
graph[mRow][mCol] = mID;
adjTable.put(mID, new ArrayList<>());
update(insertNode);
}
private void update(Node updateNode) {
ArrayDeque<Node> queue = new ArrayDeque<>();
boolean[][] vis = new boolean[n][n];
queue.add(new Node(updateNode.id, updateNode.x, updateNode.y, 0));
vis[updateNode.x][updateNode.y] = true;
while (!queue.isEmpty()) {
Node startNode = queue.poll();
for (int i = 0; i < 4; i++) {
int newX = startNode.x + dx[i];
int newY = startNode.y + dy[i];
int dist = startNode.dist + 1;
if (!isOut(newX, newY)) {
continue;
}
int id = graph[newX][newY];
if (isOut(newX, newY) && !vis[newX][newY] && id > -2 && dist <= range) {
vis[newX][newY] = true;
queue.add(new Node(id, newX, newY, dist));
if (id >= 0) {
adjTable.get(updateNode.id).add(new Node(id, newX, newY, dist));
adjTable.get(id).add(new Node(updateNode.id, updateNode.x, updateNode.y, dist));
}
}
}
}
}
private boolean isOut(int x, int y) {
return x >= 0 && y >= 0 && x < n && y < n;
}
int distance(int mFrom, int mTo)
{
Node sourceNode = nodeMap.get(mFrom);
Node targetNode = nodeMap.get(mTo);
if (sourceNode == null || targetNode == null) {
return -1;
}
PriorityQueue<Node> queue = new PriorityQueue<>(new Node());
boolean[] vis = new boolean[205];
vis[mFrom] = true;
queue.add(new Node(sourceNode.id,0));
while (!queue.isEmpty()) {
Node startNode = queue.poll();
vis[startNode.id] = true;
if (startNode.id == mTo) {
return startNode.dist;
}
for (Node node : adjTable.get(startNode.id)) {
if (!vis[node.id]) {
queue.add(new Node(node.id, node.dist + startNode.dist));
}
}
}
return -1;
}
}