Loading...
Searching...
No Matches
udq.hpp
/*
Copyright 2021 Equinor ASA.
This file is part of the Open Porous Media project (OPM).
OPM is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
OPM is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with OPM. If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef RST_UDQ
#define RST_UDQ
#include <opm/input/eclipse/EclipseState/Phase.hpp>
#include <opm/common/utility/CSRGraphFromCoordinates.hpp>
#include <opm/input/eclipse/Schedule/UDQ/UDQEnums.hpp>
#include <cstddef>
#include <iterator>
#include <optional>
#include <string>
#include <string_view>
#include <utility>
#include <variant>
#include <vector>
namespace Opm::RestartIO {
class RstUDQ
{
public:
class ValueRange
{
public:
class Iterator
{
public:
using iterator_category = std::forward_iterator_tag;
using value_type = std::pair<std::size_t, double>;
using difference_type = int;
using pointer = const value_type*;
using reference = const value_type&;
Iterator& operator++()
{
++this->ix_;
return *this;
}
Iterator operator++(int)
{
auto iter = *this;
++(*this);
return iter;
}
reference operator*()
{
this->setValue();
return this->deref_value_;
}
pointer operator->()
{
this->setValue();
return &this->deref_value_;
}
bool operator==(const Iterator& that) const
{
return (this->ix_ == that.ix_)
&& (this->i_ == that.i_)
&& (this->value_ == that.value_);
}
bool operator!=(const Iterator& that) const
{
return ! (*this == that);
}
friend class ValueRange;
private:
Iterator(std::size_t ix,
const int* i,
const std::variant<double, const double*>& value)
: ix_{ix}, i_{i}, value_{value}
{}
std::size_t ix_;
const int* i_;
std::variant<double, const double*> value_;
value_type deref_value_{};
void setValue();
};
Iterator begin() const
{ return this->makeIterator(this->begin_); }
Iterator end() const
{ return this->makeIterator(this->end_); }
friend class RstUDQ;
private:
ValueRange(std::size_t begin_arg,
std::size_t end_arg,
const int* i,
const double value)
: begin_{begin_arg}, end_{end_arg}, i_{i}, value_{value}
{}
ValueRange(std::size_t begin_arg,
std::size_t end_arg,
const int* i,
const double* value)
: begin_{begin_arg}, end_{end_arg}, i_{i}, value_{value}
{}
std::size_t begin_{};
std::size_t end_{};
const int* i_{};
std::variant<double, const double*> value_{};
Iterator makeIterator(const std::size_t ix) const
{
return { ix, this->i_, this->value_ };
}
};
std::string name{};
std::string unit{};
UDQVarType category{UDQVarType::NONE};
RstUDQ(const std::string& name_arg,
const std::string& unit_arg,
const std::string& define_arg,
UDQUpdate status_arg);
RstUDQ(const std::string& name_arg,
const std::string& unit_arg);
void prepareValues();
void addValue(const int entity, const int subEntity, const double value);
void commitValues();
void assignScalarValue(const double value);
void addEntityName(std::string_view wgname);
double scalarValue() const;
std::size_t numEntities() const;
ValueRange operator[](const std::size_t i) const;
const std::vector<std::string>& entityNames() const
{
return this->wgnames_;
}
const std::vector<int>& nameIndex() const;
std::string_view definingExpression() const;
UDQUpdate currentUpdateStatus() const;
bool isDefine() const
{
return this->definition_.has_value();
}
bool isScalar() const
{
return std::holds_alternative<double>(this->sa_);
}
private:
using Graph = utility::CSRGraphFromCoordinates<int, true, true>;
struct Definition
{
Definition(const std::string& expression_arg,
const UDQUpdate status_arg)
: expression { expression_arg }
, status { status_arg }
{}
std::string expression{};
UDQUpdate status{};
};
Graph entityMap_{};
std::variant<std::monostate, double, std::vector<double>> sa_;
std::vector<std::string> wgnames_{};
std::optional<int> maxEntityIdx_{};
mutable std::optional<std::vector<int>> wgNameIdx_{};
std::optional<Definition> definition_{};
bool isUDQSet() const
{
return std::holds_alternative<std::vector<double>>(this->sa_);
}
ValueRange scalarRange(const std::size_t i) const;
ValueRange udqSetRange(const std::size_t i) const;
void ensureValidNameIndex() const;
};
struct RstUDQActive
{
struct RstRecord
{
RstRecord(UDAControl c,
std::size_t i,
std::size_t numIuap,
std::size_t u1,
std::size_t u2);
UDAControl control;
std::size_t input_index;
std::size_t use_count;
std::size_t wg_offset;
std::size_t num_wg_elems;
};
RstUDQActive() = default;
RstUDQActive(int rstFileVersion,
const std::vector<int>& iuad,
const std::vector<int>& iuap,
const std::vector<int>& igph);
UDQ::RstFileUDAVersion udaVersion { UDQ::RstFileUDAVersion::vCurr };
std::vector<int> wg_index{};
std::vector<RstRecord> iuad{};
std::vector<Phase> ig_phase{};
};
} // namespace Opm::RestartIO
#endif // RST_UDQ
CSRGraphFromCoordinates.hpp
Facility for converting collection of region ID pairs into a sparse (CSR) adjacency matrix representa...