我正在用一个mysql数据库在java中编写一个最短路径a*算法。我在程序中执行以下SQL查询大约300次,以便从包含10,000个公交车连接的数据库中查找路线连接。执行300次查询大约需要6-7秒。有没有关于如何加快速度的建议,或者关于可以使用的不同方法的任何想法?谢谢
private HashMap<Coordinate,Node> closedNodes;
private PriorityQueue<Node> openNodes;
..
private List<Coordinate> calculatePath()
{
//While there are nodes in the open list
while (!openNodes.isEmpty())
{
//Get the node with the lowest gVal+hVal
Node node = openNodes.poll();
//Add it to the closed list
closedNodes.put(node);
//If it is not the goal node
if (!node.equals(goal))
{
//Get all the neighbours and Create neighbour node
List<Node> neighbours = helper.getNeighbours(node, goal);
//For each neighbour
for (Node neighbourNode : neighbours)
{
//Check if the neighbour is in the list of open nodes
boolean isInOpen = checkOpenNodes(neighbourNode);
//If it is not in the open nodes and not in the closed nodes
if ((!closedNodes.containsKey(neighbourNode))&& (!isInOpen))
{
//Add it to the list of open nodes
openNodes.add(neighbourNode);
}
}
}
else
{
// We found the path
path = backTrackPath(node);
break;
}
}
return path;
/**
* Gets the list of valid Nodes that are possible to travel to from <b>Node</b>
* @param stopNode Node to find neighbours for
* @param goal End Node
* @return list of neighbour Nodes
*/
public ArrayList<Node> getNeighbours(Node stopNode, Node goal)
{
ArrayList<Node> neighbours = new ArrayList<Node>();
Node neighbourNode;
//get neighbours connected to stop
try {
ResultSet rs = stmt.executeQuery("select To_Station_id, To_Station_routeID, To_Station_stopID," +
"To_Station_lat, To_Station_lng, Time from connections where Connections.From_Station_stopID ="
+stopNode.getCoord().getStopID()+" ORDER BY Connections.Time");
rs = stmt.getResultSet();
while (rs.next()) {
int id = rs.getInt("To_Station_id");
String routeID = rs.getString("To_Station_routeID");
String stopID = rs.getString("To_Station_stopID");
String stopName = rs.getString("To_Station_stopName");
Double lat = rs.getDouble("To_Station_lat");
Double lng = rs.getDouble("To_Station_lng");
int time = rs.getInt("Time");
neighbourNode = new Node(id, routeID, stopID, stopName, lat, lng);
neighbourNode.prev = stopNode;
neighbourNode.gVal = stopNode.gVal + time;
neighbourNode.hVal = heuristic.calculateHeuristic(neighbourNode, goal);
neighbours.add(neighbourNode);
}
}
catch (SQLException e) {
e.printStackTrace();
}
return neighbours;
}发布于 2010-04-07 17:39:17
通常,如果您的查询速度慢且代价高,请尝试在某个地方缓存结果,以便在下一次查找时,可以从缓存中快速检索到结果。因此,您将(代价高昂地)计算点A和B之间的连接,将整个结果集存储在数据库中具有定义生命周期的其他(temporary=cache)表中,因此在接下来的X小时/天(或直到路由发生更改之前),您可以从此缓存表中检索从A到B的路由。
发布于 2010-04-07 17:58:11
SELECT *的上有索引,如果每次只更改
WHERE子句中的常量,则仅选择您需要的列From_Station_stopID,使用参数化的预准备查询,以便数据库不必每次都解析查询并构建执行路径,或者使用WHERE From_Station_stopID IN (value1, value2, ...)如果您向我们展示了其余的代码,其中循环调用查询300次,我们也许能够提供进一步的帮助。
一般来说,我想说的是,如果你每次都要计算最短路径,那么你应该构建一个像网格一样工作的表,为每个站点预先计算路线距离,甚至是每个站点预先计算的整个路线。
发布于 2010-04-07 17:45:44
据我所知,您有一个以站点为节点,以连接为边的图。
尝试创建一些表示该图的对象(在最简单的情况下,它可以是一个矩阵),并在该对象上执行搜索。然后,您将不需要对数据库进行300次调用,从性能的角度来看,这是非常昂贵的。
https://stackoverflow.com/questions/2591319
复制相似问题