blob: 54ec79d13f20773766818d023b6b9155ff921038 [file] [log] [blame]
Parker Schuhbe36c5b2018-02-19 01:06:50 -08001#include "y2018/control_loops/superstructure/arm/graph.h"
2
3#include <assert.h>
4#include <algorithm>
5
6namespace y2018 {
7namespace control_loops {
8namespace superstructure {
9namespace arm {
10
Austin Schuhcb091712018-02-21 20:01:55 -080011SearchGraph::SearchGraph(size_t num_vertexes, std::initializer_list<Edge> edges)
Michael Schuh150f5762018-05-30 09:06:25 -100012 : SearchGraph(num_vertexes, ::std::vector<Edge>(edges)) {}
Austin Schuhcb091712018-02-21 20:01:55 -080013
14SearchGraph::SearchGraph(size_t num_vertexes, std::vector<Edge> &&edges)
15 : edges_(::std::move(edges)) {
Parker Schuhbe36c5b2018-02-19 01:06:50 -080016 vertexes_.resize(num_vertexes);
17 size_t i = 0;
Austin Schuhcb091712018-02-21 20:01:55 -080018 for (const auto &edge : edges_) {
Parker Schuhbe36c5b2018-02-19 01:06:50 -080019 assert(edge.start < num_vertexes);
20 assert(edge.end < num_vertexes);
21 assert(edge.start != edge.end);
22 assert(edge.cost > 0);
23 vertexes_[edge.start].forward.emplace_back(HalfEdge{edge.end, i});
24 vertexes_[edge.end].reverse.emplace_back(HalfEdge{edge.start, i});
25 ++i;
26 }
27 for (auto &vertex : vertexes_) {
Austin Schuhcb091712018-02-21 20:01:55 -080028 ::std::sort(vertex.forward.begin(), vertex.forward.end());
29 ::std::sort(vertex.reverse.begin(), vertex.reverse.end());
Parker Schuhbe36c5b2018-02-19 01:06:50 -080030 }
31 vertex_heap_.Reserve(num_vertexes);
Austin Schuhcb091712018-02-21 20:01:55 -080032 SetGoal(0);
Parker Schuhbe36c5b2018-02-19 01:06:50 -080033}
34
35SearchGraph::~SearchGraph() {}
36
37void SearchGraph::SetGoal(size_t vertex) {
Austin Schuhcb091712018-02-21 20:01:55 -080038 if (last_searched_vertex_ == vertex) {
39 return;
40 }
Parker Schuhbe36c5b2018-02-19 01:06:50 -080041 assert(vertex < vertexes_.size());
42 vertex_heap_.Clear();
43
44 for (auto &vertex : vertexes_) {
45 vertex.cached_distance = std::numeric_limits<double>::infinity();
46 }
47
48 vertexes_[vertex].cached_distance = 0.0;
49 vertex_heap_.InsertOrDecrease(&vertexes_[vertex]);
50
51 while (!vertex_heap_.Empty()) {
52 Vertex *vertex = vertex_heap_.PopMin();
53 for (const auto &half_edge : vertex->reverse) {
54 Vertex *to_adjust = &vertexes_[half_edge.dest];
55 double adjust_cost = vertex->cached_distance + GetCost(half_edge);
56 if (adjust_cost < to_adjust->cached_distance) {
57 to_adjust->cached_distance = adjust_cost;
58 vertex_heap_.InsertOrDecrease(to_adjust);
59 }
60 }
61 }
Austin Schuhcb091712018-02-21 20:01:55 -080062 last_searched_vertex_ = vertex;
Parker Schuhbe36c5b2018-02-19 01:06:50 -080063}
64
65double SearchGraph::GetCostToGoal(size_t vertex) {
66 assert(vertex < vertexes_.size());
67 return vertexes_[vertex].cached_distance;
68}
69
70} // namespace arm
71} // namespace superstructure
72} // namespace control_loops
73} // namespace y2018