Updating variable name in SimulatorFullyImplicitBlackoilEbos.hpp and adding tests

This commit is contained in:
Vegard Kippe 2023-06-29 15:20:38 +02:00
parent 65f73f5462
commit a80f44a3be
5 changed files with 282 additions and 7 deletions

View File

@ -252,6 +252,7 @@ list (APPEND TEST_SOURCE_FILES
tests/test_RestartSerialization.cpp
tests/test_stoppedwells.cpp
tests/test_timer.cpp
tests/test_tuning_XXXMBE.cpp
tests/test_vfpproperties.cpp
tests/test_wellmodel.cpp
tests/test_wellprodindexcalculator.cpp

View File

@ -21,7 +21,7 @@ set(BASE_RESULT_PATH ${PROJECT_BINARY_DIR}/tests/results)
# Details:
# - This test class simply runs a simulation.
function(add_test_runSimulator)
set(oneValueArgs CASENAME FILENAME SIMULATOR DIR DIR_PREFIX PROCS)
set(oneValueArgs CASENAME FILENAME SIMULATOR DIR DIR_PREFIX PROCS CONFIGURATION)
set(multiValueArgs TEST_ARGS)
cmake_parse_arguments(PARAM "$" "${oneValueArgs}" "${multiValueArgs}" ${ARGN} )
if(NOT PARAM_DIR)
@ -37,9 +37,38 @@ function(add_test_runSimulator)
-f ${PARAM_FILENAME}
-n ${PARAM_PROCS}
TEST_ARGS ${TEST_ARGS}
CONFIGURATION extra)
CONFIGURATION ${PARAM_CONFIGURATION})
endfunction()
###########################################################################
# TEST: runSimulatorAlways - Run as default test (not only with the EXTRA conf)
###########################################################################
# Input:
# - casename: basename (no extension)
#
# Details:
# - This test class simply runs a simulation
function(add_test_runSimulatorAlways)
set(oneValueArgs CASENAME FILENAME SIMULATOR DIR DIR_PREFIX PROCS)
set(multiValueArgs TEST_ARGS)
cmake_parse_arguments(PARAM "$" "${oneValueArgs}" "${multiValueArgs}" ${ARGN} )
if(NOT PARAM_DIR)
set(PARAM_DIR ${PARAM_CASENAME})
endif()
set(RESULT_PATH ${BASE_RESULT_PATH}${PARAM_DIR_PREFIX}/${PARAM_SIMULATOR}+${PARAM_CASENAME})
set(TEST_ARGS ${PARAM_TEST_ARGS})
opm_add_test(runSimulator/${PARAM_CASENAME} NO_COMPILE
EXE_NAME ${PARAM_SIMULATOR}
DRIVER_ARGS -i ${OPM_TESTS_ROOT}/${PARAM_DIR}
-r ${RESULT_PATH}
-b ${PROJECT_BINARY_DIR}/bin
-f ${PARAM_FILENAME}
-n ${PARAM_PROCS}
TEST_ARGS ${TEST_ARGS})
endfunction()
###########################################################################
# TEST: compareECLFiles
###########################################################################
@ -277,13 +306,52 @@ opm_set_test_driver(${PROJECT_SOURCE_DIR}/tests/run-test.sh "")
add_test_runSimulator(CASENAME norne
FILENAME NORNE_ATW2013
SIMULATOR flow
PROCS 1)
PROCS 1
CONFIGURATION extra)
add_test_runSimulator(CASENAME norne_parallel
FILENAME NORNE_ATW2013
SIMULATOR flow
DIR norne
PROCS 4)
PROCS 4
CONFIGURATION extra)
# Tests that are run based on simulator results, but not necessarily direct comparison to reference results
add_test_runSimulator(CASENAME run_tuning_xxxmbe
FILENAME 01_TUNING_XXXMBE
SIMULATOR flow
DIR tuning
PROCS 1
TEST_ARGS --output-extra-convergence-info=iterations --enable-tuning=true)
add_test_runSimulator(CASENAME run_notuning_xxxmbe
FILENAME 01_TUNING_XXXMBE
SIMULATOR flow
DIR tuning
PROCS 1
TEST_ARGS --output-extra-convergence-info=iterations --enable-tuning=false)
set_tests_properties(tuning_XXXMBE PROPERTIES DEPENDS "runSimulator/run_tuning_xxxmbe")
set_tests_properties(tuning_XXXMBE PROPERTIES WORKING_DIRECTORY "${BASE_RESULT_PATH}/flow+run_tuning_xxxmbe")
# Workaround to run same test on different simulation results
get_target_property(notuning_XXXMBE_cmd test_tuning_XXXMBE LOCATION)
if(MPI_FOUND)
set(notuning_XXXMBE_cmd ${MPIEXEC} ${MPIEXEC_NUMPROC_FLAG} 1 ${notuning_XXXMBE_cmd})
endif()
add_test(
NAME notuning_XXXMBE
COMMAND ${notuning_XXXMBE_cmd}
)
set_tests_properties(notuning_XXXMBE PROPERTIES DEPENDS "runSimulator/run_notuning_xxxmbe")
set_tests_properties(notuning_XXXMBE PROPERTIES WORKING_DIRECTORY "${BASE_RESULT_PATH}/flow+run_notuning_xxxmbe")
set_tests_properties(notuning_XXXMBE PROPERTIES WILL_FAIL TRUE)
include (${CMAKE_CURRENT_SOURCE_DIR}/regressionTests.cmake)
include (${CMAKE_CURRENT_SOURCE_DIR}/restartTests.cmake)

