CostResultMapSerializer.java
/*
* Copyright (c) 2021, 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.data.raoresult.io.json.serializers;
import com.powsybl.openrao.data.crac.api.Crac;
import com.powsybl.openrao.data.crac.api.Instant;
import com.powsybl.openrao.data.raoresult.api.RaoResult;
import com.fasterxml.jackson.core.JsonGenerator;
import static com.powsybl.openrao.commons.MeasurementRounding.roundValueBasedOnMargin;
import java.io.IOException;
import java.util.Objects;
import static com.powsybl.openrao.data.raoresult.io.json.RaoResultJsonConstants.*;
/**
* @author Baptiste Seguinot {@literal <baptiste.seguinot at rte-france.com>}
*/
final class CostResultMapSerializer {
private CostResultMapSerializer() {
}
static void serialize(RaoResult raoResult, Crac crac, JsonGenerator jsonGenerator) throws IOException {
jsonGenerator.writeObjectFieldStart(COST_RESULTS);
serializeCostResultForOptimizationState(null, raoResult, jsonGenerator);
for (Instant instant : crac.getSortedInstants()) {
serializeCostResultForOptimizationState(instant, raoResult, jsonGenerator);
}
jsonGenerator.writeEndObject();
}
private static void serializeCostResultForOptimizationState(Instant optInstant, RaoResult raoResult, JsonGenerator jsonGenerator) throws IOException {
double functionalCost = raoResult.getFunctionalCost(optInstant);
boolean isFunctionalCostNaN = Double.isNaN(functionalCost);
double virtualCost = raoResult.getVirtualCost(optInstant);
boolean isVirtualCostNaN = Double.isNaN(virtualCost);
if (isFunctionalCostNaN && isVirtualCostNaN) {
return;
}
double margin;
if (isFunctionalCostNaN) {
margin = -virtualCost;
} else if (isVirtualCostNaN) {
margin = -functionalCost;
} else {
margin = -functionalCost - virtualCost;
}
jsonGenerator.writeObjectFieldStart(serializeInstantId(optInstant));
if (!isFunctionalCostNaN) {
jsonGenerator.writeNumberField(FUNCTIONAL_COST, roundValueBasedOnMargin(functionalCost, margin, 2));
}
if (containAnyVirtualCostForOptimizationState(raoResult, optInstant)) {
jsonGenerator.writeObjectFieldStart(VIRTUAL_COSTS);
for (String virtualCostName : raoResult.getVirtualCostNames()) {
double virtualCostForAGivenName = raoResult.getVirtualCost(optInstant, virtualCostName);
if (!Double.isNaN(virtualCostForAGivenName)) {
jsonGenerator.writeNumberField(virtualCostName, roundValueBasedOnMargin(virtualCostForAGivenName, margin, 2));
}
}
jsonGenerator.writeEndObject();
}
jsonGenerator.writeEndObject();
}
private static boolean containAnyVirtualCostForOptimizationState(RaoResult raoResult, Instant optInstant) {
return !Objects.isNull(raoResult.getVirtualCostNames()) &&
raoResult.getVirtualCostNames().stream().anyMatch(costName -> !Double.isNaN(raoResult.getVirtualCost(optInstant, costName)));
}
}