From b14a3824abdab43d02ddef4fda43dd1f9c8b8a33 Mon Sep 17 00:00:00 2001 From: Chengqi Lu <43133404+luchengqi7@users.noreply.github.com> Date: Thu, 11 Apr 2024 11:42:17 +0200 Subject: [PATCH] Add a new estimator approach --- .../EuclideanDistanceBasedDrtEstimator.java | 78 +++++++++++++++++++ .../DrtTeleportationWithModeChoiceTest.java | 13 +++- 2 files changed, 87 insertions(+), 4 deletions(-) create mode 100644 contribs/drt/src/main/java/org/matsim/contrib/drt/estimator/impl/EuclideanDistanceBasedDrtEstimator.java diff --git a/contribs/drt/src/main/java/org/matsim/contrib/drt/estimator/impl/EuclideanDistanceBasedDrtEstimator.java b/contribs/drt/src/main/java/org/matsim/contrib/drt/estimator/impl/EuclideanDistanceBasedDrtEstimator.java new file mode 100644 index 00000000000..dd3a2492ce9 --- /dev/null +++ b/contribs/drt/src/main/java/org/matsim/contrib/drt/estimator/impl/EuclideanDistanceBasedDrtEstimator.java @@ -0,0 +1,78 @@ +package org.matsim.contrib.drt.estimator.impl; + +import org.matsim.api.core.v01.Coord; +import org.matsim.api.core.v01.network.Network; +import org.matsim.contrib.drt.estimator.DrtEstimator; +import org.matsim.contrib.drt.routing.DrtRoute; +import org.matsim.core.utils.geometry.CoordUtils; +import org.matsim.core.utils.misc.OptionalTime; + +import java.util.Random; + +public class EuclideanDistanceBasedDrtEstimator implements DrtEstimator { + private final Network network; + /** + * For travel distance related scoring (e.g., marginal utility distance), we need estimated network distance: + * Estimated network distance = Euclidean distance * network distance factor + */ + private final double networkDistanceFactor; + /** + * Slope of the linear regression + */ + private final double slope; + /** + * Intercept of the linear regression + */ + private final double intercept; + + private final double estimatedMeanWaitTime; + + private final double waitTimeStd; + + private final double mu; + private final double sigma; + private final Random random = new Random(1234); + + /** + * We use log normal distribution to estimate the ride duration of each individual trip. The distribution + * is based on the linear regression. + * @params networkDistanceFactor: Estimated network distance = Euclidean distance * network distance factor + * @params slope: slope for the linear regression + * @params intercept: intercept for linear regression + * @params mu: mu for log normal distribution + * @params sigma: sigma for log normal distribution. + */ + public EuclideanDistanceBasedDrtEstimator(Network network, double networkDistanceFactor, double slope, + double intercept, double estimatedMeanWaitTime, double waitTimeStd, + double mu, double sigma) { + this.network = network; + this.networkDistanceFactor = networkDistanceFactor; + this.slope = slope; + this.intercept = intercept; + this.estimatedMeanWaitTime = estimatedMeanWaitTime; + this.waitTimeStd = waitTimeStd; + this.mu = mu; + this.sigma = sigma; + } + + @Override + public Estimate estimate(DrtRoute route, OptionalTime departureTime) { + Coord fromCoord = network.getLinks().get(route.getStartLinkId()).getToNode().getCoord(); + Coord toCoord = network.getLinks().get(route.getEndLinkId()).getToNode().getCoord(); + double euclideanDistance = CoordUtils.calcEuclideanDistance(fromCoord, toCoord); + double typicalRideDuration = euclideanDistance * slope + intercept; + double typicalRideDistance = networkDistanceFactor * euclideanDistance; + double randomFactor = nextLogNormal(mu, sigma); + double waitTime = Math.max(estimatedMeanWaitTime * (1 + random.nextGaussian() * waitTimeStd), 0); + + return new Estimate(typicalRideDistance * randomFactor, typicalRideDuration * randomFactor, + waitTime, 0); + } + + public double nextLogNormal(double mu, double sigma) { + if (sigma == 0) + return Math.exp(mu); + + return Math.exp(sigma * random.nextGaussian() + mu); + } +} diff --git a/contribs/drt/src/test/java/org/matsim/contrib/drt/teleportation/DrtTeleportationWithModeChoiceTest.java b/contribs/drt/src/test/java/org/matsim/contrib/drt/teleportation/DrtTeleportationWithModeChoiceTest.java index 461a5c78192..effd09b64ac 100644 --- a/contribs/drt/src/test/java/org/matsim/contrib/drt/teleportation/DrtTeleportationWithModeChoiceTest.java +++ b/contribs/drt/src/test/java/org/matsim/contrib/drt/teleportation/DrtTeleportationWithModeChoiceTest.java @@ -4,8 +4,10 @@ import org.junit.jupiter.api.Test; import org.junit.jupiter.api.extension.RegisterExtension; import org.matsim.api.core.v01.TransportMode; +import org.matsim.api.core.v01.network.Network; import org.matsim.contrib.drt.estimator.DrtEstimator; import org.matsim.contrib.drt.estimator.impl.DetourBasedDrtEstimator; +import org.matsim.contrib.drt.estimator.impl.EuclideanDistanceBasedDrtEstimator; import org.matsim.contrib.drt.run.DrtConfigGroup; import org.matsim.contrib.drt.run.DrtControlerCreator; import org.matsim.contrib.drt.run.MultiModeDrtConfigGroup; @@ -37,7 +39,7 @@ void testModeChoice() { config.network().setInputFile("network.xml"); config.plans().setInputFile("plans_only_drt_4.0.xml.gz"); config.controller().setOutputDirectory(utils.getOutputDirectory()); - config.controller().setLastIteration(100); + config.controller().setLastIteration(3); config.replanning().setFractionOfIterationsToDisableInnovation(0.8); config.replanning().setMaxAgentPlanMemorySize(3); @@ -58,7 +60,7 @@ void testModeChoice() { bikeModeParams.setMarginalUtilityOfTraveling(-6.); config.scoring().addModeParams(bikeModeParams); // Update change mode - config.changeMode().setModes( new String[] { TransportMode.drt, TransportMode.bike }); + config.changeMode().setModes(new String[]{TransportMode.drt, TransportMode.bike}); // Setting DRT config group DrtConfigGroup drtConfigGroup = DrtConfigGroup.getSingleModeDrtConfig(config); @@ -70,8 +72,11 @@ void testModeChoice() { controler.addOverridingModule(new AbstractDvrpModeModule(drtConfigGroup.mode) { @Override public void install() { - bindModal(DrtEstimator.class).toInstance(DetourBasedDrtEstimator.normalDistributed(1.2, 32, - 0.3, 300, 0.4)); +// bindModal(DrtEstimator.class).toInstance(DetourBasedDrtEstimator.normalDistributed(1.2, 32, +// 0.3, 300, 0.4)); + bindModal(DrtEstimator.class).toProvider(modalProvider(getter -> new + EuclideanDistanceBasedDrtEstimator(getter.getModal(Network.class), 2.0, 0.1577493, + 103.0972273, 120, 0.3, -0.1, 0.28))); } });