Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

HVDC AC emulation #466

Merged
merged 23 commits into from
Mar 15, 2022
Merged
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
23 changes: 21 additions & 2 deletions src/main/java/com/powsybl/openloadflow/OpenLoadFlowParameters.java
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,8 @@ public class OpenLoadFlowParameters extends AbstractExtension<LoadFlowParameters

public static final boolean VOLTAGE_PER_REACTIVE_POWER_CONTROL_DEFAULT_VALUE = false;

public static final boolean HVDC_AC_EMULATION_DEFAULT_VALUE = false;

public enum VoltageInitModeOverride {
NONE,
VOLTAGE_MAGNITUDE,
Expand Down Expand Up @@ -114,6 +116,8 @@ public enum LowImpedanceBranchMode {

private TransformerVoltageControlMode transformerVoltageControlMode = TRANSFORMER_VOLTAGE_CONTROL_MODE_DEFAULT_VALUE;

private boolean hvdcAcEmulation = HVDC_AC_EMULATION_DEFAULT_VALUE;

@Override
public String getName() {
return "open-load-flow-parameters";
Expand Down Expand Up @@ -262,6 +266,14 @@ public OpenLoadFlowParameters setTransformerVoltageControlMode(TransformerVoltag
return this;
}

public boolean isHvdcAcEmulation() {
return hvdcAcEmulation; }

public OpenLoadFlowParameters setHvdcAcEmulation(boolean hvdcAcEmulation) {
this.hvdcAcEmulation = hvdcAcEmulation;
return this;
}

public static OpenLoadFlowParameters load() {
return new OpenLoadFlowConfigLoader().load(PlatformConfig.defaultConfig());
}
Expand All @@ -284,6 +296,7 @@ public String toString() {
", newtonRaphsonConvEpsPerEq=" + newtonRaphsonConvEpsPerEq +
", voltageInitModeOverride=" + voltageInitModeOverride +
", transformerVoltageControlMode=" + transformerVoltageControlMode +
", hvdcAcEmulation=" + hvdcAcEmulation +
')';
}

Expand Down Expand Up @@ -320,6 +333,8 @@ public static class OpenLoadFlowConfigLoader implements LoadFlowParameters.Confi

public static final String TRANSFORMER_VOLTAGE_CONTROL_MODE_NAME = "transformerVoltageControlMode";

public static final String HVDC_AC_EMULATION_PARAM_NAME = "hvdcAcEmulation";

@Override
public OpenLoadFlowParameters load(PlatformConfig platformConfig) {
OpenLoadFlowParameters parameters = new OpenLoadFlowParameters();
Expand All @@ -343,6 +358,7 @@ public OpenLoadFlowParameters load(PlatformConfig platformConfig) {
.setNewtonRaphsonConvEpsPerEq(config.getDoubleProperty(NEWTON_RAPHSON_CONV_EPS_PER_EQ_NAME, DefaultNewtonRaphsonStoppingCriteria.DEFAULT_CONV_EPS_PER_EQ))
.setVoltageInitModeOverride(config.getEnumProperty(VOLTAGE_INIT_MODE_OVERRIDE_NAME, VoltageInitModeOverride.class, VOLTAGE_INIT_MODE_OVERRIDE_DEFAULT_VALUE))
.setTransformerVoltageControlMode(config.getEnumProperty(TRANSFORMER_VOLTAGE_CONTROL_MODE_NAME, TransformerVoltageControlMode.class, TRANSFORMER_VOLTAGE_CONTROL_MODE_DEFAULT_VALUE))
.setHvdcAcEmulation(config.getBooleanProperty(HVDC_AC_EMULATION_PARAM_NAME, HVDC_AC_EMULATION_DEFAULT_VALUE))
);
return parameters;
}
Expand Down Expand Up @@ -420,6 +436,7 @@ public static void logAc(LoadFlowParameters parameters, OpenLoadFlowParameters p
LOGGER.info("Voltage per reactive power control: {}", parametersExt.isVoltagePerReactivePowerControl());
LOGGER.info("Reactive Power Remote control: {}", parametersExt.hasReactivePowerRemoteControl());
LOGGER.info("Shunt voltage control: {}", parameters.isShuntCompensatorVoltageControlOn());
LOGGER.info("Hvdc Ac emulation: {}", parametersExt.isHvdcAcEmulation());
}

static VoltageInitializer getVoltageInitializer(LoadFlowParameters parameters, LfNetworkParameters networkParameters, MatrixFactory matrixFactory, Reporter reporter) {
Expand Down Expand Up @@ -478,7 +495,8 @@ static LfNetworkParameters getNetworkParameters(LoadFlowParameters parameters, O
parametersExt.hasReactivePowerRemoteControl(),
parameters.isDc(),
parameters.isShuntCompensatorVoltageControlOn(),
!parameters.isNoGeneratorReactiveLimits());
!parameters.isNoGeneratorReactiveLimits(),
parametersExt.isHvdcAcEmulation());
}

public static AcLoadFlowParameters createAcParameters(Network network, LoadFlowParameters parameters, OpenLoadFlowParameters parametersExt,
Expand Down Expand Up @@ -554,7 +572,8 @@ public static DcLoadFlowParameters createDcParameters(LoadFlowParameters paramet
false,
true,
false,
false);
false,
false); // FIXME

var equationSystemCreationParameters = new DcEquationSystemCreationParameters(true,
false,
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,81 @@
/**
* 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.openloadflow.ac.equations;

import com.powsybl.openloadflow.equations.AbstractNamedEquationTerm;
import com.powsybl.openloadflow.equations.Variable;
import com.powsybl.openloadflow.equations.VariableSet;
import com.powsybl.openloadflow.network.ElementType;
import com.powsybl.openloadflow.network.LfBus;
import com.powsybl.openloadflow.network.LfHvdc;

import java.util.List;

/**
* @author Anne Tilloy <anne.tilloy at rte-france.com>
*/
public abstract class AbstractHvdcAcEmulationFlowEquationTerm extends AbstractNamedEquationTerm<AcVariableType, AcEquationType> {

protected final Variable<AcVariableType> ph1Var;

protected final Variable<AcVariableType> ph2Var;

protected final List<Variable<AcVariableType>> variables;

protected final double k;

protected final double p0;

protected final LfHvdc hvdc;

protected final double lossFactor1;

protected final double lossFactor2;

protected AbstractHvdcAcEmulationFlowEquationTerm(LfHvdc hvdc, LfBus bus1, LfBus bus2, VariableSet<AcVariableType> variableSet) {
ph1Var = variableSet.getVariable(bus1.getNum(), AcVariableType.BUS_PHI);
ph2Var = variableSet.getVariable(bus2.getNum(), AcVariableType.BUS_PHI);
variables = List.of(ph1Var, ph2Var);
this.hvdc = hvdc;
k = hvdc.getDroop() * 180 / Math.PI;
p0 = hvdc.getP0();
lossFactor1 = hvdc.getConverterStation1().getLossFactor() / 100;
lossFactor2 = hvdc.getConverterStation2().getLossFactor() / 100;
}

protected double ph1() {
return stateVector.get(ph1Var.getRow());
}

protected double ph2() {
return stateVector.get(ph2Var.getRow());
}

protected double getLossMultiplier() {
return (1 - lossFactor1) * (1 - lossFactor2);
}

@Override
public List<Variable<AcVariableType>> getVariables() {
return variables;
}

@Override
public boolean hasRhs() {
return false;
}

@Override
public ElementType getElementType() {
return ElementType.HVDC;
}

@Override
public int getElementNum() {
return hvdc.getNum();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -717,6 +717,30 @@ private static void createImpedantBranch(LfBranch branch, LfBus bus1, LfBus bus2
}
}

private static void createHvdcAcEmulationEquations(LfHvdc hvdc, EquationSystem<AcVariableType, AcEquationType> equationSystem) {
EquationTerm<AcVariableType, AcEquationType> p1 = null;
EquationTerm<AcVariableType, AcEquationType> p2 = null;
if (hvdc.getBus1() != null && hvdc.getBus2() != null) {
p1 = new HvdcAcEmulationSide1ActiveFlowEquationTerm(hvdc, hvdc.getBus1(), hvdc.getBus2(), equationSystem.getVariableSet());
p2 = new HvdcAcEmulationSide2ActiveFlowEquationTerm(hvdc, hvdc.getBus1(), hvdc.getBus2(), equationSystem.getVariableSet());
} else {
// nothing to do
}

if (p1 != null) {
equationSystem.getEquation(hvdc.getBus1().getNum(), AcEquationType.BUS_TARGET_P)
.orElseThrow()
.addTerm(p1);
hvdc.setP1(p1);
}
if (p2 != null) {
equationSystem.getEquation(hvdc.getBus2().getNum(), AcEquationType.BUS_TARGET_P)
.orElseThrow()
.addTerm(p2);
hvdc.setP2(p2);
}
}

private static void createBranchEquations(LfBranch branch, LfNetworkParameters networkParameters,
EquationSystem<AcVariableType, AcEquationType> equationSystem,
AcEquationSystemCreationParameters creationParameters) {
Expand Down Expand Up @@ -756,6 +780,10 @@ public static EquationSystem<AcVariableType, AcEquationType> create(LfNetwork ne
createBusesEquations(network, networkParameters, equationSystem, creationParameters);
createBranchesEquations(network, networkParameters, equationSystem, creationParameters);

for (LfHvdc hvdc : network.getHvdcs()) {
createHvdcAcEmulationEquations(hvdc, equationSystem);
}

EquationSystemPostProcessor.findAll().forEach(pp -> pp.onCreate(equationSystem));

network.addListener(new AcEquationSystemUpdater(equationSystem));
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
/**
* 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.openloadflow.ac.equations;

import com.powsybl.openloadflow.equations.Variable;
import com.powsybl.openloadflow.equations.VariableSet;
import com.powsybl.openloadflow.network.LfBus;
import com.powsybl.openloadflow.network.LfHvdc;

import java.util.Objects;

/**
* @author Anne Tilloy <anne.tilloy at rte-france.com>
*/
public class HvdcAcEmulationSide1ActiveFlowEquationTerm extends AbstractHvdcAcEmulationFlowEquationTerm {

public HvdcAcEmulationSide1ActiveFlowEquationTerm(LfHvdc hvdc, LfBus bus1, LfBus bus2, VariableSet<AcVariableType> variableSet) {
super(hvdc, bus1, bus2, variableSet);
}

private double p1() {
return (isController() ? 1 : getLossMultiplier()) * (p0 + k * (ph1() - ph2()));
}

private boolean isController() {
return (ph1() - ph2()) >= 0;
}

private double dp1dph1() {
return (isController() ? 1 : getLossMultiplier()) * k;
}

private double dp1dph2() {
return -dp1dph1();
}

@Override
public double eval() {
return p1();
}

@Override
public double der(Variable<AcVariableType> variable) {
Objects.requireNonNull(variable);
if (variable.equals(ph1Var)) {
return dp1dph1();
} else if (variable.equals(ph2Var)) {
return dp1dph2();
} else {
throw new IllegalStateException("Unknown variable: " + variable);
}
}

@Override
protected String getName() {
return "ac_emulation_p_1";
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
/**
* 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.openloadflow.ac.equations;

import com.powsybl.openloadflow.equations.Variable;
import com.powsybl.openloadflow.equations.VariableSet;
import com.powsybl.openloadflow.network.LfBus;
import com.powsybl.openloadflow.network.LfHvdc;

import java.util.Objects;

/**
* @author Anne Tilloy <anne.tilloy at rte-france.com>
*/
public class HvdcAcEmulationSide2ActiveFlowEquationTerm extends AbstractHvdcAcEmulationFlowEquationTerm {

public HvdcAcEmulationSide2ActiveFlowEquationTerm(LfHvdc hvdc, LfBus bus1, LfBus bus2, VariableSet<AcVariableType> variableSet) {
super(hvdc, bus1, bus2, variableSet);
}

private double p2() {
return -(isController() ? 1 : getLossMultiplier()) * (p0 + k * (ph1() - ph2()));
}

private boolean isController() {
return (ph1() - ph2()) < 0;
}

private double dp2dph1() {
return -(isController() ? 1 : getLossMultiplier()) * k;
}

private double dp2dph2() {
return -dp2dph1();
}

@Override
public double eval() {
return p2();
}

@Override
public double der(Variable<AcVariableType> variable) {
Objects.requireNonNull(variable);
if (variable.equals(ph1Var)) {
return dp2dph1();
} else if (variable.equals(ph2Var)) {
return dp2dph2();
} else {
throw new IllegalStateException("Unknown variable: " + variable);
}
}

@Override
protected String getName() {
return "ac_emulation_p_2";
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -13,4 +13,5 @@ public enum ElementType {
BUS,
BRANCH,
SHUNT_COMPENSATOR,
HVDC
}
2 changes: 2 additions & 0 deletions src/main/java/com/powsybl/openloadflow/network/LfBus.java
Original file line number Diff line number Diff line change
Expand Up @@ -128,6 +128,8 @@ default double getHighVoltageLimit() {

void addBranch(LfBranch branch);

void addHvdc(LfHvdc hvdc);

void updateState(boolean reactiveLimits, boolean writeSlackBus, boolean distributedOnConformLoad, boolean loadPowerFactorConstant);

Optional<TransformerVoltageControl> getTransformerVoltageControl();
Expand Down
42 changes: 42 additions & 0 deletions src/main/java/com/powsybl/openloadflow/network/LfHvdc.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
/**
* 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.openloadflow.network;

import com.powsybl.openloadflow.network.impl.LfVscConverterStationImpl;
import com.powsybl.openloadflow.util.Evaluable;

/**
* @author Anne Tilloy <anne.tilloy at rte-france.com>
*/
public interface LfHvdc extends LfElement {

LfBus getBus1();

LfBus getBus2();

void setP1(Evaluable p1);

Evaluable getP1();

void setP2(Evaluable p2);

Evaluable getP2();

double getDroop();

double getP0();

LfVscConverterStationImpl getConverterStation1();

LfVscConverterStationImpl getConverterStation2();

void setConverterStation1(LfVscConverterStationImpl converterStation1);

void setConverterStation2(LfVscConverterStationImpl converterStation2);

void updateState();
}
Loading