Add class UDQSet() to hold UDQ values

This commit is contained in:
Joakim Hove 2019-02-14 10:36:21 +01:00
parent 4c0c394b77
commit a1b8303ac3
4 changed files with 542 additions and 0 deletions

View File

@ -125,6 +125,7 @@ if(ENABLE_ECL_INPUT)
src/opm/parser/eclipse/EclipseState/Tables/TableSchema.cpp
src/opm/parser/eclipse/EclipseState/Tables/Tables.cpp
src/opm/parser/eclipse/EclipseState/UDQParams.cpp
src/opm/parser/eclipse/EclipseState/Schedule/UDQSet.cpp
src/opm/parser/eclipse/EclipseState/Schedule/UDQ.cpp
src/opm/parser/eclipse/EclipseState/Schedule/UDQContext.cpp
src/opm/parser/eclipse/EclipseState/Schedule/UDQExpression.cpp
@ -514,6 +515,7 @@ if(ENABLE_ECL_INPUT)
opm/parser/eclipse/EclipseState/Schedule/UDQ.hpp
opm/parser/eclipse/EclipseState/UDQParams.hpp
opm/parser/eclipse/EclipseState/Schedule/UDQ.hpp
opm/parser/eclipse/EclipseState/Schedule/UDQSet.hpp
opm/parser/eclipse/EclipseState/Schedule/UDQExpression.hpp
opm/parser/eclipse/Deck/DeckItem.hpp
opm/parser/eclipse/Deck/Deck.hpp

View File

