com.powsybl.openrao.searchtreerao.commons.optimizationperimeters.AbstractOptimizationPerimeter Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of open-rao-search-tree-rao Show documentation
Show all versions of open-rao-search-tree-rao Show documentation
Implementation of search tree remedial action optimisation with modular approach
The newest version!
/*
* Copyright (c) 2022, RTE (http://www.rte-france.com)
* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
*/
package com.powsybl.openrao.searchtreerao.commons.optimizationperimeters;
import com.powsybl.openrao.data.crac.api.Identifiable;
import com.powsybl.openrao.data.crac.api.State;
import com.powsybl.openrao.data.crac.api.cnec.Cnec;
import com.powsybl.openrao.data.crac.api.cnec.FlowCnec;
import com.powsybl.openrao.data.crac.api.networkaction.NetworkAction;
import com.powsybl.openrao.data.crac.api.rangeaction.RangeAction;
import com.powsybl.openrao.data.crac.loopflowextension.LoopFlowThreshold;
import com.powsybl.openrao.raoapi.parameters.RaoParameters;
import com.powsybl.openrao.raoapi.parameters.extensions.LoopFlowParametersExtension;
import com.powsybl.openrao.searchtreerao.result.api.RangeActionSetpointResult;
import com.powsybl.iidm.network.Network;
import java.util.*;
import java.util.stream.Collectors;
import static com.powsybl.openrao.commons.logs.OpenRaoLoggerProvider.BUSINESS_WARNS;
/**
* @author Baptiste Seguinot {@literal }
*/
public abstract class AbstractOptimizationPerimeter implements OptimizationPerimeter {
private final State mainOptimizationState;
private final Set monitoredStates;
private final Set flowCnecs;
private final Set optimizedFlowCnecs;
private final Set monitoredFlowCnecs;
private final Set loopFlowCnecs;
private final Set availableNetworkActions;
private final Map>> availableRangeActions;
protected AbstractOptimizationPerimeter(State mainOptimizationState,
Set flowCnecs,
Set loopFlowCnecs,
Set availableNetworkActions,
Map>> availableRangeActions) {
this.mainOptimizationState = mainOptimizationState;
this.monitoredStates = flowCnecs.stream().map(FlowCnec::getState).collect(Collectors.toSet());
this.flowCnecs = new TreeSet<>(Comparator.comparing(Identifiable::getId));
this.flowCnecs.addAll(flowCnecs);
this.optimizedFlowCnecs = new TreeSet<>(Comparator.comparing(Identifiable::getId));
this.optimizedFlowCnecs.addAll(flowCnecs.stream().filter(Cnec::isOptimized).collect(Collectors.toSet()));
this.monitoredFlowCnecs = new TreeSet<>(Comparator.comparing(Identifiable::getId));
this.monitoredFlowCnecs.addAll(flowCnecs.stream().filter(Cnec::isMonitored).collect(Collectors.toSet()));
this.loopFlowCnecs = new TreeSet<>(Comparator.comparing(Identifiable::getId));
this.loopFlowCnecs.addAll(loopFlowCnecs);
this.availableNetworkActions = new TreeSet<>(Comparator.comparing(Identifiable::getId));
this.availableNetworkActions.addAll(availableNetworkActions);
this.availableRangeActions = new TreeMap<>(Comparator.comparing(State::getId));
availableRangeActions.forEach((state, rangeActions) -> {
Set> rangeActionSet = new TreeSet<>(Comparator.comparing(Identifiable::getId));
rangeActionSet.addAll(availableRangeActions.get(state));
this.availableRangeActions.put(state, rangeActionSet);
});
}
@Override
public State getMainOptimizationState() {
return mainOptimizationState;
}
@Override
public Set getRangeActionOptimizationStates() {
return availableRangeActions.keySet();
}
@Override
public Set getMonitoredStates() {
return monitoredStates;
}
@Override
public Set getFlowCnecs() {
return flowCnecs;
}
@Override
public Set getOptimizedFlowCnecs() {
return optimizedFlowCnecs;
}
@Override
public Set getMonitoredFlowCnecs() {
return monitoredFlowCnecs;
}
@Override
public Set getLoopFlowCnecs() {
return loopFlowCnecs;
}
@Override
public Set getNetworkActions() {
return availableNetworkActions;
}
@Override
public Map>> getRangeActionsPerState() {
return availableRangeActions;
}
@Override
public Set> getRangeActions() {
return availableRangeActions.values().stream().flatMap(Collection::stream).collect(Collectors.toSet());
}
public static Set getLoopFlowCnecs(Set flowCnecs, RaoParameters raoParameters, Network network) {
if (raoParameters.hasExtension(LoopFlowParametersExtension.class)
&& !raoParameters.getExtension(LoopFlowParametersExtension.class).getCountries().isEmpty()) {
// loopFlow limited, and set of country for which loop-flow are monitored is defined
return flowCnecs.stream()
.filter(cnec -> !Objects.isNull(cnec.getExtension(LoopFlowThreshold.class)) &&
cnec.getLocation(network).stream().anyMatch(country -> country.isPresent() && raoParameters.getExtension(LoopFlowParametersExtension.class).getCountries().contains(country.get())))
.collect(Collectors.toSet());
} else if (raoParameters.hasExtension(LoopFlowParametersExtension.class)) {
// loopFlow limited, but no set of country defined
return flowCnecs.stream()
.filter(cnec -> !Objects.isNull(cnec.getExtension(LoopFlowThreshold.class)))
.collect(Collectors.toSet());
} else {
//no loopFLow limitation
return Collections.emptySet();
}
}
static boolean doesPrePerimeterSetpointRespectRange(RangeAction> rangeAction, RangeActionSetpointResult prePerimeterSetpoints) {
double preperimeterSetPoint = prePerimeterSetpoints.getSetpoint(rangeAction);
double minSetPoint = rangeAction.getMinAdmissibleSetpoint(preperimeterSetPoint);
double maxSetPoint = rangeAction.getMaxAdmissibleSetpoint(preperimeterSetPoint);
if (preperimeterSetPoint < minSetPoint || preperimeterSetPoint > maxSetPoint) {
BUSINESS_WARNS.warn("Range action {} has an initial setpoint of {} that does not respect its allowed range [{} {}]. It will be filtered out of the linear problem.",
rangeAction.getId(), preperimeterSetPoint, minSetPoint, maxSetPoint);
return false;
} else {
return true;
}
}
/**
* If aligned range actions' initial setpoint are different, this function filters them out
*/
static void removeAlignedRangeActionsWithDifferentInitialSetpoints(Set> rangeActions, RangeActionSetpointResult prePerimeterSetPoints) {
Set groups = rangeActions.stream().map(RangeAction::getGroupId)
.filter(Optional::isPresent).map(Optional::get).collect(Collectors.toSet());
for (String group : groups) {
Set> groupRangeActions = rangeActions.stream().filter(rangeAction -> rangeAction.getGroupId().isPresent() && rangeAction.getGroupId().get().equals(group)).collect(Collectors.toSet());
double preperimeterSetPoint = prePerimeterSetPoints.getSetpoint(groupRangeActions.iterator().next());
if (groupRangeActions.stream().anyMatch(rangeAction -> Math.abs(prePerimeterSetPoints.getSetpoint(rangeAction) - preperimeterSetPoint) > 1e-6)) {
BUSINESS_WARNS.warn("Range actions of group {} do not have the same prePerimeter setpoint. They will be filtered out of the linear problem.", group);
rangeActions.removeAll(groupRangeActions);
}
}
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy