Skip to content
GitLab
Projects
Groups
Snippets
Help
Loading...
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
D
dorie
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
31
Issues
31
List
Boards
Labels
Service Desk
Milestones
Merge Requests
9
Merge Requests
9
Operations
Operations
Incidents
Environments
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
dorie
dorie
Commits
85549071
Commit
85549071
authored
Aug 22, 2019
by
Lukas Riedel
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Add two unit test suites for boundary conditions
Using Google Test
parent
9c0c39eb
Changes
4
Pipelines
1
Hide whitespace changes
Inline
Side-by-side
Showing
4 changed files
with
432 additions
and
217 deletions
+432
-217
dune/dorie/test/CMakeLists.txt
dune/dorie/test/CMakeLists.txt
+5
-4
dune/dorie/test/test-boundary-condition-manager.cc
dune/dorie/test/test-boundary-condition-manager.cc
+301
-0
dune/dorie/test/test-boundary-condition.cc
dune/dorie/test/test-boundary-condition.cc
+124
-211
dune/dorie/test/test-boundary-condition.mini.in
dune/dorie/test/test-boundary-condition.mini.in
+2
-2
No files found.
dune/dorie/test/CMakeLists.txt
View file @
85549071
...
...
@@ -14,16 +14,17 @@ dorie_add_unit_test(SOURCES test-grid-function-container.cc NAME test-grid-funct
dorie_add_unit_test
(
SOURCES test-interpolators.cc NAME test-interpolators
)
dorie_add_unit_test
(
SOURCES test-scaling-adapters.cc NAME test-scaling-adapters
)
dorie_add_unit_test
(
SOURCES test-param-factory.cc NAME test-param-factory
)
dorie_add_unit_test
(
SOURCES test-boundary-condition.cc
NAME test-boundary-condition
)
# boundary condition test
dorie_add_metaini_test
(
UNIT_TEST
SOURCE test-boundary-condition.cc
BASENAME test-boundary-condition
UNIT_TEST
CUSTOM_MAIN
SOURCE test-boundary-condition
-manager
.cc
BASENAME test-boundary-condition
-manager
METAINI test-boundary-condition.mini.in
CREATED_TARGETS bc_target
)
target_link_libraries
(
${
bc_target
}
spdlog
)
# grid creator test
dorie_add_metaini_test
(
...
...
dune/dorie/test/test-boundary-condition-manager.cc
0 → 100644
View file @
85549071
#include <gtest/gtest.h>
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#include <memory>
#include <yaml-cpp/yaml.h>
#include <dune/common/exceptions.hh>
#include <dune/common/float_cmp.hh>
#include <dune/common/parallel/mpihelper.hh>
#include <dune/grid/yaspgrid.hh>
#include <dune/grid/common/gridview.hh>
#include <dune/dorie/common/setup.hh>
#include <dune/dorie/common/logging.hh>
#include <dune/dorie/common/grid_creator.hh>
#include <dune/dorie/common/boundary_condition/manager.hh>
#include <dune/dorie/common/boundary_condition/factory.hh>
// Store command line arguments
int
_argc
;
char
**
_argv
;
/// The traits mock-up for this test
struct
Traits
{
static
constexpr
int
dim
=
2
;
using
RF
=
double
;
using
Grid
=
Dune
::
YaspGrid
<
dim
>
;
using
GV
=
typename
Grid
::
LeafGridView
;
using
Intersection
=
typename
GV
::
Traits
::
Intersection
;
};
/// Alias for the boundary condition type
using
BC
=
Dune
::
Dorie
::
BoundaryCondition
<
typename
Traits
::
RF
>
;
/* ------------------------------------------------------------------------- */
// Test BC factory creating BCs from YAML nodes
/// BCFactory fixture. Create three factories with a different mode each.
class
BCFactory
:
public
::
testing
::
Test
{
protected:
using
Mode
=
Dune
::
Dorie
::
BCMMode
;
template
<
Mode
mode
>
using
BCF
=
Dune
::
Dorie
::
BoundaryConditionFactory
<
double
,
mode
>
;
/// Initialize the DUNE MPI Helper from the command line arguments
Dune
::
MPIHelper
&
helper
=
Dune
::
MPIHelper
::
instance
(
_argc
,
_argv
);
std
::
unique_ptr
<
BCF
<
Mode
::
none
>>
_bcf_none
;
std
::
unique_ptr
<
BCF
<
Mode
::
richards
>>
_bcf_richards
;
std
::
unique_ptr
<
BCF
<
Mode
::
transport
>>
_bcf_transport
;
void
SetUp
()
override
{
auto
[
inifile
,
log
,
helper
]
=
Dune
::
Dorie
::
Setup
::
init
(
_argc
,
_argv
);
_bcf_none
=
std
::
make_unique
<
BCF
<
Mode
::
none
>>
(
log
);
_bcf_richards
=
std
::
make_unique
<
BCF
<
Mode
::
richards
>>
(
log
);
_bcf_transport
=
std
::
make_unique
<
BCF
<
Mode
::
transport
>>
(
log
);
}
void
TearDown
()
override
{
// Remove loggers
spdlog
::
drop_all
();
}
};
TEST_F
(
BCFactory
,
Dirichlet
)
{
YAML
::
Node
config
=
YAML
::
Load
(
"{type: Dirichlet,"
"value: 1.0,"
"time: 0.0"
"}"
);
EXPECT_NO_THROW
(
_bcf_none
->
create
(
"name"
,
config
,
1.0
));
EXPECT_NO_THROW
(
_bcf_richards
->
create
(
"name"
,
config
,
1.0
));
EXPECT_THROW
(
_bcf_transport
->
create
(
"name"
,
config
,
1.0
),
Dune
::
IOError
);
config
=
YAML
::
Load
(
"{type: Dirichlet,"
"value: 1.0,"
"time: 0.0,"
"concentration_type: water_phase"
"}"
);
EXPECT_NO_THROW
(
_bcf_none
->
create
(
"name"
,
config
,
1.0
));
EXPECT_NO_THROW
(
_bcf_richards
->
create
(
"name"
,
config
,
1.0
));
EXPECT_NO_THROW
(
_bcf_transport
->
create
(
"name"
,
config
,
1.0
));
config
=
YAML
::
Load
(
"{type: Dirichlet,"
"value: 1.0,"
"time: 0.0,"
"concentration_type: none"
"}"
);
EXPECT_NO_THROW
(
_bcf_none
->
create
(
"name"
,
config
,
1.0
));
EXPECT_NO_THROW
(
_bcf_richards
->
create
(
"name"
,
config
,
1.0
));
EXPECT_THROW
(
_bcf_transport
->
create
(
"name"
,
config
,
1.0
),
Dune
::
IOError
);
}
TEST_F
(
BCFactory
,
Neumann
)
{
YAML
::
Node
config
=
YAML
::
Load
(
"{type: Neumann,"
"value: 1.0,"
"time: 0.0,"
"horizontal_projection: true"
"}"
);
EXPECT_NO_THROW
(
_bcf_none
->
create
(
"name"
,
config
,
1.0
));
EXPECT_NO_THROW
(
_bcf_richards
->
create
(
"name"
,
config
,
1.0
));
EXPECT_NO_THROW
(
_bcf_transport
->
create
(
"name"
,
config
,
1.0
));
}
TEST_F
(
BCFactory
,
Outflow
)
{
YAML
::
Node
config
=
YAML
::
Load
(
"{type: Outflow,"
"value: 1.0,"
"time: 0.0"
"}"
);
EXPECT_NO_THROW
(
_bcf_none
->
create
(
"name"
,
config
,
1.0
));
EXPECT_THROW
(
_bcf_richards
->
create
(
"name"
,
config
,
1.0
),
Dune
::
IOError
);
EXPECT_NO_THROW
(
_bcf_transport
->
create
(
"name"
,
config
,
1.0
));
}
/* ------------------------------------------------------------------------- */
// Test BC manager and loaded BC data.
/// BoundaryConditionManager fixture
/** \tparam T BCMMode wrapped into an integral constant to appear as type
*/
// template<typename T>
class
BCManager
:
public
::
testing
::
Test
{
protected:
/// Initialize the DUNE MPI Helper from the command line arguments
Dune
::
MPIHelper
&
helper
=
Dune
::
MPIHelper
::
instance
(
_argc
,
_argv
);
/// Pointer to the grid
std
::
shared_ptr
<
Traits
::
Grid
>
_grid
;
using
BCM
=
Dune
::
Dorie
::
BoundaryConditionManager
<
Traits
,
Dune
::
Dorie
::
BCMMode
::
none
>
;
/// Pointer to the manager
std
::
unique_ptr
<
BCM
>
_manager
;
/// Initialize
void
SetUp
()
override
{
// Initialize ALL the things!
auto
[
inifile
,
log
,
helper
]
=
Dune
::
Dorie
::
Setup
::
init
(
_argc
,
_argv
);
// create the grid
Dune
::
Dorie
::
GridCreator
<
Traits
::
Grid
>
gc
(
inifile
,
helper
);
_grid
=
gc
.
grid
();
const
auto
&
index_map
=
gc
.
boundary_index_map
();
inifile
=
Dune
::
Dorie
::
Setup
::
prep_ini_for_richards
(
inifile
);
const
auto
log_level
=
inifile
.
get
<
std
::
string
>
(
"output.logLevel"
);
Dune
::
Dorie
::
create_logger
(
Dune
::
Dorie
::
log_richards
,
helper
,
spdlog
::
level
::
from_str
(
log_level
));
_manager
=
std
::
make_unique
<
BCM
>
(
inifile
,
index_map
);
}
void
TearDown
()
override
{
// remove loggers
spdlog
::
drop_all
();
}
};
TEST_F
(
BCManager
,
TimeSteps
)
{
// check correct maximum time steps
double
max_dt
=
0.0
;
double
time_prev
=
0.0
;
for
(
auto
time
:
{
time_prev
,
0.5
,
1.5
})
{
EXPECT_DOUBLE_EQ
(
time
,
time_prev
+
max_dt
);
time_prev
=
time
;
this
->
_manager
->
set_time
(
time
);
max_dt
=
this
->
_manager
->
max_time_step
(
time
);
}
EXPECT_DOUBLE_EQ
(
max_dt
,
0.5
);
// assert exception if out of interval
EXPECT_THROW
(
this
->
_manager
->
set_time
(
-
0.5
),
Dune
::
InvalidStateException
);
EXPECT_THROW
(
this
->
_manager
->
set_time
(
2.0
),
Dune
::
InvalidStateException
);
}
TEST_F
(
BCManager
,
Neumann
)
{
auto
gv
=
_grid
->
leafGridView
();
auto
cell
=
*
Dune
::
elements
(
gv
).
begin
();
if
(
not
cell
.
hasBoundaryIntersections
())
{
ADD_FAILURE
();
}
for
(
auto
&&
is
:
Dune
::
intersections
(
gv
,
cell
))
{
const
auto
coords
=
is
.
geometry
().
center
();
if
(
Dune
::
FloatCmp
::
eq
(
coords
[
1
],
1.0
))
{
for
(
auto
time
:
{
0.0
,
1.0
,
1.5
,
1.9
})
{
using
namespace
Dune
::
Dorie
;
_manager
->
set_time
(
time
);
const
auto
bc
=
_manager
->
bc
(
is
);
EXPECT_EQ
(
bc
->
name
(),
"neumann"
);
EXPECT_EQ
(
bc
->
type
(),
Operator
::
BCType
::
Neumann
);
EXPECT_DOUBLE_EQ
(
bc
->
evaluate
(
time
),
1.0
);
auto
&
time_int
=
bc
->
time_interval
();
EXPECT_DOUBLE_EQ
(
time_int
.
begin
,
0.0
);
EXPECT_DOUBLE_EQ
(
time_int
.
end
,
2.0
);
auto
&
bc_neumann
=
dynamic_cast
<
NeumannBoundaryCondition
<
double
>&>
(
*
bc
);
EXPECT_TRUE
(
bc_neumann
.
horizontal_projection
());
}
}
}
}
TEST_F
(
BCManager
,
Dirichlet
)
{
auto
gv
=
_grid
->
leafGridView
();
auto
cell
=
*
Dune
::
elements
(
gv
).
begin
();
if
(
not
cell
.
hasBoundaryIntersections
())
{
ADD_FAILURE
();
}
for
(
auto
&&
is
:
Dune
::
intersections
(
gv
,
cell
))
{
const
auto
coords
=
is
.
geometry
().
center
();
if
(
Dune
::
FloatCmp
::
eq
(
coords
[
1
],
0.0
))
{
using
namespace
Dune
::
Dorie
;
for
(
auto
time
:
{
0.5
,
1.4
})
{
_manager
->
set_time
(
time
);
const
auto
bc
=
_manager
->
bc
(
is
);
EXPECT_EQ
(
bc
->
name
(),
"dirichlet"
);
EXPECT_EQ
(
bc
->
type
(),
Operator
::
BCType
::
Dirichlet
);
EXPECT_DOUBLE_EQ
(
bc
->
evaluate
(
time
),
time
-
0.5
);
auto
&
time_int
=
bc
->
time_interval
();
EXPECT_DOUBLE_EQ
(
time_int
.
begin
,
0.5
);
EXPECT_DOUBLE_EQ
(
time_int
.
end
,
1.5
);
auto
&
bc_dirichlet
=
dynamic_cast
<
DirichletBoundaryCondition
<
double
>&>
(
*
bc
);
EXPECT_EQ
(
bc_dirichlet
.
concentration_type
(),
SoluteConcentration
::
water_phase
);
}
for
(
auto
time
:
{
0.0
,
1.5
,
1.9
})
{
_manager
->
set_time
(
time
);
const
auto
bc
=
_manager
->
bc
(
is
);
EXPECT_EQ
(
bc
->
name
(),
"default"
);
EXPECT_EQ
(
bc
->
type
(),
Operator
::
BCType
::
Neumann
);
EXPECT_DOUBLE_EQ
(
bc
->
evaluate
(
time
),
0.0
);
}
}
}
}
TEST_F
(
BCManager
,
Outflow
)
{
auto
gv
=
_grid
->
leafGridView
();
auto
cell
=
*
Dune
::
elements
(
gv
).
begin
();
if
(
not
cell
.
hasBoundaryIntersections
())
{
ADD_FAILURE
();
}
for
(
auto
&&
is
:
Dune
::
intersections
(
gv
,
cell
))
{
const
auto
coords
=
is
.
geometry
().
center
();
if
(
Dune
::
FloatCmp
::
eq
(
coords
[
1
],
1.0
))
{
for
(
auto
time
:
{
0.0
,
1.0
,
1.5
,
1.9
})
{
_manager
->
set_time
(
time
);
const
auto
bc
=
_manager
->
bc
(
is
);
EXPECT_EQ
(
bc
->
name
(),
"outflow"
);
EXPECT_EQ
(
bc
->
type
(),
Dune
::
Dorie
::
Operator
::
BCType
::
Outflow
);
EXPECT_DOUBLE_EQ
(
bc
->
evaluate
(
time
),
0.0
);
auto
&
time_int
=
bc
->
time_interval
();
EXPECT_DOUBLE_EQ
(
time_int
.
begin
,
0.0
);
EXPECT_DOUBLE_EQ
(
time_int
.
end
,
2.0
);
}
}
}
}
// --- Main Function --- //
int
main
(
int
argc
,
char
**
argv
)
{
// Parse input arguments
::
testing
::
InitGoogleTest
(
&
argc
,
argv
);
_argc
=
argc
;
_argv
=
argv
;
return
RUN_ALL_TESTS
();
}
dune/dorie/test/test-boundary-condition.cc
View file @
85549071
#include <gtest/gtest.h>
#ifdef HAVE_CONFIG_H
#include "config.h"
#include "config.h"
#endif
#include <memory>
#include <cassert>
#include <vector>
#include <yaml-cpp/yaml.h>
#include <type_traits>
#include <string>
#include <dune/common/exceptions.hh>
#include <dune/common/float_cmp.hh>
#include <dune/common/parallel/mpihelper.hh>
#include <dune/
grid/yaspgrid
.hh>
#include <dune/
grid/common/gridview
.hh>
#include <dune/
dorie/common/typedefs
.hh>
#include <dune/
dorie/common/boundary_condition/factory
.hh>
#include <dune/dorie/common/setup.hh>
#include <dune/dorie/common/logging.hh>
#include <dune/dorie/common/grid_creator.hh>
#include <dune/dorie/common/boundary_condition/manager.hh>
using
RF
=
double
;
/// The traits mock-up for this test
struct
Traits
/// Initialize the BC base class
/** \param value_end Set to True if an optional final value is to be added.
*/
template
<
typename
BC
>
BC
initialize_bc
(
bool
value_end
=
false
)
{
static
constexpr
int
dim
=
2
;
using
RF
=
double
;
using
Grid
=
Dune
::
YaspGrid
<
dim
>
;
using
GV
=
typename
Grid
::
LeafGridView
;
using
Intersection
=
typename
GV
::
Traits
::
Intersection
;
};
using
namespace
Dune
::
Dorie
;
TimeInterval
<
RF
>
t_int
({
1.0
,
2.0
});
const
RF
v_begin
=
1.0
;
const
RF
v_end
=
2.0
;
const
std
::
string
name
=
"bc"
;
if
constexpr
(
std
::
is_same_v
<
BC
,
NeumannBoundaryCondition
<
RF
>>
)
{
if
(
value_end
)
{
return
BC
(
name
,
t_int
,
v_begin
,
v_end
,
false
);
}
else
{
return
BC
(
name
,
t_int
,
v_begin
,
false
);
}
}
else
{
if
(
value_end
)
{
return
BC
(
name
,
t_int
,
v_begin
,
v_end
);
}
else
{
return
BC
(
name
,
t_int
,
v_begin
);
}
}
}
/
// Alias for the boundary condition type
using
BC
=
Dune
::
Dorie
::
BoundaryCondition
<
typename
Traits
::
RF
>
;
/
* ------------------------------------------------------------------------- */
// Test common features of all boundary conditions
/// Test the default boundary condition, after specs of the YAML input file
void
test_default_bc
(
const
std
::
shared_ptr
<
BC
>
bc
,
const
typename
Traits
::
RF
time
)
template
<
typename
BC
>
class
BoundaryCondition
:
public
::
testing
::
Test
{
using
namespace
Dune
::
FloatCmp
;
assert
(
eq
(
bc
->
evaluate
(
time
),
0.0
));
protected:
BC
_bc
=
initialize_bc
<
BC
>
();
};
// perform a cast
using
namespace
Dune
::
Dorie
;
const
auto
&
bc_neumann
=
dynamic_cast
<
const
NeumannBoundaryCondition
<
double
>&>
(
*
bc
);
assert
(
not
bc_neumann
.
horizontal_projection
());
}
using
BCTypes
=
::
testing
::
Types
<
Dune
::
Dorie
::
NeumannBoundaryCondition
<
RF
>
,
Dune
::
Dorie
::
BoundaryCondition
<
RF
>
,
Dune
::
Dorie
::
DirichletBoundaryCondition
<
RF
>
,
Dune
::
Dorie
::
OutflowBoundaryCondition
<
RF
>>
;
TYPED_TEST_SUITE
(
BoundaryCondition
,
BCTypes
);
/// Test the Neumann boundary condition, after specs of the YAML input file
void
test_neumann_bc
(
const
std
::
shared_ptr
<
BC
>
bc
,
const
typename
Traits
::
RF
time
,
const
bool
transport_mode
)
TYPED_TEST
(
BoundaryCondition
,
Initialize
)
{
using
namespace
Dune
::
FloatCmp
;
assert
(
eq
(
bc
->
evaluate
(
0.0
),
1.0
));
assert
(
eq
(
bc
->
evaluate
(
2.0
),
1.0
));
// perform a cast
using
namespace
Dune
::
Dorie
;
const
auto
&
bc_neumann
=
dynamic_cast
<
const
NeumannBoundaryCondition
<
double
>&>
(
*
bc
);
assert
(
bc_neumann
.
horizontal_projection
()
^
transport_mode
);
const
auto
&
time_interval
=
this
->
_bc
.
time_interval
();
EXPECT_DOUBLE_EQ
(
1.0
,
time_interval
.
begin
);
EXPECT_DOUBLE_EQ
(
2.0
,
time_interval
.
end
);
EXPECT_EQ
(
this
->
_bc
.
name
(),
"bc"
);
}
/// Test the Dirichlet boundary condition, after specs of the YAML input file
void
test_dirichlet_bc
(
const
std
::
shared_ptr
<
BC
>
bc
,
const
typename
Traits
::
RF
time
,
const
bool
transport_mode
)
TYPED_TEST
(
BoundaryCondition
,
EvaluateThrow
)
{
using
namespace
Dune
::
FloatCmp
;
assert
(
ge
(
time
,
0.5
)
and
le
(
time
,
1.5
));
assert
(
eq
(
bc
->
evaluate
(
0.5
),
0.0
));
assert
(
eq
(
bc
->
evaluate
(
1.0
),
0.5
));
assert
(
eq
(
bc
->
evaluate
(
1.5
),
1.0
));
// perform a cast
using
namespace
Dune
::
Dorie
;
const
auto
&
bc_dirichlet
=
dynamic_cast
<
const
DirichletBoundaryCondition
<
double
>&>
(
*
bc
);
// case: not transport
if
(
transport_mode
)
{
assert
(
bc_dirichlet
.
concentration_type
()
==
SoluteConcentration
::
water_phase
);
}
else
{
assert
(
bc_dirichlet
.
concentration_type
()
==
SoluteConcentration
::
none
);
}
// check interval testing
try
{
const
auto
log
=
Dune
::
Dorie
::
get_logger
(
Dune
::
Dorie
::
log_base
);
log
->
warn
(
"Expecting one error message about a wrong query:"
);
bc
->
evaluate
(
2.0
);
}
catch
(
Dune
::
InvalidStateException
&
e
)
{
return
;
}
// execution should not reach this point
assert
(
false
);
// inside time interval
EXPECT_NO_THROW
(
this
->
_bc
.
evaluate
(
1.0
));
EXPECT_NO_THROW
(
this
->
_bc
.
evaluate
(
1.5
));
EXPECT_NO_THROW
(
this
->
_bc
.
evaluate
(
2.0
));
// outside time interval
EXPECT_THROW
(
this
->
_bc
.
evaluate
(
-
1.0
),
Dune
::
InvalidStateException
);
EXPECT_THROW
(
this
->
_bc
.
evaluate
(
0.0
),
Dune
::
InvalidStateException
);
EXPECT_THROW
(
this
->
_bc
.
evaluate
(
2.5
),
Dune
::
InvalidStateException
);
}
/// Test the Outflow boundary condition
void
test_outflow_bc
(
const
std
::
shared_ptr
<
BC
>
bc
,
const
typename
Traits
::
RF
time
)
TYPED_TEST
(
BoundaryCondition
,
Evaluate
)
{
assert
(
Dune
::
FloatCmp
::
eq
(
bc
->
evaluate
(
time
),
0.0
));
EXPECT_DOUBLE_EQ
(
this
->
_bc
.
evaluate
(
1.0
),
1.0
);
EXPECT_DOUBLE_EQ
(
this
->
_bc
.
evaluate
(
1.5
),
1.0
);
EXPECT_DOUBLE_EQ
(
this
->
_bc
.
evaluate
(
2.0
),
1.0
);
}
/// Test a single boundary condition for a given time
/** Delegates the actual test to the respective functions which are
* specialized to the type and respective values of the BC
*/
void
test_boundary_condition
(
const
std
::
shared_ptr
<
BC
>
bc
,
const
typename
Traits
::
RF
time
,
const
bool
transport_mode
)
TEST
(
BoundaryCondition
,
EvaluateInterpolate
)
{
using
namespace
Dune
::
Dorie
;
const
auto
log
=
get_logger
(
log_base
);
auto
bc
=
initialize_bc
<
Dune
::
Dorie
::
BoundaryCondition
<
RF
>>
(
true
);
EXPECT_DOUBLE_EQ
(
bc
.
evaluate
(
1.0
),
1.0
);
EXPECT_DOUBLE_EQ
(
bc
.
evaluate
(
1.5
),
1.5
);
EXPECT_DOUBLE_EQ
(
bc
.
evaluate
(
2.0
),
2.0
);
}
const
auto
name
=
bc
->
name
();
const
auto
type
=
bc
->
type
();
/* ------------------------------------------------------------------------- */
// Test Dirichlet BC
log
->
info
(
"Query time: {}. Testing boundary condition: {}"
,
time
,
name
);
if
(
name
==
"default"
)
{
test_default_bc
(
bc
,
time
);
}
else
if
(
type
==
Operator
::
BCType
::
Dirichlet
)
{
test_dirichlet_bc
(
bc
,
time
,
transport_mode
);
}
else
if
(
type
==
Operator
::
BCType
::
Neumann
)
{
test_neumann_bc
(
bc
,
time
,
transport_mode
);
}
else
if
(
type
==
Operator
::
BCType
::
Outflow
)
{
test_outflow_bc
(
bc
,
time
);
}
else
{
DUNE_THROW
(
Dune
::
InvalidStateException
,
"Encountered unknown "
"boundary condition"
);
}
class
Dirichlet
:
public
testing
::
TestWithParam
<
Dune
::
Dorie
::
SoluteConcentration
>
{
protected:
using
BC
=
Dune
::
Dorie
::
DirichletBoundaryCondition
<
RF
>
;
BC
_bc
=
BC
(
"bc"
,
{
1.0
,
2.0
},
1.0
,
GetParam
());
};
TEST_P
(
Dirichlet
,
SoluteConcentration
)
{
EXPECT_EQ
(
_bc
.
concentration_type
(),
GetParam
());
}
/// Iterate over boundary intersections and test the respective BC
template
<
typename
BCManager
>
void
test_bcs_on_grid
(
const
std
::
shared_ptr
<
typename
Traits
::
Grid
>
grid
,
const
BCManager
&
boundary
,
const
typename
Traits
::
RF
time
,
const
bool
transport_mode
)
TEST_P
(
Dirichlet
,
StaticInformation
)
{
const
auto
gv
=
grid
->
leafGridView
();
EXPECT_EQ
(
_bc
.
type
(),
Dune
::
Dorie
::
Operator
::
BCType
::
Dirichlet
);
EXPECT_EQ
(
_bc
.
type_str
,
"dirichlet"
);
}
// iterate over grid elements
for
(
const
auto
&
elem
:
elements
(
gv
))
{
if
(
not
elem
.
hasBoundaryIntersections
())
continue
;
INSTANTIATE_TEST_SUITE_P
(
DirichletConcentrationType
,
Dirichlet
,
testing
::
Values
(
Dune
::
Dorie
::
SoluteConcentration
::
total
,
Dune
::
Dorie
::
SoluteConcentration
::
water_phase
,
Dune
::
Dorie
::
SoluteConcentration
::
none
));
// iterate over boundary intersections
for
(
const
auto
&
is
:
intersections
(
gv
,
elem
))
{
if
(
not
is
.
boundary
())
continue
;
const
auto
bc
=
boundary
.
bc
(
is
);
test_boundary_condition
(
bc
,
time
,
transport_mode
);
}
}
}
/* ------------------------------------------------------------------------- */
// Test Neumann BC
/// Test if set_time properly throws
/** \return True if the test passes
*/
template
<
typename
BCManager
>
bool
test_set_time_throw
(
BCManager
&
boundary
)
class
Neumann
:
public
testing
::
TestWithParam
<
bool
>
{
try
{
boundary
.
set_time
(
2.0
);
}
catch
(
Dune
::
InvalidStateException
&
e
)
{
return
true
;
}
return
false
;
}
protected:
using
BC
=
Dune
::
Dorie
::
NeumannBoundaryCondition
<
RF
>
;
BC
_bc
=
BC
(
"bc"
,
{
1.0
,
2.0
},
1.0
,
GetParam
());
};
int
main
(
int
argc
,
char
**
argv
)
TEST_P
(
Neumann
,
HorizontalProjection
)
{
try
{