@ -0,0 +1,115 @@
/*
Copyright 2019 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 UDQSET_HPP
#define UDQSET_HPP
#include <stdexcept>
#include <vector>
namespace Opm {
class UDQScalar {
public:
UDQScalar() = default;
UDQScalar(double value);
void operator+=(const UDQScalar& rhs);
void operator+=(double rhs);
void operator*=(const UDQScalar& rhs);
void operator*=(double rhs);
void operator/=(const UDQScalar& rhs);
void operator/=(double rhs);
void operator-=(const UDQScalar& rhs);
void operator-=(double rhs);
operator bool() const;
void assign(double value);
bool defined() const;
double value() const;
public:
double m_value;
bool m_defined = false;
};
class UDQSet {
public:
explicit UDQSet(std::size_t size);
void assign(double value);
void assign(std::size_t index, double value);
std::size_t size() const;
void operator+=(const UDQSet& rhs);
void operator+=(double rhs);
void operator-=(const UDQSet& rhs);
void operator-=(double rhs);
void operator*=(const UDQSet& rhs);
void operator*=(double rhs);
void operator/=(const UDQSet& rhs);
void operator/=(double rhs);
const UDQScalar& operator[](std::size_t index) const;
std::vector<UDQScalar>::const_iterator begin() const;
std::vector<UDQScalar>::const_iterator end() const;
std::vector<double> defined_values() const;
std::size_t defined_size() const;
private:
std::vector<UDQScalar> values;
};
UDQScalar operator+(const UDQScalar&lhs, const UDQScalar& rhs);
UDQScalar operator+(const UDQScalar&lhs, double rhs);
UDQScalar operator+(double lhs, const UDQScalar& rhs);
UDQScalar operator-(const UDQScalar&lhs, const UDQScalar& rhs);
UDQScalar operator-(const UDQScalar&lhs, double rhs);
UDQScalar operator-(double lhs, const UDQScalar& rhs);
UDQScalar operator*(const UDQScalar&lhs, const UDQScalar& rhs);
UDQScalar operator*(const UDQScalar&lhs, double rhs);
UDQScalar operator*(double lhs, const UDQScalar& rhs);
UDQScalar operator/(const UDQScalar&lhs, const UDQScalar& rhs);
UDQScalar operator/(const UDQScalar&lhs, double rhs);
UDQScalar operator/(double lhs, const UDQScalar& rhs);
UDQSet operator+(const UDQSet&lhs, const UDQSet& rhs);
UDQSet operator+(const UDQSet&lhs, double rhs);
UDQSet operator+(double lhs, const UDQSet& rhs);
UDQSet operator-(const UDQSet&lhs, const UDQSet& rhs);
UDQSet operator-(const UDQSet&lhs, double rhs);
UDQSet operator-(double lhs, const UDQSet& rhs);
UDQSet operator*(const UDQSet&lhs, const UDQSet& rhs);
UDQSet operator*(const UDQSet&lhs, double rhs);
UDQSet operator*(double lhs, const UDQSet& rhs);
UDQSet operator/(const UDQSet&lhs, const UDQSet& rhs);
UDQSet operator/(const UDQSet&lhs, double rhs);
UDQSet operator/(double lhs, const UDQSet&rhs);
}
#endif

View File

@ -0,0 +1,356 @@
/*
Copyright 2019 Statoil 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/>.
*/
#include <opm/parser/eclipse/EclipseState/Schedule/UDQSet.hpp>
namespace Opm {
UDQScalar::UDQScalar(double value) :
m_value(value),
m_defined(true)
{}
bool UDQScalar::defined() const {
return this->m_defined;
}
double UDQScalar::value() const {
if (!this->m_defined)
throw std::invalid_argument("Value not defined");
return this->m_value;
}
void UDQScalar::assign(double value) {
this->m_value = value;
this->m_defined = true;
}
void UDQScalar::operator-=(const UDQScalar& rhs) {
if (this->m_defined && rhs.m_defined)
this->m_value -= rhs.m_value;
else
this->m_defined = false;
}
void UDQScalar::operator-=(double rhs) {
if (this->m_defined)
this->m_value -= rhs;
}
void UDQScalar::operator/=(const UDQScalar& rhs) {
if (this->m_defined && rhs.m_defined)
this->m_value /= rhs.m_value;
else
this->m_defined = false;
}
void UDQScalar::operator/=(double rhs) {
if (this->m_defined)
this->m_value /= rhs;
}
void UDQScalar::operator+=(const UDQScalar& rhs) {
if (this->m_defined && rhs.m_defined)
this->m_value += rhs.m_value;
else
this->m_defined = false;
}
void UDQScalar::operator+=(double rhs) {
if (this->m_defined)
this->m_value += rhs;
}
void UDQScalar::operator*=(const UDQScalar& rhs) {
if (this->m_defined && rhs.m_defined)
this->m_value *= rhs.m_value;
else
this->m_defined = false;
}
void UDQScalar::operator*=(double rhs) {
if (this->m_defined)
this->m_value *= rhs;
}
UDQScalar::operator bool() const {
return this->m_defined;
}
UDQSet::UDQSet(std::size_t size) {
this->values.resize(size);
}
std::size_t UDQSet::size() const {
return this->values.size();
}
void UDQSet::assign(double value) {
for (auto& v : this->values)
v.assign(value);
}
void UDQSet::assign(std::size_t index, double value) {
auto& scalar = this->values[index];
scalar.assign(value);
}
void UDQSet::operator+=(const UDQSet& rhs) {
if (this->size() != rhs.size())
throw std::invalid_argument("Incompatible size");
for (std::size_t index = 0; index < this->size(); index++)
this->values[index] += rhs[index];
}
void UDQSet::operator+=(double rhs) {
for (std::size_t index = 0; index < this->size(); index++)
this->values[index] += rhs;
}
void UDQSet::operator-=(double rhs) {
*(this) += (-rhs);
}
void UDQSet::operator-=(const UDQSet& rhs) {
*(this) += (rhs * -1.0);
}
void UDQSet::operator*=(const UDQSet& rhs) {
if (this->size() != rhs.size())
throw std::invalid_argument("Incompatible size");
for (std::size_t index = 0; index < this->size(); index++)
this->values[index] *= rhs[index];
}
void UDQSet::operator*=(double rhs) {
for (std::size_t index = 0; index < this->size(); index++)
this->values[index] *= rhs;
}
void UDQSet::operator/=(const UDQSet& rhs) {
if (this->size() != rhs.size())
throw std::invalid_argument("Incompatible size");
for (std::size_t index = 0; index < this->size(); index++)
this->values[index] /= rhs[index];
}
void UDQSet::operator/=(double rhs) {
for (std::size_t index = 0; index < this->size(); index++)
this->values[index] /= rhs;
}
std::vector<double> UDQSet::defined_values() const {
std::vector<double> dv;
for (const auto& v : this->values) {
if (v)
dv.push_back(v.value());
}
return dv;
}
std::size_t UDQSet::defined_size() const {
std::size_t dsize = 0;
for (const auto& v : this->values) {
if (v)
dsize += 1;
}
return dsize;
}
const UDQScalar& UDQSet::operator[](std::size_t index) const {
if (index >= this->size())
throw std::invalid_argument("Index out of range");
return this->values[index];
}
std::vector<UDQScalar>::const_iterator UDQSet::begin() const {
return this->values.begin();
}
std::vector<UDQScalar>::const_iterator UDQSet::end() const {
return this->values.end();
}
/*****************************************************************/
UDQScalar operator+(const UDQScalar&lhs, const UDQScalar& rhs) {
UDQScalar sum = lhs;
sum += rhs;
return sum;
}
UDQScalar operator+(const UDQScalar&lhs, double rhs) {
UDQScalar sum = lhs;
sum += rhs;
return sum;
}
UDQScalar operator+(double lhs, const UDQScalar& rhs) {
UDQScalar sum = rhs;
sum += lhs;
return sum;
}
UDQScalar operator-(const UDQScalar&lhs, const UDQScalar& rhs) {
UDQScalar sum = lhs;
sum -= rhs;
return sum;
}
UDQScalar operator-(const UDQScalar&lhs, double rhs) {
UDQScalar sum = lhs;
sum -= rhs;
return sum;
}
UDQScalar operator-(double lhs, const UDQScalar& rhs) {
UDQScalar sum = rhs;
sum -= lhs;
return sum;
}
UDQScalar operator*(const UDQScalar&lhs, const UDQScalar& rhs) {
UDQScalar sum = lhs;
sum *= rhs;
return sum;
}
UDQScalar operator*(const UDQScalar&lhs, double rhs) {
UDQScalar sum = lhs;
sum *= rhs;
return sum;
}
UDQScalar operator*(double lhs, const UDQScalar& rhs) {
UDQScalar sum = rhs;
sum *= lhs;
return sum;
}
UDQScalar operator/(const UDQScalar&lhs, const UDQScalar& rhs) {
UDQScalar sum = lhs;
sum /= rhs;
return sum;
}
UDQScalar operator/(const UDQScalar&lhs, double rhs) {
UDQScalar sum = lhs;
sum /= rhs;
return sum;
}
UDQScalar operator/(double lhs, const UDQScalar& rhs) {
UDQScalar result = rhs;
if (result)
result.assign(lhs / result.value());
return result;
}
UDQSet operator+(const UDQSet&lhs, const UDQSet& rhs) {
UDQSet sum = lhs;
sum += rhs;
return sum;
}
UDQSet operator+(const UDQSet&lhs, double rhs) {
UDQSet sum = lhs;
sum += rhs;
return sum;
}
UDQSet operator+(double lhs, const UDQSet& rhs) {
UDQSet sum = rhs;
sum += lhs;
return sum;
}
UDQSet operator-(const UDQSet&lhs, const UDQSet& rhs) {
UDQSet sum = lhs;
sum -= rhs;
return sum;
}
UDQSet operator-(const UDQSet&lhs, double rhs) {
UDQSet sum = lhs;
sum -= rhs;
return sum;
}
UDQSet operator-(double lhs, const UDQSet& rhs) {
UDQSet sum = rhs;
sum -= lhs;
return sum;
}
UDQSet operator*(const UDQSet&lhs, const UDQSet& rhs) {
UDQSet sum = lhs;
sum *= rhs;
return sum;
}
UDQSet operator*(const UDQSet&lhs, double rhs) {
UDQSet sum = lhs;
sum *= rhs;
return sum;
}
UDQSet operator*(double lhs, const UDQSet& rhs) {
UDQSet sum = rhs;
sum *= lhs;
return sum;
}
UDQSet operator/(const UDQSet&lhs, const UDQSet& rhs) {
UDQSet sum = lhs;
sum /= rhs;
return sum;
}
UDQSet operator/(const UDQSet&lhs, double rhs) {
UDQSet sum = lhs;
sum /= rhs;
return sum;
}
UDQSet operator/(double lhs, const UDQSet&rhs) {
UDQSet result = rhs;
for (std::size_t index = 0; index < rhs.size(); index++) {
const auto& elm = rhs[index];
if (elm)
result.assign(index, lhs / elm.value());
}
return result;
}
}

