only update when control is changed

This commit is contained in:
Tor Harald Sandve 2021-08-27 07:57:16 +02:00
parent 9db6b2b946
commit c6660f0aa2
4 changed files with 71 additions and 47 deletions

View File

@ -780,7 +780,7 @@ checkGconsaleLimits(const Group& group,
deferred_logger.info(ss.str()); deferred_logger.info(ss.str());
} }
void bool
BlackoilWellModelGeneric:: BlackoilWellModelGeneric::
checkGroupHigherConstraints(const Group& group, checkGroupHigherConstraints(const Group& group,
DeferredLogger& deferred_logger, DeferredLogger& deferred_logger,
@ -797,6 +797,7 @@ checkGroupHigherConstraints(const Group& group,
? pvt_region_idx_[0] ? pvt_region_idx_[0]
: pvt_region_idx_[well_perf_data_[0][0].cell_index]; : pvt_region_idx_[well_perf_data_[0][0].cell_index];
bool changed = false;
if ( comm_.size() > 1) if ( comm_.size() > 1)
{ {
// Just like in the sequential case the pvtregion is determined // Just like in the sequential case the pvtregion is determined
@ -832,7 +833,7 @@ checkGroupHigherConstraints(const Group& group,
auto currentControl = this->groupState().injection_control(group.name(), phase); auto currentControl = this->groupState().injection_control(group.name(), phase);
if (currentControl != Group::InjectionCMode::FLD && group.injectionGroupControlAvailable(phase)) { if (currentControl != Group::InjectionCMode::FLD && group.injectionGroupControlAvailable(phase)) {
const Group& parentGroup = schedule().getGroup(group.parent(), reportStepIdx); const Group& parentGroup = schedule().getGroup(group.parent(), reportStepIdx);
const std::pair<bool, double> changed = WellGroupHelpers::checkGroupConstraintsInj( const std::pair<bool, double> changed_this = WellGroupHelpers::checkGroupConstraintsInj(
group.name(), group.name(),
group.parent(), group.parent(),
parentGroup, parentGroup,
@ -848,10 +849,11 @@ checkGroupHigherConstraints(const Group& group,
summaryState_, summaryState_,
resv_coeff_inj, resv_coeff_inj,
deferred_logger); deferred_logger);
if (changed.first) { if (changed_this.first) {
switched_groups.insert(group.name()); switched_groups.insert(group.name());
actionOnBrokenConstraints(group, Group::InjectionCMode::FLD, phase, deferred_logger); actionOnBrokenConstraints(group, Group::InjectionCMode::FLD, phase, deferred_logger);
WellGroupHelpers::updateWellRatesFromGroupTargetScale(changed.second, group, schedule(), reportStepIdx, /* isInjector */ true, this->groupState(), this->wellState()); WellGroupHelpers::updateWellRatesFromGroupTargetScale(changed_this.second, group, schedule(), reportStepIdx, /* isInjector */ true, this->groupState(), this->wellState());
changed = true;
} }
} }
} }
@ -870,7 +872,7 @@ checkGroupHigherConstraints(const Group& group,
const Group::ProductionCMode& currentControl = this->groupState().production_control(group.name()); const Group::ProductionCMode& currentControl = this->groupState().production_control(group.name());
if (currentControl != Group::ProductionCMode::FLD && group.productionGroupControlAvailable()) { if (currentControl != Group::ProductionCMode::FLD && group.productionGroupControlAvailable()) {
const Group& parentGroup = schedule().getGroup(group.parent(), reportStepIdx); const Group& parentGroup = schedule().getGroup(group.parent(), reportStepIdx);
const std::pair<bool, double> changed = WellGroupHelpers::checkGroupConstraintsProd( const std::pair<bool, double> changed_this = WellGroupHelpers::checkGroupConstraintsProd(
group.name(), group.name(),
group.parent(), group.parent(),
parentGroup, parentGroup,
@ -885,28 +887,33 @@ checkGroupHigherConstraints(const Group& group,
summaryState_, summaryState_,
resv_coeff, resv_coeff,
deferred_logger); deferred_logger);
if (changed.first) { if (changed_this.first) {
switched_groups.insert(group.name()); switched_groups.insert(group.name());
const auto exceed_action = group.productionControls(summaryState_).exceed_action; const auto exceed_action = group.productionControls(summaryState_).exceed_action;
actionOnBrokenConstraints(group, exceed_action, Group::ProductionCMode::FLD, deferred_logger); actionOnBrokenConstraints(group, exceed_action, Group::ProductionCMode::FLD, deferred_logger);
WellGroupHelpers::updateWellRatesFromGroupTargetScale(changed.second, group, schedule(), reportStepIdx, /* isInjector */ false, this->groupState(), this->wellState()); WellGroupHelpers::updateWellRatesFromGroupTargetScale(changed_this.second, group, schedule(), reportStepIdx, /* isInjector */ false, this->groupState(), this->wellState());
changed = true;
} }
} }
} }
// call recursively down the group hiearchy // call recursively down the group hiearchy
for (const std::string& groupName : group.groups()) { for (const std::string& groupName : group.groups()) {
checkGroupHigherConstraints( schedule().getGroup(groupName, reportStepIdx), deferred_logger, reportStepIdx, switched_groups); bool changed_this = checkGroupHigherConstraints( schedule().getGroup(groupName, reportStepIdx), deferred_logger, reportStepIdx, switched_groups);
} changed = changed || changed_this;
}
return changed;
} }
void bool
BlackoilWellModelGeneric:: BlackoilWellModelGeneric::
updateGroupIndividualControl(const Group& group, updateGroupIndividualControl(const Group& group,
DeferredLogger& deferred_logger, DeferredLogger& deferred_logger,
const int reportStepIdx, const int reportStepIdx,
std::set<std::string>& switched_groups) std::set<std::string>& switched_groups)
{ {
bool changed = false;
const bool skip = switched_groups.count(group.name()); const bool skip = switched_groups.count(group.name());
if (!skip && group.isInjectionGroup()) if (!skip && group.isInjectionGroup())
{ {
@ -915,33 +922,38 @@ updateGroupIndividualControl(const Group& group,
if (!group.hasInjectionControl(phase)) { if (!group.hasInjectionControl(phase)) {
continue; continue;
} }
const auto& changed = checkGroupInjectionConstraints(group, reportStepIdx, phase); const auto& changed_this = checkGroupInjectionConstraints(group, reportStepIdx, phase);
if (changed.first != Group::InjectionCMode::NONE) if (changed_this.first != Group::InjectionCMode::NONE)
{ {
switched_groups.insert(group.name()); switched_groups.insert(group.name());
actionOnBrokenConstraints(group, changed.first, phase, deferred_logger); actionOnBrokenConstraints(group, changed_this.first, phase, deferred_logger);
WellGroupHelpers::updateWellRatesFromGroupTargetScale(changed.second, group, schedule(), reportStepIdx, /* isInjector */ false, this->groupState(), this->wellState()); WellGroupHelpers::updateWellRatesFromGroupTargetScale(changed_this.second, group, schedule(), reportStepIdx, /* isInjector */ false, this->groupState(), this->wellState());
changed = true;
} }
} }
} }
if (!skip && group.isProductionGroup()) { if (!skip && group.isProductionGroup()) {
const auto& changed = checkGroupProductionConstraints(group, reportStepIdx, deferred_logger); const auto& changed_this = checkGroupProductionConstraints(group, reportStepIdx, deferred_logger);
const auto controls = group.productionControls(summaryState_); const auto controls = group.productionControls(summaryState_);
if (changed.first != Group::ProductionCMode::NONE) if (changed_this.first != Group::ProductionCMode::NONE)
{ {
switched_groups.insert(group.name()); switched_groups.insert(group.name());
actionOnBrokenConstraints(group, controls.exceed_action, changed.first, deferred_logger); actionOnBrokenConstraints(group, controls.exceed_action, changed_this.first, deferred_logger);
WellGroupHelpers::updateWellRatesFromGroupTargetScale(changed.second, group, schedule(), reportStepIdx, /* isInjector */ false, this->groupState(), this->wellState()); WellGroupHelpers::updateWellRatesFromGroupTargetScale(changed_this.second, group, schedule(), reportStepIdx, /* isInjector */ false, this->groupState(), this->wellState());
changed = true;
} }
} }
// call recursively down the group hiearchy // call recursively down the group hiearchy
for (const std::string& groupName : group.groups()) { for (const std::string& groupName : group.groups()) {
updateGroupIndividualControl( schedule().getGroup(groupName, reportStepIdx), deferred_logger, reportStepIdx, switched_groups); bool changed_this = updateGroupIndividualControl( schedule().getGroup(groupName, reportStepIdx), deferred_logger, reportStepIdx, switched_groups);
changed = changed || changed_this;
} }
return changed;
} }
void bool
BlackoilWellModelGeneric:: BlackoilWellModelGeneric::
updateGroupIndividualControls(DeferredLogger& deferred_logger, updateGroupIndividualControls(DeferredLogger& deferred_logger,
std::set<std::string>& switched_groups, std::set<std::string>& switched_groups,
@ -952,21 +964,21 @@ updateGroupIndividualControls(DeferredLogger& deferred_logger,
// don't switch group control when iterationIdx > nupcol // don't switch group control when iterationIdx > nupcol
// to avoid oscilations between group controls // to avoid oscilations between group controls
if (iterationIdx > nupcol) if (iterationIdx > nupcol)
return; return false;
const Group& fieldGroup = schedule().getGroup("FIELD", reportStepIdx); const Group& fieldGroup = schedule().getGroup("FIELD", reportStepIdx);
updateGroupIndividualControl(fieldGroup, deferred_logger, return updateGroupIndividualControl(fieldGroup, deferred_logger,
reportStepIdx, switched_groups); reportStepIdx, switched_groups);
} }
void bool
BlackoilWellModelGeneric:: BlackoilWellModelGeneric::
updateGroupHigherControls(DeferredLogger& deferred_logger, updateGroupHigherControls(DeferredLogger& deferred_logger,
const int reportStepIdx, const int reportStepIdx,
std::set<std::string>& switched_groups) std::set<std::string>& switched_groups)
{ {
const Group& fieldGroup = schedule().getGroup("FIELD", reportStepIdx); const Group& fieldGroup = schedule().getGroup("FIELD", reportStepIdx);
checkGroupHigherConstraints(fieldGroup, deferred_logger, reportStepIdx, switched_groups); return checkGroupHigherConstraints(fieldGroup, deferred_logger, reportStepIdx, switched_groups);
} }
void void

View File

@ -300,22 +300,22 @@ protected:
const int reportStepIdx, const int reportStepIdx,
DeferredLogger& deferred_logger); DeferredLogger& deferred_logger);
void checkGroupHigherConstraints(const Group& group, bool checkGroupHigherConstraints(const Group& group,
DeferredLogger& deferred_logger, DeferredLogger& deferred_logger,
const int reportStepIdx, const int reportStepIdx,
std::set<std::string>& switched_groups); std::set<std::string>& switched_groups);
void updateGroupIndividualControl(const Group& group, bool updateGroupIndividualControl(const Group& group,
DeferredLogger& deferred_logger, DeferredLogger& deferred_logger,
const int reportStepIdx, const int reportStepIdx,
std::set<std::string>& switched_groups); std::set<std::string>& switched_groups);
void updateGroupIndividualControls(DeferredLogger& deferred_logger, bool updateGroupIndividualControls(DeferredLogger& deferred_logger,
std::set<std::string>& switched_groups, std::set<std::string>& switched_groups,
const int reportStepIdx, const int reportStepIdx,
const int iterationIdx); const int iterationIdx);
void updateGroupHigherControls(DeferredLogger& deferred_logger, bool updateGroupHigherControls(DeferredLogger& deferred_logger,
const int reportStepIdx, const int reportStepIdx,
std::set<std::string>& switched_groups); std::set<std::string>& switched_groups);

View File

@ -1272,8 +1272,8 @@ namespace Opm {
const int episodeIdx = ebosSimulator_.episodeIndex(); const int episodeIdx = ebosSimulator_.episodeIndex();
const int iterationIdx = ebosSimulator_.model().newtonMethod().numIterations(); const int iterationIdx = ebosSimulator_.model().newtonMethod().numIterations();
const auto& comm = ebosSimulator_.vanguard().grid().comm();
updateAndCommunicate(episodeIdx, iterationIdx, deferred_logger); updateAndCommunicateGroupData(episodeIdx, iterationIdx);
updateNetworkPressures(episodeIdx); updateNetworkPressures(episodeIdx);
@ -1282,38 +1282,50 @@ namespace Opm {
if (checkGroupControls) { if (checkGroupControls) {
// Check group individual constraints. // Check group individual constraints.
updateGroupIndividualControls(deferred_logger, switched_groups, bool changed_individual = updateGroupIndividualControls(deferred_logger, switched_groups,
episodeIdx, iterationIdx); episodeIdx, iterationIdx);
updateAndCommunicate(episodeIdx, iterationIdx, deferred_logger); if (changed_individual)
updateAndCommunicate(episodeIdx, iterationIdx, deferred_logger);
// Check group's constraints from higher levels. // Check group's constraints from higher levels.
updateGroupHigherControls(deferred_logger, bool changed_higher = updateGroupHigherControls(deferred_logger,
episodeIdx, episodeIdx,
switched_groups); switched_groups);
updateAndCommunicate(episodeIdx, iterationIdx, deferred_logger); if (changed_higher)
updateAndCommunicate(episodeIdx, iterationIdx, deferred_logger);
// Check wells' group constraints and communicate. // Check wells' group constraints and communicate.
bool changed_well_group = false;
for (const auto& well : well_container_) { for (const auto& well : well_container_) {
const auto mode = WellInterface<TypeTag>::IndividualOrGroup::Group; const auto mode = WellInterface<TypeTag>::IndividualOrGroup::Group;
const bool changed = well->updateWellControl(ebosSimulator_, mode, this->wellState(), this->groupState(), deferred_logger); const bool changed_well = well->updateWellControl(ebosSimulator_, mode, this->wellState(), this->groupState(), deferred_logger);
if (changed) { if (changed_well) {
switched_wells.insert(well->name()); switched_wells.insert(well->name());
changed_well_group = changed_well || changed_well_group;
} }
} }
updateAndCommunicate(episodeIdx, iterationIdx, deferred_logger); changed_well_group = comm.sum(changed_well_group);
if (changed_well_group)
updateAndCommunicate(episodeIdx, iterationIdx, deferred_logger);
} }
// Check individual well constraints and communicate. // Check individual well constraints and communicate.
bool changed_well_individual = false;
for (const auto& well : well_container_) { for (const auto& well : well_container_) {
if (switched_wells.count(well->name())) { if (switched_wells.count(well->name())) {
continue; continue;
} }
const auto mode = WellInterface<TypeTag>::IndividualOrGroup::Individual; const auto mode = WellInterface<TypeTag>::IndividualOrGroup::Individual;
well->updateWellControl(ebosSimulator_, mode, this->wellState(), this->groupState(), deferred_logger); const bool changed_well = well->updateWellControl(ebosSimulator_, mode, this->wellState(), this->groupState(), deferred_logger);
if (changed_well) {
changed_well_individual = changed_well || changed_well_individual;
}
} }
updateAndCommunicate(episodeIdx, iterationIdx, deferred_logger); changed_well_individual = comm.sum(changed_well_individual);
if (changed_well_individual)
updateAndCommunicate(episodeIdx, iterationIdx, deferred_logger);
} }
@ -1329,6 +1341,7 @@ namespace Opm {
for (const auto& well : well_container_) { for (const auto& well : well_container_) {
well->updateWellStateWithTarget(ebosSimulator_, this->groupState(), this->wellState(), deferred_logger); well->updateWellStateWithTarget(ebosSimulator_, this->groupState(), this->wellState(), deferred_logger);
} }
updateAndCommunicateGroupData(reportStepIdx, iterationIdx);
} }
template<typename TypeTag> template<typename TypeTag>

View File

@ -608,12 +608,11 @@ namespace Opm
const auto& summaryState = ebos_simulator.vanguard().summaryState(); const auto& summaryState = ebos_simulator.vanguard().summaryState();
const auto& schedule = ebos_simulator.vanguard().schedule(); const auto& schedule = ebos_simulator.vanguard().schedule();
if (this->wellIsStopped() || !this->isOperable()) { if (this->wellIsStopped()) {
for (int p = 0; p<np; ++p) { for (int p = 0; p<np; ++p) {
ws.surface_rates[p] = 0.0; ws.surface_rates[p] = 0;
ws.well_potentials[p] = 0.0;
} }
ws.thp = 0.0; ws.thp = 0;
return; return;
} }