Skip to content

Commit

Permalink
Pass expiry through LBCS and clampedIntegrate
Browse files Browse the repository at this point in the history
Removes the use of eraseExpiry in LinearBoundaryConsistencySolver.
This was a patch put in place to support feedback loops involving the solver,
but it erases too much information. Leaving the expiry in place and erasing it
only when actually building a feedback loop lets downstream components like approximations
take that expiry into account.

Also reconfigures the use of eraseExpiry in clampedIntegrate to pass expiry information through.
  • Loading branch information
David Legg authored and mattdailis committed Mar 1, 2024
1 parent 762a534 commit fac6582
Show file tree
Hide file tree
Showing 2 changed files with 6 additions and 6 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,6 @@
import static gov.nasa.jpl.aerie.contrib.streamline.core.Expiring.neverExpiring;
import static gov.nasa.jpl.aerie.contrib.streamline.core.Reactions.whenever;
import static gov.nasa.jpl.aerie.contrib.streamline.core.monads.ExpiringMonad.bind;
import static gov.nasa.jpl.aerie.contrib.streamline.core.Resources.eraseExpiry;
import static gov.nasa.jpl.aerie.contrib.streamline.debugging.Context.contextualized;
import static gov.nasa.jpl.aerie.contrib.streamline.debugging.Dependencies.addDependency;
import static gov.nasa.jpl.aerie.contrib.streamline.debugging.Naming.getName;
Expand Down Expand Up @@ -314,7 +313,7 @@ private Stream<DirectionalConstraint> directionalConstraints(Variable constraine
// Expiry for driven terms is captured by re-solving rather than expiring the solution.
// If solver has a feedback loop from last iteration (which is common)
// feeding that expiry in here can loop the solver forever.
var result = eraseExpiry(drivenTerm);
var result = drivenTerm;
for (var drivingVariable : drivingVariables) {
var scale = controlledTerm.get(drivingVariable);
var domain = domains.get(drivingVariable);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -364,6 +364,7 @@ public static ClampedIntegrateResult clampedIntegrate(
Resource<Polynomial> integrand, Resource<Polynomial> lowerBound, Resource<Polynomial> upperBound, double startingValue) {
LinearBoundaryConsistencySolver rateSolver = new LinearBoundaryConsistencySolver("clampedIntegrate rate solver");
var integral = resource(polynomial(startingValue));
var neverExpiringIntegral = eraseExpiry(integral);

// Solve for the rate as a function of value
var overflowRate = rateSolver.variable("overflowRate", Domain::lowerBound);
Expand All @@ -377,11 +378,11 @@ public static ClampedIntegrateResult clampedIntegrate(

// Set up rate clamping conditions
var integrandUB = choose(
greaterThanOrEquals(integral, upperBound),
greaterThanOrEquals(neverExpiringIntegral, upperBound),
differentiate(upperBound),
constant(Double.POSITIVE_INFINITY));
var integrandLB = choose(
lessThanOrEquals(integral, lowerBound),
lessThanOrEquals(neverExpiringIntegral, lowerBound),
differentiate(lowerBound),
constant(Double.NEGATIVE_INFINITY));

Expand All @@ -390,10 +391,10 @@ public static ClampedIntegrateResult clampedIntegrate(

// Use a simple feedback loop on volumes to do the integration and clamping.
// Clamping here takes care of discrete under-/overflows and overshooting bounds due to discrete time steps.
var clampedCell = clamp(integral, lowerBound, upperBound);
var clampedCell = clamp(neverExpiringIntegral, lowerBound, upperBound);
var correctedCell = map(clampedCell, rate.resource(), (v, r) -> r.integral(v.extract()));
// Use the corrected integral values to set volumes, but erase expiry information in the process to avoid loops
forward(eraseExpiry(correctedCell), integral);
forward(correctedCell, integral);

name(integral, "Clamped Integral (%s)", integrand);
name(overflowRate.resource(), "Overflow of %s", integral);
Expand Down

0 comments on commit fac6582

Please sign in to comment.