View File

@ -25,6 +25,7 @@
#include <opm/parser/eclipse/Parser/Parser.hpp>
#include <opm/parser/eclipse/EclipseState/Schedule/Schedule.hpp>
#include <opm/parser/eclipse/EclipseState/Schedule/UDQ.hpp>
#include <opm/parser/eclipse/EclipseState/Schedule/UDQSet.hpp>
#include <opm/parser/eclipse/EclipseState/Schedule/UDQExpression.hpp>
#include <opm/parser/eclipse/EclipseState/Schedule/UDQContext.hpp>
#include <opm/parser/eclipse/EclipseState/Schedule/SummaryState.hpp>
@ -201,3 +202,71 @@ BOOST_AUTO_TEST_CASE(UDQ_CONTEXT) {
st.add("SUMMARY:KEY", 1.0);
BOOST_CHECK_EQUAL(ctx.get("SUMMARY:KEY") , 1.0 );
}
BOOST_AUTO_TEST_CASE(UDQ_SET) {
UDQSet s1(5);
for (const auto& v : s1) {
BOOST_CHECK_EQUAL(false, v.defined());
BOOST_REQUIRE_THROW( v.value(), std::invalid_argument);
}
BOOST_CHECK_EQUAL(s1.defined_size(), 0);
s1.assign(1);
for (const auto& v : s1) {
BOOST_CHECK_EQUAL(true, v.defined());
BOOST_CHECK_EQUAL( v.value(), 1.0);
}
BOOST_CHECK_EQUAL(s1.defined_size(), s1.size());
s1.assign(0,0.0);
{
UDQSet s2(6);
BOOST_REQUIRE_THROW(s1 + s2, std::invalid_argument);
}
{
UDQSet s2(5);
s2.assign(0, 25);
auto s3 = s1 + s2;
auto v0 = s3[0];
BOOST_CHECK_EQUAL(v0.value(), 25);
auto v4 = s3[4];
BOOST_CHECK( !v4.defined() );
}
s1.assign(0,1.0);
{
UDQSet s2 = s1 + 1.0;
UDQSet s3 = s2 * 2.0;
UDQSet s4 = s1 - 1.0;
for (const auto& v : s2) {
BOOST_CHECK_EQUAL(true, v.defined());
BOOST_CHECK_EQUAL( v.value(), 2.0);
}
for (const auto& v : s3) {
BOOST_CHECK_EQUAL(true, v.defined());
BOOST_CHECK_EQUAL( v.value(), 4.0);
}
for (const auto& v : s4) {
BOOST_CHECK_EQUAL(true, v.defined());
BOOST_CHECK_EQUAL( v.value(), 0);
}
}
}
BOOST_AUTO_TEST_CASE(UDQ_SET_DIV) {
UDQSet s(5);
s.assign(0,1);
s.assign(2,2);
s.assign(4,5);
auto result = 10 / s;
BOOST_CHECK_EQUAL( result.defined_size(), 3);
BOOST_CHECK_EQUAL( result[0].value(), 10);
BOOST_CHECK_EQUAL( result[2].value(), 5);
BOOST_CHECK_EQUAL( result[4].value(), 2);
}