View File

@ -403,7 +403,7 @@ public:
adaptiveTimeStepping_->updateTUNING(max_next_tstep, tuning);
// \Note: Assumes TUNING is only used with adaptive time-stepping
// \Note: Need to update both solver (model) and simulator since solver is re-created each report step.
solver->model().updateTUNING(tuning);
solver_->model().updateTUNING(tuning);
this->updateTUNING(tuning);
}
}

View File

@ -33,8 +33,8 @@ TEST_ARGS="$@"
mkdir -p ${RESULT_PATH}
if (( ${MPI_PROCS} > 1))
then
mpirun -np ${MPI_PROCS} ${BINPATH}/${EXE_NAME} ${TEST_ARGS} --output-dir=${RESULT_PATH}
mpirun -np ${MPI_PROCS} ${BINPATH}/${EXE_NAME} ${TEST_ARGS} --output-dir=${RESULT_PATH} "${INPUT_DATA_PATH}/${FILENAME}.DATA"
else
${BINPATH}/${EXE_NAME} ${TEST_ARGS} --output-dir=${RESULT_PATH}
${BINPATH}/${EXE_NAME} ${TEST_ARGS} --output-dir=${RESULT_PATH} "${INPUT_DATA_PATH}/${FILENAME}.DATA"
fi
test $? -eq 0 || exit 1

View File

@ -0,0 +1,206 @@
#include <iostream>
#include <fstream>
#include <sstream>
#include <string>
#include <vector>
#include <map>
#include <limits>
#include <algorithm>
#define BOOST_TEST_MODULE TestTuningXXXMBE
#include <boost/test/unit_test.hpp>
struct Column : public std::vector<std::string> {
Column(const std::string& name_, const int size = 0, const int num_rows_estimate = 1000) :
std::vector<std::string>(size), name(name_)
{
this->reserve(num_rows_estimate);
}
// Return vector of double values, invalid elements set to NaN
std::vector<double> dvalues() const {
std::vector<double> vec;
vec.reserve(this->size());
const auto& conv_func = [](const std::string& strval) {
double dval;
try {
dval = std::stod(strval);
} catch (std::invalid_argument& exc) {
dval = std::numeric_limits<double>::quiet_NaN();
}
return dval;
};
std::transform(this->cbegin(), this->cend(), std::back_inserter(vec), conv_func);
return vec;
}
// Return vector of double values values, invalid elements set to std::numeric_limits<int>::min()
std::vector<int> ivalues() const {
std::vector<int> vec;
vec.reserve(this->size());
const auto& conv_func = [](const std::string& strval) {
int ival;
try {
ival = static_cast<int>(std::stod(strval));
} catch (std::invalid_argument& exc) {
ival = std::numeric_limits<int>::min();
}
return ival;
};
std::transform(this->cbegin(), this->cend(), std::back_inserter(vec), conv_func);
return vec;
}
std::string name;
};
struct ColumnData {
ColumnData(const std::string& file_name, const int num_columns_estimate=20) {
raw_columns.reserve(num_columns_estimate);
load_file(file_name);
}
void load_file(const std::string& file_name) {
// Open file and read first line with column names
std::ifstream ifs(file_name);
std::string line, colname;
std::getline(ifs, line);
std::istringstream iss(line);
while (iss >> colname) {
column_names.push_back(colname);
raw_columns.emplace_back(colname);
columns[colname] = &(raw_columns.back());
}
const int num_columns = column_names.size();
// Read remaining lines into std::string vectors
int lineno = 1;
while (std::getline(ifs, line)) {
iss.str(line); iss.clear();
int i=0;
while (iss >> colname && i < num_columns) {
raw_columns[i].push_back(colname);
++i;
}
if (i > num_columns) {
std::cout << "Warning:Ignoring extra column(s) on line " << lineno << std::endl;
}
++lineno;
}
}
// Get data vectors of different types
std::vector<double> get_dvector(const std::string& colname) { return columns[colname]->dvalues(); }
std::vector<int> get_ivector(const std::string& colname) { return columns[colname]->ivalues(); }
// Default is to return double values
std::vector<double> operator[](const std::string& colname) { return columns[colname]->dvalues(); }
std::vector<std::string> column_names;
std::vector<Column> raw_columns;
std::map<std::string, Column*> columns;
};
BOOST_AUTO_TEST_CASE(CheckMassBalanceWithinXXXMBE)
{
//std::string case_name(boost::unit_test::framework::master_test_suite().argv[1]);
std::string case_name("01_TUNING_XXXMBE");
std::string file_name = case_name + ".INFOITER";
ColumnData data(file_name);
auto rstep = data.get_ivector("ReportStep");
auto tstep = data.get_ivector("TimeStep");
auto mbo = data["MB_Oil"];
auto mbw = data["MB_Water"];
auto mbg = data["MB_Gas"];
const int num_reports = 1 + *std::max_element(rstep.begin(), rstep.end());
std::vector<double> max_mb;
max_mb.reserve(num_reports);
// Find the maximum mass balance error at each converged time step for each report step..
const int nrows = rstep.size();
int rcur = 0;
int tcur = 0;
double max_mb_step = std::numeric_limits<double>::min();
for (int i=0; i<(nrows-1); ++i) {
if (tcur != tstep[i+1] || rcur != rstep[i+1]) {
max_mb_step = std::max({mbo[i], mbw[i], mbg[i], max_mb_step});
tcur = tstep[i+1];
}
if (rcur != rstep[i+1]) {
max_mb.push_back(max_mb_step);
max_mb_step = std::numeric_limits<double>::min();
rcur = rstep[i+1];
}
}
max_mb.push_back( std::max({mbo.back(), mbw.back(), mbg.back(), max_mb_step}) );
std::cout << "---------------------------------------------------------------------------" << std::endl;
std::cout << "Found the following converged max mass balance error (per report step):" << std::endl;
for (auto& val : max_mb)
std::cout << val << std::endl;
std::cout << "---------------------------------------------------------------------------" << std::endl;
BOOST_CHECK( max_mb[0] < 1.0e-6 );
BOOST_CHECK( max_mb[1] < 1.0e-8 );
BOOST_CHECK( max_mb[2] < 1.0e-10 );
}
// int main(int argc, char** argv)
// {
// return boost::unit_test::unit_test_main(&init_unit_test, argc, argv);
// }
// int main(int argc, char** argv) {
// if (argc < 2) {
// std::cout << "Usage: test_tuning_XXXMBE CASE_NAME" << std::endl;
// exit(1);
// }
// std::string case_name(argv[1]);
// std::string file_name = case_name + ".INFOITER";
// ColumnData data(file_name);
// auto rstep = data.get_ivector("ReportStep");
// auto tstep = data.get_ivector("TimeStep");
// auto mbo = data["MB_Oil"];
// auto mbw = data["MB_Water"];
// auto mbg = data["MB_Gas"];
// const int num_reports = 1 + *std::max_element(rstep.begin(), rstep.end());
// std::vector<double> max_mb;
// max_mb.reserve(num_reports);
// // Find the maximum mass balance error at each converged time step for each report step..
// const int nrows = rstep.size();
// int rcur = 0;
// int tcur = 0;
// double max_mb_step = std::numeric_limits<double>::min();
// for (int i=0; i<(nrows-1); ++i) {
// if (tcur != tstep[i+1]) {
// max_mb_step = std::max({mbo[i], mbw[i], mbg[i], max_mb_step});
// tcur = tstep[i+1];
// }
// if (rcur != rstep[i+1]) {
// max_mb.push_back(max_mb_step);
// max_mb_step = std::numeric_limits<double>::min();
// rcur = rstep[i+1];
// }
// }
// max_mb.push_back( std::max({mbo.back(), mbw.back(), mbg.back(), max_mb_step}) );
// for (int i=0; i<num_reports; ++i)
// std::cout << "ReportStep " << i << ": " << max_mb[i] << std::endl;
// return 0;
// }