Skip to content

Commit

Permalink
Merge remote-tracking branch 'upstream/dev-2.x' into dev-2.x
Browse files Browse the repository at this point in the history
  • Loading branch information
leonardehrenfried committed Jun 3, 2021
2 parents 089baca + 6a9082b commit 2698711
Show file tree
Hide file tree
Showing 14 changed files with 499 additions and 41 deletions.
Empty file added .attach_pid128911
Empty file.
Empty file.
Empty file.
Empty file.
Original file line number Diff line number Diff line change
Expand Up @@ -52,10 +52,6 @@ public String getName(Locale locale) {
}

public State traverse(State s0) {
// Do not even consider bike rental vertices unless bike rental is enabled.
if ( ! s0.getOptions().bikeRental) {
return null;
}
// Disallow traversing two StreetBikeRentalLinks in a row.
// This prevents the router from using bike rental stations as shortcuts to get around
// turn restrictions.
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package org.opentripplanner.routing.graphfinder;

import com.beust.jcommander.internal.Lists;
import java.util.List;
import org.locationtech.jts.geom.Coordinate;
import org.opentripplanner.common.geometry.SphericalDistanceLibrary;
import org.opentripplanner.model.FeedScopedId;
Expand All @@ -10,8 +11,6 @@
import org.opentripplanner.routing.impl.StreetVertexIndex;
import org.opentripplanner.routing.vertextype.TransitStopVertex;

import java.util.List;

/**
* A Graph finder used in conjunction with a graph, which does not have a street network included.
* Also usable if performance is more important or if the "as the crow flies" distance id required.
Expand All @@ -33,7 +32,7 @@ public List<NearbyStop> findClosestStops(double lat, double lon, double radiusMe
List<NearbyStop> stopsFound = Lists.newArrayList();
Coordinate coordinate = new Coordinate(lon, lat);
for (TransitStopVertex it : streetIndex.getNearbyTransitStops(coordinate, radiusMeters)) {
double distance = SphericalDistanceLibrary.distance(coordinate, it.getCoordinate());
double distance = Math.round(SphericalDistanceLibrary.distance(coordinate, it.getCoordinate()));
if (distance < radiusMeters) {
NearbyStop sd = new NearbyStop(
it,
Expand All @@ -44,6 +43,9 @@ public List<NearbyStop> findClosestStops(double lat, double lon, double radiusMe
stopsFound.add(sd);
}
}

stopsFound.sort(NearbyStop::compareTo);

return stopsFound;
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,8 @@
package org.opentripplanner.routing.graphfinder;

import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
import java.util.ArrayList;
import java.util.List;
import org.locationtech.jts.geom.LineString;
Expand Down Expand Up @@ -43,8 +46,33 @@ public int compareTo(NearbyStop that) {
return (int) (this.distance) - (int) (that.distance);
}

@Override
public boolean equals(Object o) {
if (this == o) { return true; }
if (o == null || getClass() != o.getClass()) { return false; }
final NearbyStop that = (NearbyStop) o;
return Double.compare(that.distance, distance) == 0
&& distanceIndependentTime == that.distanceIndependentTime
&& stop.equals(that.stop)
&& Objects.equals(edges, that.edges)
&& Objects.equals(geometry, that.geometry)
&& Objects.equals(state, that.state);
}

@Override
public int hashCode() {
return Objects.hash(stop, distance, distanceIndependentTime, edges, geometry, state);
}

public String toString() {
return String.format("stop %s at %.1f meters", stop, distance);
return String.format(
"stop %s at %.1f meters%s%s%s%s",
stop, distance,
distanceIndependentTime > 0 ? " +" + distanceIndependentTime + " seconds" : "",
edges != null ? " (" + edges.size() + " edges)" : "",
geometry != null ? " w/geometry" : "",
state != null ? " w/state" : ""
);
}

/**
Expand Down
Original file line number Diff line number Diff line change
@@ -1,15 +1,16 @@
package org.opentripplanner.routing.graphfinder;

import java.nio.charset.StandardCharsets;
import java.util.Base64;
import java.util.List;
import java.util.Objects;
import org.opentripplanner.model.FeedScopedId;
import org.opentripplanner.model.Stop;
import org.opentripplanner.model.TripPattern;
import org.opentripplanner.model.TripTimeShort;
import org.opentripplanner.model.base.ToStringBuilder;
import org.opentripplanner.routing.RoutingService;

import java.nio.charset.StandardCharsets;
import java.util.Base64;
import java.util.List;

/**
* A reference to a pattern at a specific stop.
*
Expand Down Expand Up @@ -77,4 +78,28 @@ public List<TripTimeShort> getStoptimes(
omitNonPickups
);
}

@Override
public boolean equals(Object o) {
if (this == o) { return true; }
if (o == null || getClass() != o.getClass()) { return false; }
final PatternAtStop that = (PatternAtStop) o;
return Objects.equals(id, that.id)
&& Objects.equals(stop, that.stop)
&& Objects.equals(pattern, that.pattern);
}

@Override
public int hashCode() {
return Objects.hash(id, stop, pattern);
}

@Override
public String toString() {
return ToStringBuilder.of(getClass())
.addStr("id", id)
.addObj("stop", stop)
.addObj("pattern", pattern)
.toString();
}
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,8 @@
package org.opentripplanner.routing.graphfinder;

import java.util.Objects;
import org.opentripplanner.model.base.ToStringBuilder;

/**
* A place of any of the types defined in PlaceType at a specified distance.
*
Expand All @@ -14,4 +17,26 @@ public PlaceAtDistance(Object place, double distance) {
this.place = place;
this.distance = distance;
}

@Override
public boolean equals(Object o) {
if (this == o) { return true; }
if (o == null || getClass() != o.getClass()) { return false; }
final PlaceAtDistance that = (PlaceAtDistance) o;
return Double.compare(that.distance, distance) == 0
&& Objects.equals(place, that.place);
}

@Override
public int hashCode() {
return Objects.hash(place, distance);
}

@Override
public String toString() {
return ToStringBuilder.of(getClass())
.addObj("place", place)
.addNum("distance", distance)
.toString();
}
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
package org.opentripplanner.routing.graphfinder;

import static java.lang.Integer.min;

import java.util.Comparator;
import java.util.List;
import org.opentripplanner.model.FeedScopedId;
import org.opentripplanner.model.GenericLocation;
import org.opentripplanner.model.TransitMode;
Expand All @@ -13,11 +17,6 @@
import org.opentripplanner.routing.graph.Graph;
import org.opentripplanner.routing.spt.DominanceFunction;

import java.util.Comparator;
import java.util.List;

import static java.lang.Integer.min;

/**
* A GraphFinder which uses the street network to traverse the graph in order to find the nearest
* stops and/or places from the origin.
Expand All @@ -30,6 +29,7 @@ public StreetGraphFinder(Graph graph) {
this.graph = graph;
}

@Override
public List<NearbyStop> findClosestStops(double lat, double lon, double radiusMeters) {
StopFinderTraverseVisitor visitor = new StopFinderTraverseVisitor();
findClosestUsingStreets(lat, lon, radiusMeters, visitor, null);
Expand Down Expand Up @@ -64,22 +64,20 @@ private void findClosestUsingStreets(
) {
// Make a normal OTP routing request so we can traverse edges and use GenericAStar
// TODO make a function that builds normal routing requests from profile requests
RoutingRequest rr = new RoutingRequest(TraverseMode.WALK);
rr.from = new GenericLocation(null, null, lat, lon);
rr.oneToMany = true;
rr.setRoutingContext(graph);
rr.walkSpeed = 1;
rr.dominanceFunction = new DominanceFunction.LeastWalk();
rr.rctx.remainingWeightHeuristic = new TrivialRemainingWeightHeuristic();
// RR dateTime defaults to currentTime.
// If elapsed time is not capped, searches are very slow.
rr.worstTime = (rr.dateTime + (int) radius);
AStar astar = new AStar();
rr.setNumItineraries(1);
astar.setTraverseVisitor(visitor);
astar.getShortestPathTree(rr, 1, terminationStrategy); // timeout in seconds
// Destroy the routing context, to clean up the temporary edges & vertices
rr.rctx.destroy();
try (RoutingRequest rr = new RoutingRequest(TraverseMode.WALK)) {
rr.from = new GenericLocation(null, null, lat, lon);
rr.oneToMany = true;
rr.setRoutingContext(graph);
rr.walkSpeed = 1;
rr.dominanceFunction = new DominanceFunction.LeastWalk();
rr.rctx.remainingWeightHeuristic = new TrivialRemainingWeightHeuristic();
// RR dateTime defaults to currentTime.
// If elapsed time is not capped, searches are very slow.
rr.worstTime = (rr.dateTime + (int) radius);
AStar astar = new AStar();
rr.setNumItineraries(1);
astar.setTraverseVisitor(visitor);
astar.getShortestPathTree(rr, 1, terminationStrategy); // timeout in seconds
}
}

}
Original file line number Diff line number Diff line change
@@ -1,6 +1,11 @@
package org.opentripplanner.api.parameter;

import static org.junit.jupiter.api.Assertions.assertEquals;
import org.junit.Test;
import org.opentripplanner.routing.api.request.RequestModes;

import javax.ws.rs.BadRequestException;
import java.util.Set;

import static org.junit.jupiter.api.Assertions.assertThrows;
import static org.opentripplanner.routing.api.request.StreetMode.BIKE;
import static org.opentripplanner.routing.api.request.StreetMode.BIKE_RENTAL;
Expand All @@ -23,14 +28,14 @@ public void emptyModeSet() {
public void singleWalk() {
QualifiedModeSet modeSet = new QualifiedModeSet("WALK");
assertEquals(Set.of(new QualifiedMode("WALK")), modeSet.qModes);
assertEquals(new RequestModes(WALK, WALK, WALK, WALK, Set.of()), modeSet.getRequestModes());
assertEquals(new RequestModes(WALK, WALK, WALK, Set.of()), modeSet.getRequestModes());
}

@Test
public void multipleWalks() {
QualifiedModeSet modeSet = new QualifiedModeSet("WALK,WALK,WALK");
assertEquals(Set.of(new QualifiedMode("WALK")), modeSet.qModes);
assertEquals(new RequestModes(WALK, WALK, WALK, WALK, Set.of()), modeSet.getRequestModes());
assertEquals(new RequestModes(WALK, WALK, WALK, Set.of()), modeSet.getRequestModes());
}

@Test
Expand All @@ -40,7 +45,7 @@ public void singleWalkAndBicycle() {
new QualifiedMode("WALK"),
new QualifiedMode("BICYCLE")
), modeSet.qModes);
assertEquals(new RequestModes(BIKE, BIKE, BIKE, BIKE, Set.of()), modeSet.getRequestModes());
assertEquals(new RequestModes(BIKE, BIKE, BIKE, Set.of()), modeSet.getRequestModes());
}

@Test
Expand All @@ -60,7 +65,7 @@ public void singleWalkAndBicycleToPark() {
new QualifiedMode("WALK"),
new QualifiedMode("BICYCLE_PARK")
), modeSet.qModes);
assertEquals(new RequestModes(BIKE_TO_PARK, WALK, WALK, BIKE_TO_PARK, Set.of()), modeSet.getRequestModes());
assertEquals(new RequestModes(BIKE_TO_PARK, WALK, BIKE_TO_PARK, Set.of()), modeSet.getRequestModes());
}

@Test
Expand All @@ -70,7 +75,7 @@ public void multipleWalksAndBicycle() {
new QualifiedMode("WALK"),
new QualifiedMode("BICYCLE")
), modeSet.qModes);
assertEquals(new RequestModes(BIKE, BIKE, BIKE, BIKE, Set.of()), modeSet.getRequestModes());
assertEquals(new RequestModes(BIKE, BIKE, BIKE, Set.of()), modeSet.getRequestModes());
}

@Test
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
import org.opentripplanner.model.Entrance;
import org.opentripplanner.model.FeedScopedId;
import org.opentripplanner.model.Stop;
import org.opentripplanner.model.TripPattern;
import org.opentripplanner.model.WgsCoordinate;
import org.opentripplanner.model.WheelChairBoarding;
import org.opentripplanner.routing.algorithm.astar.AStar;
Expand Down Expand Up @@ -65,7 +66,6 @@ public Graph graph() {
return graph;
}


public <T> T v(String label) {
return vertex(label);
}
Expand Down Expand Up @@ -339,6 +339,11 @@ public StreetVehicleParkingLink link(VehicleParkingEntranceVertex from, StreetVe
public List<StreetVehicleParkingLink> biLink(StreetVertex from, VehicleParkingEntranceVertex to) {
return List.of(link(from, to), link(to, from));
}

// Transit
public void tripPattern(TripPattern tripPattern) {
graph.tripPatternForId.put(tripPattern.getId(), tripPattern);
}
}

public static String graphPathToString(GraphPath graphPath) {
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,66 @@
package org.opentripplanner.routing.graphfinder;

import static org.junit.jupiter.api.Assertions.assertEquals;

import java.util.Arrays;
import java.util.List;
import java.util.stream.IntStream;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
import org.locationtech.jts.geom.Coordinate;
import org.locationtech.jts.geom.GeometryFactory;
import org.locationtech.jts.geom.LineString;
import org.opentripplanner.common.geometry.GeometryUtils;
import org.opentripplanner.routing.algorithm.GraphRoutingTest;
import org.opentripplanner.routing.graph.Graph;
import org.opentripplanner.routing.vertextype.TransitStopVertex;

class DirectGraphFinderTest extends GraphRoutingTest {

private static GeometryFactory geometryFactory = GeometryUtils.getGeometryFactory();

private Graph graph;

private TransitStopVertex S1, S2, S3;

@BeforeEach
protected void setUp() throws Exception {
graph = graphOf(new Builder() {
@Override
public void build() {
S1 = stop("S1", 47.500, 19);
S2 = stop("S2", 47.510, 19);
S3 = stop("S3", 47.520, 19);
}
});
}

@Test
void findClosestStops() {
var ns1 = new NearbyStop(S1, 0, null, linestring(47.500, 19.000, 47.500, 19.000), null);
var ns2 = new NearbyStop(S2, 1112, null, linestring(47.500, 19.000, 47.510, 19.000), null);

var testee = new DirectGraphFinder(graph);
assertEquals(
List.of(ns1),
testee.findClosestStops(47.500, 19.000, 100)
);

assertEquals(
List.of(ns1, ns2),
testee.findClosestStops(47.500, 19.000, 2000)
);
}

static LineString linestring(double ... latlon) {
if (latlon.length % 2 != 0) {
throw new IllegalArgumentException("Uneven number of parameters: " + Arrays.toString(latlon));
}

return geometryFactory.createLineString(
IntStream.range(0, latlon.length / 2)
.mapToObj(i -> new Coordinate(latlon[i * 2 + 1], latlon[i * 2]))
.toArray(Coordinate[]::new)
);
}
}
Loading

0 comments on commit 2698711

Please sign in to comment.