Skip to content

Commit 3d40022

Browse files
second chance second try
1 parent 796a535 commit 3d40022

File tree

1 file changed

+162
-160
lines changed

1 file changed

+162
-160
lines changed

src/route.cc

Lines changed: 162 additions & 160 deletions
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,7 @@ namespace osr {
3030

3131
constexpr auto const kMaxMatchingDistanceSquaredRatio = 9.0;
3232

33-
#define trace(...)
33+
#define trace(...)
3434

3535
struct connecting_way {
3636
constexpr bool valid() const { return way_ != way_idx_t::invalid(); }
@@ -436,54 +436,44 @@ best_candidate(ways const& w,
436436
return std::pair{best_node, best_cost};
437437
};
438438

439-
for (auto const accept_bad_max_matching_dist : {false, true}) {
440-
for (auto const [j, dest] : utl::enumerate(m)) {
441-
if (w.r_->way_component_[start.way_] != w.r_->way_component_[dest.way_]) {
442-
trace("reject {}: component mismatch {} vs {}",
443-
w.way_osm_idx_[dest.way_], w.r_->way_component_[start.way_],
444-
w.r_->way_component_[dest.way_]);
445-
continue;
446-
}
447-
if (!should_continue && component_seen(w, m, j, 10)) {
448-
trace("reject {}: should_continue={}, component_seen={}",
449-
w.way_osm_idx_[dest.way_], should_continue,
450-
component_seen(w, m, j, 10));
451-
continue;
452-
}
453-
if (accept_bad_max_matching_dist &&
454-
std::pow(dest.dist_to_way_, 2) >
455-
limit_squared_max_matching_distance) {
456-
trace("reject {}: limit squared matching distance: {} > {} ",
457-
w.way_osm_idx_[dest.way_], dest.dist_to_way_,
458-
std::sqrt(limit_squared_max_matching_distance));
459-
break;
460-
} else if (std::pow(dest.dist_to_way_, 2) >
461-
limit_squared_max_matching_distance) {
462-
trace("WOULD reject {}: limit squared matching distance: {} > {} ",
463-
w.way_osm_idx_[dest.way_], dest.dist_to_way_,
464-
std::sqrt(limit_squared_max_matching_distance));
465-
}
466-
auto best_node = Profile::node::invalid();
467-
auto best_cost = path{.cost_ = std::numeric_limits<cost_t>::max()};
468-
auto best = static_cast<node_candidate const*>(nullptr);
469-
470-
for (auto const x : {&dest.left_, &dest.right_}) {
471-
if (x->valid()) {
472-
auto const [x_node, x_cost] = get_best(dest, x);
473-
if (x_cost.cost_ < best_cost.cost_) {
474-
best = x;
475-
best_node = x_node;
476-
best_cost = x_cost;
477-
}
439+
for (auto const [j, dest] : utl::enumerate(m)) {
440+
if (w.r_->way_component_[start.way_] != w.r_->way_component_[dest.way_]) {
441+
trace("reject {}: component mismatch {} vs {}", w.way_osm_idx_[dest.way_],
442+
w.r_->way_component_[start.way_], w.r_->way_component_[dest.way_]);
443+
continue;
444+
}
445+
if (!should_continue && component_seen(w, m, j, 10)) {
446+
trace("reject {}: should_continue={}, component_seen={}",
447+
w.way_osm_idx_[dest.way_], should_continue,
448+
component_seen(w, m, j, 10));
449+
continue;
450+
}
451+
if (std::pow(dest.dist_to_way_, 2) > limit_squared_max_matching_distance) {
452+
trace("reject {}: limit squared matching distance: {} > {} ",
453+
w.way_osm_idx_[dest.way_], dest.dist_to_way_,
454+
std::sqrt(limit_squared_max_matching_distance));
455+
break;
456+
}
457+
auto best_node = Profile::node::invalid();
458+
auto best_cost = path{.cost_ = std::numeric_limits<cost_t>::max()};
459+
auto best = static_cast<node_candidate const*>(nullptr);
460+
461+
for (auto const x : {&dest.left_, &dest.right_}) {
462+
if (x->valid()) {
463+
auto const [x_node, x_cost] = get_best(dest, x);
464+
if (x_cost.cost_ < best_cost.cost_) {
465+
best = x;
466+
best_node = x_node;
467+
best_cost = x_cost;
478468
}
479469
}
470+
}
480471

481-
if (best != nullptr) {
482-
trace("MATCHED cost={} (max={})", best_cost.cost_, max);
483-
return best_cost.cost_ < max ? std::optional{std::tuple{
484-
best, &dest, best_node, best_cost}}
485-
: std::nullopt;
486-
}
472+
if (best != nullptr) {
473+
trace("MATCHED cost={} (max={})", best_cost.cost_, max);
474+
return best_cost.cost_ < max
475+
? std::optional{std::tuple{best, &dest, best_node, best_cost}}
476+
: std::nullopt;
487477
}
488478
}
489479
trace("NOTHING MATCHED");
@@ -556,50 +546,45 @@ std::optional<path> route_bidirectional(ways const& w,
556546
if (b.pq1_.empty()) {
557547
continue;
558548
}
559-
for (auto const accept_bad_max_matching_dist : {false, true}) {
560-
for (auto const [j, end] : utl::enumerate(to_match)) {
561-
if (w.r_->way_component_[start.way_] !=
562-
w.r_->way_component_[end.way_]) {
563-
continue;
564-
}
565-
if (b.max_reached_2_ && component_seen(w, to_match, j)) {
566-
continue;
567-
}
568-
if (accept_bad_max_matching_dist &&
569-
std::pow(end.dist_to_way_, 2) >
570-
limit_squared_max_matching_distance) {
571-
break;
572-
}
573-
auto const end_way = end.way_;
574-
for (auto const* nc : {&end.left_, &end.right_}) {
575-
if (nc->valid() && nc->cost_ < max) {
576-
Profile::resolve_start_node(
577-
*w.r_, end_way, nc->node_, to.lvl_, opposite(dir),
578-
[&](auto const node) {
579-
auto label = typename Profile::label{node, nc->cost_};
580-
label.track(label, *w.r_, end_way, node.get_node(), false);
581-
b.add_end(w, label, sharing);
582-
});
583-
}
584-
}
585-
if (b.pq2_.empty()) {
586-
continue;
549+
for (auto const [j, end] : utl::enumerate(to_match)) {
550+
if (w.r_->way_component_[start.way_] != w.r_->way_component_[end.way_]) {
551+
continue;
552+
}
553+
if (b.max_reached_2_ && component_seen(w, to_match, j)) {
554+
continue;
555+
}
556+
if (std::pow(end.dist_to_way_, 2) > limit_squared_max_matching_distance) {
557+
break;
558+
}
559+
auto const end_way = end.way_;
560+
for (auto const* nc : {&end.left_, &end.right_}) {
561+
if (nc->valid() && nc->cost_ < max) {
562+
Profile::resolve_start_node(
563+
*w.r_, end_way, nc->node_, to.lvl_, opposite(dir),
564+
[&](auto const node) {
565+
auto label = typename Profile::label{node, nc->cost_};
566+
label.track(label, *w.r_, end_way, node.get_node(), false);
567+
b.add_end(w, label, sharing);
568+
});
587569
}
588-
auto const should_continue =
589-
b.run(w, *w.r_, max, blocked, sharing, elevations, dir);
570+
}
571+
if (b.pq2_.empty()) {
572+
continue;
573+
}
574+
auto const should_continue =
575+
b.run(w, *w.r_, max, blocked, sharing, elevations, dir);
590576

591-
if (b.meet_point_1_.get_node() == node_idx_t::invalid()) {
592-
if (should_continue) {
593-
continue;
594-
}
595-
return std::nullopt;
577+
if (b.meet_point_1_.get_node() == node_idx_t::invalid()) {
578+
if (should_continue) {
579+
continue;
596580
}
581+
return std::nullopt;
582+
}
597583

598-
auto const cost = b.get_cost_to_mp(b.meet_point_1_, b.meet_point_2_);
584+
auto const cost = b.get_cost_to_mp(b.meet_point_1_, b.meet_point_2_);
599585

600-
return reconstruct_bi(w, l, blocked, sharing, elevations, b, from, to,
601-
start, end, cost, dir);
602-
}
586+
return reconstruct_bi(w, l, blocked, sharing, elevations, b, from, to,
587+
start, end, cost, dir);
603588
}
604589
b.pq1_.clear();
605590
b.pq2_.clear();
@@ -626,45 +611,53 @@ std::optional<path> route_dijkstra(ways const& w,
626611
return *direct;
627612
}
628613

629-
auto const limit_squared_max_matching_distance =
630-
std::pow(geo::distance(from.pos_, to.pos_), 2) /
631-
kMaxMatchingDistanceSquaredRatio;
614+
auto const distance_lng_degrees = geo::approx_distance_lng_degrees(from.pos_);
632615

633616
d.reset(max);
634617
auto should_continue = true;
635-
for (auto const [i, start] : utl::enumerate(from_match)) {
636-
if (!should_continue && component_seen(w, from_match, i)) {
637-
continue;
638-
}
639-
if (utl::none_of(to_match, [&](way_candidate const& end) {
640-
return w.r_->way_component_[start.way_] ==
641-
w.r_->way_component_[end.way_];
642-
})) {
643-
continue;
644-
}
645-
646-
for (auto const* nc : {&start.left_, &start.right_}) {
647-
if (nc->valid() && nc->cost_ < max) {
648-
Profile::resolve_start_node(
649-
*w.r_, start.way_, nc->node_, from.lvl_, dir,
650-
[&](auto const node) { d.add_start(w, {node, nc->cost_}); });
618+
for (auto const accept_bad_max_matching_dist : {false, true}) {
619+
auto const limit_squared_max_matching_distance =
620+
accept_bad_max_matching_dist
621+
? std::numeric_limits<double>::max()
622+
: geo::approx_squared_distance(from.pos_, to.pos_,
623+
distance_lng_degrees) /
624+
kMaxMatchingDistanceSquaredRatio;
625+
626+
for (auto const [i, start] : utl::enumerate(from_match)) {
627+
if (!should_continue && component_seen(w, from_match, i)) {
628+
continue;
629+
}
630+
if (utl::none_of(to_match, [&](way_candidate const& end) {
631+
return w.r_->way_component_[start.way_] ==
632+
w.r_->way_component_[end.way_];
633+
})) {
634+
continue;
651635
}
652-
}
653636

654-
if (d.pq_.empty()) {
655-
continue;
656-
}
637+
for (auto const* nc : {&start.left_, &start.right_}) {
638+
if (nc->valid() && nc->cost_ < max) {
639+
Profile::resolve_start_node(
640+
*w.r_, start.way_, nc->node_, from.lvl_, dir,
641+
[&](auto const node) { d.add_start(w, {node, nc->cost_}); });
642+
}
643+
}
657644

658-
should_continue = d.run(w, *w.r_, max, blocked, sharing, elevations, dir) &&
659-
should_continue;
645+
if (d.pq_.empty()) {
646+
continue;
647+
}
660648

661-
auto const c =
662-
best_candidate(w, d, to.lvl_, to_match, max, dir, should_continue,
663-
start, limit_squared_max_matching_distance);
664-
if (c.has_value()) {
665-
auto const [nc, wc, node, p] = *c;
666-
return reconstruct<Profile>(w, l, blocked, sharing, elevations, d, from,
667-
to, start, *wc, *nc, node, p.cost_, dir);
649+
should_continue =
650+
d.run(w, *w.r_, max, blocked, sharing, elevations, dir) &&
651+
should_continue;
652+
653+
auto const c =
654+
best_candidate(w, d, to.lvl_, to_match, max, dir, should_continue,
655+
start, limit_squared_max_matching_distance);
656+
if (c.has_value()) {
657+
auto const [nc, wc, node, p] = *c;
658+
return reconstruct<Profile>(w, l, blocked, sharing, elevations, d, from,
659+
to, start, *wc, *nc, node, p.cost_, dir);
660+
}
668661
}
669662
}
670663

@@ -697,56 +690,65 @@ std::vector<std::optional<path>> route(
697690

698691
d.reset(max);
699692
auto should_continue = true;
700-
for (auto const [i, start] : utl::enumerate(from_match)) {
701-
if (!should_continue && component_seen(w, from_match, i)) {
702-
continue;
703-
}
704-
auto const start_way = start.way_;
705-
for (auto const* nc : {&start.left_, &start.right_}) {
706-
if (nc->valid() && nc->cost_ < max) {
707-
Profile::resolve_start_node(
708-
*w.r_, start.way_, nc->node_, from.lvl_, dir, [&](auto const node) {
709-
auto label = typename Profile::label{node, nc->cost_};
710-
label.track(label, *w.r_, start_way, node.get_node(), false);
711-
d.add_start(w, label);
712-
});
693+
694+
for (auto const accept_bad_max_matching_dist : {false, true}) {
695+
for (auto const [i, start] : utl::enumerate(from_match)) {
696+
if (!should_continue && component_seen(w, from_match, i)) {
697+
continue;
698+
}
699+
auto const start_way = start.way_;
700+
for (auto const* nc : {&start.left_, &start.right_}) {
701+
if (nc->valid() && nc->cost_ < max) {
702+
Profile::resolve_start_node(
703+
*w.r_, start.way_, nc->node_, from.lvl_, dir,
704+
[&](auto const node) {
705+
auto label = typename Profile::label{node, nc->cost_};
706+
label.track(label, *w.r_, start_way, node.get_node(), false);
707+
d.add_start(w, label);
708+
});
709+
}
713710
}
714-
}
715711

716-
should_continue = d.run(w, *w.r_, max, blocked, sharing, elevations, dir) &&
717-
should_continue;
712+
should_continue =
713+
d.run(w, *w.r_, max, blocked, sharing, elevations, dir) &&
714+
should_continue;
718715

719-
auto found = 0U;
720-
for (auto const [m, t, r] : utl::zip(to_match, to, result)) {
721-
if (r.has_value()) {
722-
++found;
723-
} else if (auto const direct = try_direct(from, t); direct.has_value()) {
724-
r = direct;
725-
} else {
726-
auto const limit_squared_max_matching_distance =
727-
geo::approx_squared_distance(from.pos_, t.pos_,
728-
distance_lng_degrees) /
729-
kMaxMatchingDistanceSquaredRatio;
730-
731-
auto const c =
732-
best_candidate(w, d, t.lvl_, m, max, dir, should_continue, start,
733-
limit_squared_max_matching_distance);
734-
if (c.has_value()) {
735-
auto [nc, wc, n, p] = *c;
736-
d.cost_.at(n.get_key()).write(n, p);
737-
if (do_reconstruct(p)) {
738-
p = reconstruct<Profile>(w, l, blocked, sharing, elevations, d,
739-
from, t, start, *wc, *nc, n, p.cost_, dir);
740-
p.uses_elevator_ = true;
741-
}
742-
r = std::make_optional(p);
716+
auto found = 0U;
717+
for (auto const [m, t, r] : utl::zip(to_match, to, result)) {
718+
if (r.has_value()) {
743719
++found;
720+
} else if (auto const direct = try_direct(from, t);
721+
direct.has_value()) {
722+
r = direct;
723+
} else {
724+
auto const limit_squared_max_matching_distance =
725+
accept_bad_max_matching_dist
726+
? std::numeric_limits<double>::max()
727+
: geo::approx_squared_distance(from.pos_, t.pos_,
728+
distance_lng_degrees) /
729+
kMaxMatchingDistanceSquaredRatio;
730+
731+
auto const c =
732+
best_candidate(w, d, t.lvl_, m, max, dir, should_continue, start,
733+
limit_squared_max_matching_distance);
734+
if (c.has_value()) {
735+
auto [nc, wc, n, p] = *c;
736+
d.cost_.at(n.get_key()).write(n, p);
737+
if (do_reconstruct(p)) {
738+
p = reconstruct<Profile>(w, l, blocked, sharing, elevations, d,
739+
from, t, start, *wc, *nc, n, p.cost_,
740+
dir);
741+
p.uses_elevator_ = true;
742+
}
743+
r = std::make_optional(p);
744+
++found;
745+
}
744746
}
745747
}
746-
}
747748

748-
if (found == result.size()) {
749-
return result;
749+
if (found == result.size()) {
750+
return result;
751+
}
750752
}
751753
}
752754

0 commit comments

Comments
 (0)