commit
b57a4a39a3
@ -327,6 +327,7 @@ if(ENABLE_ECL_INPUT)
|
||||
tests/parser/RockTableTests.cpp
|
||||
tests/parser/RunspecTests.cpp
|
||||
tests/parser/SaltTableTests.cpp
|
||||
tests/parser/ScheduleRestartTests.cpp
|
||||
tests/parser/ScheduleTests.cpp
|
||||
tests/parser/SectionTests.cpp
|
||||
tests/parser/SimpleTableTests.cpp
|
||||
|
@ -20,6 +20,9 @@
|
||||
#define RST_CONNECTION
|
||||
|
||||
#include <array>
|
||||
|
||||
#include <opm/parser/eclipse/EclipseState/Schedule/Well/Connection.hpp>
|
||||
|
||||
namespace Opm {
|
||||
namespace RestartIO {
|
||||
|
||||
@ -30,11 +33,11 @@ struct RstConnection {
|
||||
|
||||
int insert_index;
|
||||
std::array<int,3> ijk;
|
||||
int status;
|
||||
Connection::State state;
|
||||
int drain_sat_table;
|
||||
int imb_sat_table;
|
||||
int completion;
|
||||
int dir;
|
||||
Connection::Direction dir;
|
||||
int segment;
|
||||
|
||||
float tran;
|
||||
|
@ -65,6 +65,7 @@ struct RstState {
|
||||
|
||||
static RstState load(EclIO::ERst& rst_file, int report_step);
|
||||
|
||||
const RstWell& get_well(const std::string& wname) const;
|
||||
std::vector<RstWell> wells;
|
||||
std::vector<RstGroup> groups;
|
||||
RstHeader header;
|
||||
|
@ -35,6 +35,7 @@ class RstHeader;
|
||||
|
||||
struct RstWell {
|
||||
RstWell(const RstHeader& header,
|
||||
const std::string& group_arg,
|
||||
const std::string* zwel,
|
||||
const int * iwel,
|
||||
const float * swel,
|
||||
@ -44,6 +45,7 @@ struct RstWell {
|
||||
const double * xcon);
|
||||
|
||||
RstWell(const RstHeader& header,
|
||||
const std::string& group_arg,
|
||||
const std::string* zwel,
|
||||
const int * iwel,
|
||||
const float * swel,
|
||||
@ -55,6 +57,7 @@ struct RstWell {
|
||||
const std::vector<double>& rseg);
|
||||
|
||||
std::string name;
|
||||
std::string group;
|
||||
std::array<int, 2> ij;
|
||||
std::pair<int,int> k1k2;
|
||||
int wtype;
|
||||
|
@ -41,7 +41,7 @@ namespace Opm {
|
||||
enum class State {
|
||||
OPEN = 1,
|
||||
SHUT = 2,
|
||||
AUTO = 3
|
||||
AUTO = 3 // Seems like the AUTO state can not be serialized to restart files.
|
||||
};
|
||||
|
||||
static const std::string State2String( State enumValue );
|
||||
|
@ -26,15 +26,45 @@ namespace VI = ::Opm::RestartIO::Helpers::VectorItems;
|
||||
namespace Opm {
|
||||
namespace RestartIO {
|
||||
|
||||
namespace {
|
||||
|
||||
template <typename T>
|
||||
T from_int(int);
|
||||
|
||||
template <>
|
||||
Connection::State from_int(int int_state) {
|
||||
if (int_state == 1)
|
||||
return Connection::State::OPEN;
|
||||
|
||||
return Connection::State::SHUT;
|
||||
}
|
||||
|
||||
template <>
|
||||
Connection::Direction from_int(int int_dir) {
|
||||
switch (int_dir) {
|
||||
case 1:
|
||||
return Connection::Direction::X;
|
||||
case 2:
|
||||
return Connection::Direction::Y;
|
||||
case 3:
|
||||
return Connection::Direction::Z;
|
||||
throw
|
||||
std::invalid_argument("Can not convert: " + std::to_string(int_dir) + " to string");
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
RstConnection::RstConnection(const int* icon, const float* scon, const double* xcon) :
|
||||
insert_index(icon[VI::IConn::SeqIndex]),
|
||||
insert_index(icon[VI::IConn::SeqIndex] - 1),
|
||||
ijk({icon[VI::IConn::CellI] - 1, icon[VI::IConn::CellJ] - 1, icon[VI::IConn::CellK] - 1}),
|
||||
status(icon[VI::IConn::ConnStat]),
|
||||
state(from_int<Connection::State>(icon[VI::IConn::ConnStat])),
|
||||
drain_sat_table(icon[VI::IConn::Drainage]),
|
||||
imb_sat_table(icon[VI::IConn::Imbibition]),
|
||||
completion(icon[VI::IConn::ComplNum] - 1),
|
||||
dir(icon[VI::IConn::ConnDir]),
|
||||
segment(icon[VI::IConn::Segment]),
|
||||
dir(from_int<Connection::Direction>(icon[VI::IConn::ConnDir])),
|
||||
segment(icon[VI::IConn::Segment] - 1),
|
||||
tran(scon[VI::SConn::ConnTrans]),
|
||||
depth(scon[VI::SConn::Depth]),
|
||||
diameter(scon[VI::SConn::Diameter]),
|
||||
|
@ -16,6 +16,8 @@
|
||||
along with OPM. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include <algorithm>
|
||||
|
||||
#include <opm/io/eclipse/rst/header.hpp>
|
||||
#include <opm/io/eclipse/rst/connection.hpp>
|
||||
#include <opm/io/eclipse/rst/well.hpp>
|
||||
@ -55,8 +57,11 @@ RstState::RstState(const std::vector<int>& intehead,
|
||||
std::size_t icon_offset = iw * this->header.niconz * this->header.ncwmax;
|
||||
std::size_t scon_offset = iw * this->header.nsconz * this->header.ncwmax;
|
||||
std::size_t xcon_offset = iw * this->header.nxconz * this->header.ncwmax;
|
||||
int group_index = iwel[ iwel_offset + VI::IWell::Group ] - 1;
|
||||
const std::string group = this->groups[group_index].name;
|
||||
|
||||
this->wells.emplace_back(this->header,
|
||||
group,
|
||||
zwel.data() + zwel_offset,
|
||||
iwel.data() + iwel_offset,
|
||||
swel.data() + swel_offset,
|
||||
@ -98,8 +103,11 @@ RstState::RstState(const std::vector<int>& intehead,
|
||||
std::size_t icon_offset = iw * this->header.niconz * this->header.ncwmax;
|
||||
std::size_t scon_offset = iw * this->header.nsconz * this->header.ncwmax;
|
||||
std::size_t xcon_offset = iw * this->header.nxconz * this->header.ncwmax;
|
||||
int group_index = iwel[ iwel_offset + VI::IWell::Group ] - 1;
|
||||
const std::string group = this->groups[group_index].name;
|
||||
|
||||
this->wells.emplace_back(this->header,
|
||||
group,
|
||||
zwel.data() + zwel_offset,
|
||||
iwel.data() + iwel_offset,
|
||||
swel.data() + swel_offset,
|
||||
@ -130,6 +138,17 @@ void RstState::add_groups(const std::vector<std::string>& zgrp,
|
||||
}
|
||||
}
|
||||
|
||||
const RstWell& RstState::get_well(const std::string& wname) const {
|
||||
const auto well_iter = std::find_if(this->wells.begin(),
|
||||
this->wells.end(),
|
||||
[&wname] (const auto& well) {
|
||||
return well.name == wname;
|
||||
});
|
||||
if (well_iter == this->wells.end())
|
||||
throw std::out_of_range("No such well: " + wname);
|
||||
|
||||
return *well_iter;
|
||||
}
|
||||
|
||||
RstState RstState::load(EclIO::ERst& rst_file, int report_step) {
|
||||
rst_file.loadReportStepNumber(report_step);
|
||||
@ -169,3 +188,4 @@ RstState RstState::load(EclIO::ERst& rst_file, int report_step) {
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -33,6 +33,7 @@ namespace Opm {
|
||||
namespace RestartIO {
|
||||
|
||||
RstWell::RstWell(const RstHeader& header,
|
||||
const std::string& group_arg,
|
||||
const std::string* zwel,
|
||||
const int * iwel,
|
||||
const float * swel,
|
||||
@ -41,6 +42,7 @@ RstWell::RstWell(const RstHeader& header,
|
||||
const float * scon,
|
||||
const double * xcon) :
|
||||
name(trim_copy(zwel[0])),
|
||||
group(group_arg),
|
||||
ij({iwel[VI::IWell::IHead] - 1, iwel[VI::IWell::JHead] - 1}),
|
||||
k1k2(std::make_pair(iwel[VI::IWell::FirstK] - 1, iwel[VI::IWell::LastK] - 1)),
|
||||
wtype(iwel[VI::IWell::WType]),
|
||||
@ -96,6 +98,7 @@ RstWell::RstWell(const RstHeader& header,
|
||||
|
||||
|
||||
RstWell::RstWell(const RstHeader& header,
|
||||
const std::string& group_arg,
|
||||
const std::string* zwel,
|
||||
const int * iwel,
|
||||
const float * swel,
|
||||
@ -105,7 +108,7 @@ RstWell::RstWell(const RstHeader& header,
|
||||
const double * xcon,
|
||||
const std::vector<int>& iseg,
|
||||
const std::vector<double>& rseg) :
|
||||
RstWell(header, zwel, iwel, swel, xwel, icon, scon, xcon)
|
||||
RstWell(header, group_arg, zwel, iwel, swel, xwel, icon, scon, xcon)
|
||||
{
|
||||
|
||||
if (this->msw_index) {
|
||||
|
@ -40,15 +40,60 @@
|
||||
|
||||
using namespace Opm;
|
||||
|
||||
void compare_connections(const RestartIO::RstConnection& rst_conn, const Connection& sched_conn) {
|
||||
BOOST_CHECK_EQUAL(rst_conn.ijk[0], sched_conn.getI());
|
||||
BOOST_CHECK_EQUAL(rst_conn.ijk[1], sched_conn.getJ());
|
||||
BOOST_CHECK_EQUAL(rst_conn.ijk[2], sched_conn.getK());
|
||||
|
||||
BOOST_CHECK_EQUAL(rst_conn.segment, sched_conn.segment());
|
||||
BOOST_CHECK_EQUAL(rst_conn.insert_index, static_cast<int>(sched_conn.getSeqIndex()));
|
||||
BOOST_CHECK(rst_conn.state == sched_conn.state());
|
||||
BOOST_CHECK(rst_conn.dir == sched_conn.dir());
|
||||
}
|
||||
|
||||
|
||||
void compare_wells(const RestartIO::RstWell& rst_well, const Well& sched_well) {
|
||||
BOOST_CHECK_EQUAL(rst_well.name, sched_well.name());
|
||||
BOOST_CHECK_EQUAL(rst_well.group, sched_well.groupName());
|
||||
|
||||
const auto& sched_connections = sched_well.getConnections();
|
||||
BOOST_CHECK_EQUAL(sched_connections.size(), rst_well.connections.size());
|
||||
|
||||
for (std::size_t ic=0; ic < rst_well.connections.size(); ic++) {
|
||||
const auto& rst_conn = rst_well.connections[ic];
|
||||
const auto& sched_conn = sched_connections[ic];
|
||||
compare_connections(rst_conn, sched_conn);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
BOOST_AUTO_TEST_CASE(LoadRST) {
|
||||
Parser parser;
|
||||
auto deck = parser.parseFile("SPE1CASE2.DATA");
|
||||
EclIO::ERst rst_file("SPE1CASE2.X0060");
|
||||
auto rst_state = RestartIO::RstState::load(rst_file, 60);
|
||||
BOOST_REQUIRE_THROW( rst_state.get_well("NO_SUCH_WELL"), std::out_of_range);
|
||||
|
||||
EclipseState ecl_state(deck);
|
||||
Schedule sched(deck, ecl_state);
|
||||
const auto& well_names = sched.wellNames(60);
|
||||
BOOST_CHECK_EQUAL(well_names.size(), rst_state.wells.size());
|
||||
|
||||
for (const auto& wname : well_names) {
|
||||
const auto& rst_well = rst_state.get_well(wname);
|
||||
const auto& sched_well = sched.getWell(wname, 60);
|
||||
compare_wells(rst_well, sched_well);
|
||||
}
|
||||
}
|
||||
|
||||
BOOST_AUTO_TEST_CASE(LoadRestartSim) {
|
||||
Parser parser;
|
||||
auto deck = parser.parseFile("SPE1CASE2.DATA");
|
||||
auto restart_deck = parser.parseFile("SPE1CASE2_RESTART.DATA");
|
||||
EclIO::ERst rst_file("SPECASE2.X0060");
|
||||
EclIO::ERst rst_file("SPE1CASE2.X0060");
|
||||
auto rst_state = RestartIO::RstState::load(rst_file, 60);
|
||||
|
||||
EclipseState ecl_state(deck);
|
||||
Schedule sched(deck, ecl_state);
|
||||
Schedule restart_sched(deck, ecl_state, &rst_state);
|
||||
//Schedule restart_sched(deck, ecl_state, &rst_state);
|
||||
}
|
||||
|
@ -827,7 +827,7 @@ BOOST_AUTO_TEST_CASE(TestRestartIOConnection) {
|
||||
}
|
||||
}
|
||||
const auto& conn0 = connections[0];
|
||||
BOOST_CHECK_EQUAL(conn0.insert_index, 1);
|
||||
BOOST_CHECK_EQUAL(conn0.insert_index, 0);
|
||||
BOOST_CHECK_EQUAL(conn0.ijk[0], 0);
|
||||
BOOST_CHECK_EQUAL(conn0.ijk[1], 4);
|
||||
BOOST_CHECK_EQUAL(conn0.ijk[2], 1);
|
||||
|
@ -828,6 +828,7 @@ BOOST_AUTO_TEST_CASE(WELL_POD) {
|
||||
std::size_t xcon_offset = header.nxconz * header.ncwmax * iw;
|
||||
|
||||
wells.emplace_back(header,
|
||||
"GROUP",
|
||||
zwel.data() + zwel_offset,
|
||||
iwel.data() + iwel_offset,
|
||||
swel.data() + swel_offset,
|
||||
|
Loading…
Reference in New Issue
Block a user