At some point, this code changed:
using SDDP, GLPK
const demand_probs = Dict(:Ah => [0.2, 0.8], :Bh => [0.8, 0.2])
graph = SDDP.Graph(
:root_node,
[:Ad, :Ah, :Bd, :Bh],
[
(:root_node => :Ad, 0.5),
(:root_node => :Bd, 0.5),
(:Ad => :Ah, 1.0),
(:Ah => :Ad, 0.9),
(:Bd => :Bh, 1.0),
(:Bh => :Bd, 0.9),
],
)
SDDP.add_ambiguity_set(graph, [:Ad, :Bd], 1e2)
SDDP.add_ambiguity_set(graph, [:Ah, :Bh], 1e2)
model = SDDP.PolicyGraph(
graph,
lower_bound = 0.0,
optimizer = GLPK.Optimizer,
) do subproblem, node
@variable(subproblem, 0 <= inventory <= 2, SDDP.State, initial_value = 0.0)
@variable(subproblem, buy >= 0)
@variable(subproblem, demand == 0)
@constraint(subproblem, demand == inventory.in - inventory.out + buy)
if node == :Ad || node == :Bd
@stageobjective(subproblem, buy)
else
SDDP.parameterize(subproblem, 1:2, demand_probs[node]) do ω
JuMP.fix(demand, ω)
end
@stageobjective(subproblem, 2 * buy + inventory.out)
end
end
SDDP.train(model; iteration_limit = 200)
simulations = SDDP.simulate(
model,
2_000;
sampling_scheme = SDDP.InSampleMonteCarlo(;
max_depth = 50,
terminate_on_dummy_leaf = false,
),
)
function calculate_objective(simulation)
ρ(t) = 0.9^div(t - 1, 2)
return sum(ρ(t) * s[:stage_objective] for (t, s) in enumerate(simulation))
end
objectives = calculate_objective.(simulations)
minimum(objectives)
I'm currently bisecting.
Known good:
(sddp) pkg> st
Status `/private/tmp/sddp/Project.toml`
[60bf3e95] GLPK v0.14.14
[f4570300] SDDP v0.4.3
[9a3f8284] Random
[10745b16] Statistics
Known bad:
(sddp) pkg> st
Status `/private/tmp/sddp/Project.toml`
[60bf3e95] GLPK v0.15.3
[f4570300] SDDP v0.4.4
[9a3f8284] Random
[10745b16] Statistics
At some point, this code changed:
I'm currently bisecting.
Known good:
Known bad: