Add option for not including the removed volume in the MinpvProcessor

The volume in cells with pore volume less than the minpv threshold is
removed if minpvMode is ECLStd while it is added to the underlying cell
if minpvMode is OpmFil
This commit is contained in:
Tor Harald Sandve 2015-10-19 15:22:26 +02:00
parent e8ab4341f1
commit dec23df301
3 changed files with 49 additions and 15 deletions

View File

@ -159,7 +159,8 @@ namespace Opm
if (!poreVolumes.empty() && (eclipseGrid->getMinpvMode() != MinpvMode::ModeEnum::Inactive)) { if (!poreVolumes.empty() && (eclipseGrid->getMinpvMode() != MinpvMode::ModeEnum::Inactive)) {
MinpvProcessor mp(g.dims[0], g.dims[1], g.dims[2]); MinpvProcessor mp(g.dims[0], g.dims[1], g.dims[2]);
const double minpv_value = eclipseGrid->getMinpvValue(); const double minpv_value = eclipseGrid->getMinpvValue();
mp.process(poreVolumes, minpv_value, actnum, zcorn.data()); bool opmfil = eclipseGrid->getMinpvMode() == MinpvMode::OpmFIL;
mp.process(poreVolumes, minpv_value, actnum, opmfil, zcorn.data());
} }
const double z_tolerance = eclipseGrid->isPinchActive() ? const double z_tolerance = eclipseGrid->isPinchActive() ?

View File

@ -41,13 +41,17 @@ namespace Opm
/// \param[in] pv pore volumes of all logical cartesian cells /// \param[in] pv pore volumes of all logical cartesian cells
/// \param[in] minpv minimum pore volume to accept a cell /// \param[in] minpv minimum pore volume to accept a cell
/// \param[in] actnum active cells, inactive cells are not considered /// \param[in] actnum active cells, inactive cells are not considered
/// \param[in] mergeMinPVCells flag to determine whether cells below minpv
/// should be included in the cell below
/// \param[in, out] zcorn ZCORN array to be manipulated /// \param[in, out] zcorn ZCORN array to be manipulated
/// After processing, all cells that have lower pore volume than minpv /// After processing, all cells that have lower pore volume than minpv
/// will have the zcorn numbers changed so they are zero-thickness. Any /// will have the zcorn numbers changed so they are zero-thickness. Any
/// cell below will be changed to include the deleted volume. /// cell below will be changed to include the deleted volume if mergeMinPCCells is true
/// els the volume will be lost
void process(const std::vector<double>& pv, void process(const std::vector<double>& pv,
const double minpv, const double minpv,
const std::vector<int>& actnum, const std::vector<int>& actnum,
const bool mergeMinPVCells,
double* zcorn) const; double* zcorn) const;
private: private:
std::array<int,8> cornerIndices(const int i, const int j, const int k) const; std::array<int,8> cornerIndices(const int i, const int j, const int k) const;
@ -74,6 +78,7 @@ namespace Opm
inline void MinpvProcessor::process(const std::vector<double>& pv, inline void MinpvProcessor::process(const std::vector<double>& pv,
const double minpv, const double minpv,
const std::vector<int>& actnum, const std::vector<int>& actnum,
const bool mergeMinPVCells,
double* zcorn) const double* zcorn) const
{ {
// Algorithm: // Algorithm:
@ -83,9 +88,9 @@ namespace Opm
// pv[c] is less than minpv. // pv[c] is less than minpv.
// 3. If below the minpv threshold, move the lower four // 3. If below the minpv threshold, move the lower four
// zcorn associated with the cell c to coincide with // zcorn associated with the cell c to coincide with
// the upper four (so it becomes degenerate). Also move // the upper four (so it becomes degenerate). If mergeMinPVcells
// the higher four zcorn associated with the cell below // is true, the higher four zcorn associated with the cell below
// to these values (so it gains the deleted volume). // is moved to these values (so it gains the deleted volume).
// Check for sane input sizes. // Check for sane input sizes.
const size_t log_size = dims_[0] * dims_[1] * dims_[2]; const size_t log_size = dims_[0] * dims_[1] * dims_[2];
@ -108,14 +113,18 @@ namespace Opm
cz[count + 4] = cz[count]; cz[count + 4] = cz[count];
} }
setCellZcorn(ii, jj, kk, cz, zcorn); setCellZcorn(ii, jj, kk, cz, zcorn);
// Check if there is a cell below.
if (pv[c] > 0.0 && kk < dims_[2] - 1) { // optionally add removed volume to the cell below.
// Set lower k coordinates of cell below to upper cells's coordinates. if (mergeMinPVCells) {
std::array<double, 8> cz_below = getCellZcorn(ii, jj, kk + 1, zcorn); // Check if there is a cell below.
for (int count = 0; count < 4; ++count) { if (pv[c] > 0.0 && kk < dims_[2] - 1) {
cz_below[count] = cz[count]; // Set lower k coordinates of cell below to upper cells's coordinates.
std::array<double, 8> cz_below = getCellZcorn(ii, jj, kk + 1, zcorn);
for (int count = 0; count < 4; ++count) {
cz_below[count] = cz[count];
}
setCellZcorn(ii, jj, kk + 1, cz_below, zcorn);
} }
setCellZcorn(ii, jj, kk + 1, cz_below, zcorn);
} }
} }
} }

View File

@ -50,21 +50,45 @@ BOOST_AUTO_TEST_CASE(Processing)
0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0,
6, 6, 6, 6 }; 6, 6, 6, 6 };
std::vector<double> zcorn4after = { 0, 0, 0, 0,
0, 0, 0, 0,
1, 1, 1, 1,
3, 3, 3, 3,
3, 3, 3, 3,
6, 6, 6, 6 };
std::vector<double> zcorn5after = { 0, 0, 0, 0,
0, 0, 0, 0,
1, 1, 1, 1,
1, 1, 1, 1,
3, 3, 3, 3,
6, 6, 6, 6 };
std::vector<double> pv = { 1, 2, 3 }; std::vector<double> pv = { 1, 2, 3 };
std::vector<int> actnum = { 1, 1, 1 }; std::vector<int> actnum = { 1, 1, 1 };
Opm::MinpvProcessor mp1(1, 1, 3); Opm::MinpvProcessor mp1(1, 1, 3);
auto z1 = zcorn; auto z1 = zcorn;
mp1.process(pv, 0.5, actnum, z1.data()); bool fill_removed_cells = true;
mp1.process(pv, 0.5, actnum, fill_removed_cells, z1.data());
BOOST_CHECK_EQUAL_COLLECTIONS(z1.begin(), z1.end(), zcorn.begin(), zcorn.end()); BOOST_CHECK_EQUAL_COLLECTIONS(z1.begin(), z1.end(), zcorn.begin(), zcorn.end());
Opm::MinpvProcessor mp2(1, 1, 3); Opm::MinpvProcessor mp2(1, 1, 3);
auto z2 = zcorn; auto z2 = zcorn;
mp2.process(pv, 1.5, actnum, z2.data()); mp2.process(pv, 1.5, actnum, fill_removed_cells, z2.data());
BOOST_CHECK_EQUAL_COLLECTIONS(z2.begin(), z2.end(), zcorn2after.begin(), zcorn2after.end()); BOOST_CHECK_EQUAL_COLLECTIONS(z2.begin(), z2.end(), zcorn2after.begin(), zcorn2after.end());
Opm::MinpvProcessor mp3(1, 1, 3); Opm::MinpvProcessor mp3(1, 1, 3);
auto z3 = zcorn; auto z3 = zcorn;
mp3.process(pv, 2.5, actnum, z3.data()); mp3.process(pv, 2.5, actnum, fill_removed_cells, z3.data());
BOOST_CHECK_EQUAL_COLLECTIONS(z3.begin(), z3.end(), zcorn3after.begin(), zcorn3after.end()); BOOST_CHECK_EQUAL_COLLECTIONS(z3.begin(), z3.end(), zcorn3after.begin(), zcorn3after.end());
Opm::MinpvProcessor mp4(1, 1, 3);
auto z4 = zcorn;
mp4.process(pv, 1.5, actnum, !fill_removed_cells, z4.data());
BOOST_CHECK_EQUAL_COLLECTIONS(z4.begin(), z4.end(), zcorn4after.begin(), zcorn4after.end());
Opm::MinpvProcessor mp5(1, 1, 3);
auto z5 = zcorn;
mp5.process(pv, 2.5, actnum, !fill_removed_cells, z5.data());
BOOST_CHECK_EQUAL_COLLECTIONS(z5.begin(), z5.end(), zcorn5after.begin(), zcorn5after.end());
} }