Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -73,8 +73,7 @@ public CastorContingencyScenarios(Crac crac,
}

public Map<State, PostPerimeterResult> optimizeContingencyScenarios(Network network,
PrePerimeterResult prePerimeterSensitivityOutput,
boolean automatonsOnly) {
PrePerimeterResult prePerimeterSensitivityOutput) {
Map<State, PostPerimeterResult> contingencyScenarioResults = new ConcurrentHashMap<>();
// Create a new variant
String newVariant = RandomizedString.getRandomizedString(CONTINGENCY_SCENARIO, network.getVariantManager().getVariantIds(), 10);
Expand All @@ -86,7 +85,7 @@ public Map<State, PostPerimeterResult> optimizeContingencyScenarios(Network netw
try (AbstractNetworkPool networkPool = AbstractNetworkPool.create(network, newVariant, getAvailableCPUs(raoParameters), true)) {
AtomicInteger remainingScenarios = new AtomicInteger(stateTree.getContingencyScenarios().size());
List<ForkJoinTask<Object>> tasks = stateTree.getContingencyScenarios().stream().map(optimizedScenario ->
networkPool.submit(() -> runScenario(prePerimeterSensitivityOutput, automatonsOnly, optimizedScenario, networkPool, automatonSimulator, contingencyScenarioResults, remainingScenarios))
networkPool.submit(() -> runScenario(prePerimeterSensitivityOutput, optimizedScenario, networkPool, automatonSimulator, contingencyScenarioResults, remainingScenarios))
).toList();
for (ForkJoinTask<Object> task : tasks) {
try {
Expand All @@ -102,7 +101,7 @@ public Map<State, PostPerimeterResult> optimizeContingencyScenarios(Network netw
return contingencyScenarioResults;
}

private Object runScenario(PrePerimeterResult prePerimeterSensitivityOutput, boolean automatonsOnly, ContingencyScenario optimizedScenario, AbstractNetworkPool networkPool, AutomatonSimulator automatonSimulator, Map<State, PostPerimeterResult> contingencyScenarioResults, AtomicInteger remainingScenarios) throws InterruptedException {
private Object runScenario(PrePerimeterResult prePerimeterSensitivityOutput, ContingencyScenario optimizedScenario, AbstractNetworkPool networkPool, AutomatonSimulator automatonSimulator, Map<State, PostPerimeterResult> contingencyScenarioResults, AtomicInteger remainingScenarios) throws InterruptedException {
Network networkClone = networkPool.getAvailableNetwork(); //This is where the threads actually wait for available networks
TECHNICAL_LOGS.info("Optimizing scenario post-contingency {}.", optimizedScenario.getContingency().getId());

Expand All @@ -129,15 +128,14 @@ private Object runScenario(PrePerimeterResult prePerimeterSensitivityOutput, boo
// Do not simulate curative instant if last sensitivity analysis failed
// -- if there was no automaton state, check prePerimeterSensitivityOutput sensi status
// -- or if there was an automaton state that failed
if (!automatonsOnly
&& automatonState.isEmpty()
if (automatonState.isEmpty()
&& !optimizedScenario.getCurativePerimeters().isEmpty()
&& prePerimeterSensitivityOutput.getSensitivityStatus(optimizedScenario.getCurativePerimeters().get(0).getRaOptimisationState()) == ComputationStatus.FAILURE
|| automatonState.isPresent()
&& autoStateSensiFailed
) {
curativeStates.forEach(curativeState -> contingencyScenarioResults.put(curativeState, generateSkippedPostPerimeterResult(curativeState, sensitivityFailureOvercost)));
} else if (!automatonsOnly) {
} else {
boolean allPreviousPerimetersSucceded = true;
PrePerimeterResult previousPerimeterResult = preCurativeResult;
// Optimize curative perimeters
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -170,7 +170,7 @@ public CompletableFuture<RaoResult> run() {
BUSINESS_LOGS.info("----- Post-contingency perimeters optimization [start]");
TreeParameters curativeTreeParameters = TreeParameters.buildForCurativePerimeter(raoParameters, preventiveOptimalCost);
CastorContingencyScenarios castorContingencyScenarios = new CastorContingencyScenarios(crac, raoParameters, toolProvider, stateTree, curativeTreeParameters, initialOutput);
Map<State, PostPerimeterResult> postContingencyResults = castorContingencyScenarios.optimizeContingencyScenarios(network, preCurativeSensitivityAnalysisOutput, false);
Map<State, PostPerimeterResult> postContingencyResults = castorContingencyScenarios.optimizeContingencyScenarios(network, preCurativeSensitivityAnalysisOutput);
BUSINESS_LOGS.info("----- Post-contingency perimeters optimization [end]");

// ----- SECOND PREVENTIVE PERIMETER OPTIMIZATION -----
Expand All @@ -180,7 +180,7 @@ public CompletableFuture<RaoResult> run() {
// Run second preventive when necessary
CastorSecondPreventive castorSecondPreventive = new CastorSecondPreventive(crac, raoParameters, network, stateTree, toolProvider, targetEndInstant);
if (castorSecondPreventive.shouldRunSecondPreventiveRao(preventiveResult, postContingencyResults.values(), mergedRaoResults, preventiveRaoTime)) {
RaoResult secondPreventiveRaoResults = castorSecondPreventive.runSecondPreventiveAndAutoRao(castorContingencyScenarios, prePerimeterSensitivityAnalysis, initialOutput, postPreventiveResult, postContingencyResults);
RaoResult secondPreventiveRaoResults = castorSecondPreventive.runSecondPreventiveAutoAndCurativeRao(castorContingencyScenarios, prePerimeterSensitivityAnalysis, initialOutput, postPreventiveResult, postContingencyResults);
if (secondPreventiveImprovesResults(secondPreventiveRaoResults, mergedRaoResults)) {
mergedRaoResults = secondPreventiveRaoResults;
mergedRaoResults.setExecutionDetails(OptimizationStepsExecuted.SECOND_PREVENTIVE_IMPROVED_FIRST);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -134,11 +134,11 @@ private static boolean isFinalCostWorseThanPreventive(double curativeMinObjImpro
return postFirstRaoResult.getCost(curativeInstant) > preventiveResult.getCost() - curativeMinObjImprovement;
}

RaoResult runSecondPreventiveAndAutoRao(CastorContingencyScenarios castorContingencyScenarios,
PrePerimeterSensitivityAnalysis prePerimeterSensitivityAnalysis,
PrePerimeterResult initialOutput,
PostPerimeterResult firstPreventiveResult,
Map<State, PostPerimeterResult> postContingencyResults) {
RaoResult runSecondPreventiveAutoAndCurativeRao(CastorContingencyScenarios castorContingencyScenarios,
PrePerimeterSensitivityAnalysis prePerimeterSensitivityAnalysis,
PrePerimeterResult initialOutput,
PostPerimeterResult firstPreventiveResult,
Map<State, PostPerimeterResult> postContingencyResults) {
// Run 2nd preventive RAO
SecondPreventiveRaoResult secondPreventiveRaoResult;
try {
Expand All @@ -151,10 +151,10 @@ RaoResult runSecondPreventiveAndAutoRao(CastorContingencyScenarios castorConting
return new FailedRaoResultImpl(String.format("RAO failed during second preventive : %s", e.getMessage()));
}

// Run 2nd automaton simulation and update results
BUSINESS_LOGS.info("----- Second automaton simulation [start]");
Map<State, PostPerimeterResult> newPostContingencyResults = castorContingencyScenarios.optimizeContingencyScenarios(network, secondPreventiveRaoResult.postPraSensitivityAnalysisOutput, true);
BUSINESS_LOGS.info("----- Second automaton simulation [end]");
// Run 2nd automaton simulation, 2nd curative optimization and update results
BUSINESS_LOGS.info("----- Re-optimization of post-contingency scenarios [start]");
Map<State, PostPerimeterResult> newPostContingencyResults = castorContingencyScenarios.optimizeContingencyScenarios(network, secondPreventiveRaoResult.postPraSensitivityAnalysisOutput);
BUSINESS_LOGS.info("----- Re-optimization of post-contingency scenarios [end]");

BUSINESS_LOGS.info("Merging first, second preventive and post-contingency RAO results:");
// Always re-run curative sensitivity analysis (re-run is necessary in several specific cases)
Expand All @@ -163,21 +163,21 @@ RaoResult runSecondPreventiveAndAutoRao(CastorContingencyScenarios castorConting
// ------ appliedCras from secondPreventiveRaoResult
AppliedRemedialActions appliedArasAndCras = secondPreventiveRaoResult.appliedArasAndCras().copyCurative();
// ------ + curative range actions optimized during second preventive with global optimization
if (getSecondPreventiveReOptimizeCurativeRangeActions(raoParameters)) {
for (Map.Entry<State, PostPerimeterResult> entry : postContingencyResults.entrySet()) {
State state = entry.getKey();
if (!state.getInstant().isCurative()) {
continue;
}
secondPreventiveRaoResult.perimeterResult().getActivatedRangeActions(state)
.forEach(rangeAction -> appliedArasAndCras.addAppliedRangeAction(state, rangeAction, secondPreventiveRaoResult.perimeterResult.getOptimizedSetpoint(rangeAction, state)));
}
}
// if (getSecondPreventiveReOptimizeCurativeRangeActions(raoParameters)) {
// for (Map.Entry<State, PostPerimeterResult> entry : postContingencyResults.entrySet()) {
// State state = entry.getKey();
// if (!state.getInstant().isCurative()) {
// continue;
// }
// secondPreventiveRaoResult.perimeterResult().getActivatedRangeActions(state)
// .forEach(rangeAction -> appliedArasAndCras.addAppliedRangeAction(state, rangeAction, secondPreventiveRaoResult.perimeterResult.getOptimizedSetpoint(rangeAction, state)));
// }
// }
// ---- Auto remedial actions : computed during second auto, saved in newPostContingencyResults
// ---- only RAs from perimeters that haven't failed are included in appliedArasAndCras
// ---- this check is only performed here because SkippedOptimizationResultImpl with appliedRas can only be generated for AUTO instant
newPostContingencyResults.entrySet().stream().filter(entry ->
!(entry.getValue().getOptimizationResult() instanceof SkippedOptimizationResultImpl) && entry.getKey().getInstant().isAuto())
!(entry.getValue().getOptimizationResult() instanceof SkippedOptimizationResultImpl))
.forEach(entry -> {
appliedArasAndCras.addAppliedNetworkActions(entry.getKey(), entry.getValue().getOptimizationResult().getActivatedNetworkActions());
entry.getValue().getOptimizationResult().getActivatedRangeActions(entry.getKey()).forEach(rangeAction -> appliedArasAndCras.addAppliedRangeAction(entry.getKey(), rangeAction, entry.getValue().getOptimizationResult().getOptimizedSetpoint(rangeAction, entry.getKey())));
Expand Down
Loading