-
Notifications
You must be signed in to change notification settings - Fork 27
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Improve MultiMat Sphinx documentation #1476
base: develop
Are you sure you want to change the base?
Changes from 6 commits
a1c2e4e
9c3b7fc
adf611f
d025ff2
0852ea8
4dc92aa
a5b0927
bf51abd
bf2901f
bf3c2b6
6d1f322
e099b77
859f8b2
1f6eeba
4ff89ad
d483834
a06c88f
fbb3b06
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,49 @@ | ||
.. ## Copyright (c) 2017-2024, Lawrence Livermore National Security, LLC and | ||
.. ## other Axom Project Developers. See the top-level LICENSE file for details. | ||
.. ## | ||
.. ## SPDX-License-Identifier: (BSD-3-Clause) | ||
|
||
****************************************************** | ||
Dynamic Mode | ||
****************************************************** | ||
|
||
The distribution of materials in MultiMat is controlled by the | ||
Cell-Material Relation (CMR). For many MultiMat use cases, this is set | ||
once (static mode) and then fields are defined on the MultiMat object. MultiMat | ||
also supports a dynamic mode that permits materials to move around in the mesh. | ||
|
||
When creating a MultiMat object using the default constructor, it will default | ||
to static mode using ``CELL_DOM`` data layout with sparse data. The data layout | ||
argument later impacts the ``addEntry()`` and ``removeEntry()`` methods that modify | ||
the MultiMat object's CMR in dynamic mode. For those methods, when MultiMat is | ||
created with a ``CELL_DOM`` data layout, it means that the first argument to | ||
``addEntry()`` will be a cell number and the second will be a material number. | ||
|
||
To convert the MultiMat object to dynamic mode, call the ``convertToDynamic()`` | ||
method. This method changes some internal representations (including field | ||
organization) to better support dynamic modifications of the CMR. For example, | ||
when changing to dynamic mode, ``SPARSE`` fields are converted to ``DENSE`` | ||
so further changes do not require field data to be reallocated/reorganized | ||
again. The CMR is modfified using calls to the ``addEntry()`` and ``removeEntry()`` | ||
BradWhitlock marked this conversation as resolved.
Show resolved
Hide resolved
|
||
methods. | ||
|
||
.. code-block:: cpp | ||
|
||
constexpr int nmats = 3; | ||
constexpr int ncells = 9; | ||
|
||
axom::multimat::MultiMat mm; | ||
|
||
// Multimat initialization omitted | ||
|
||
// Switch to dynamic mode | ||
mm.convertToDynamic(); | ||
|
||
// Add material 2 in zone 3 that was not there before. | ||
mm.addEntry(3, 2); | ||
|
||
// Remove material 1 in zone 5 | ||
mm.removeEntry(5, 1); | ||
|
||
// Volume fraction updates omitted (iterate Volfrac field, set new values) | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,118 @@ | ||
.. ## Copyright (c) 2017-2024, Lawrence Livermore National Security, LLC and | ||
.. ## other Axom Project Developers. See the top-level LICENSE file for details. | ||
.. ## | ||
.. ## SPDX-License-Identifier: (BSD-3-Clause) | ||
|
||
****************************************************** | ||
Field Concepts | ||
****************************************************** | ||
|
||
Fields are data that are defined over a mesh, typically with one or more values | ||
per cell. Fields can be scalar, indicating 1-component per cell - or they can | ||
contain multiple components as with vector data (2+ components per cell). This | ||
section talks about important MultiMat field concepts that determine where fields | ||
live on the mesh and how their data are organized in memory. | ||
|
||
####################### | ||
Field Mapping | ||
####################### | ||
|
||
MultiMat is associates materials with cells in a mesh, possibly subdividing cells. | ||
MultiMat includes the concept of field *mapping*, which is where on the mesh the | ||
field data live. Fields can be defined over the cells, which is how most simulations | ||
think about cell-centered fields. With MultiMat, fields can also be defined over | ||
the materials, allowing for compact storage of material-level data. Fields can | ||
also be defined over the cells/material pairs from the Cell-Material Relation (CMR), | ||
allowing fields to have data values for each material in a cell. | ||
|
||
.. figure:: figures/mapping.png | ||
:figwidth: 800px | ||
|
||
Diagram showing field mapping concept. | ||
|
||
+--------------------+----------------------------------------------------------+ | ||
| FieldMapping | Meaning | | ||
+====================+==========================================================+ | ||
| PER_CELL | The field contains up to ncells*ncomponents values (for | | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Minor: A space before and after the There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I added spaces. |
||
| | dense storage) and there are ncomponents values per cell.| | ||
| | For scalars *ncomponents* is 1 so the field length is | | ||
| | ncells. | | ||
+--------------------+----------------------------------------------------------+ | ||
| PER_MAT | The field contains nmats*ncomponents values and there | | ||
| | are ncomponents values per material. This mapping allows | | ||
| | fields to be defined over the entire material region and | | ||
| | any cell that uses the material inherits the per-material| | ||
| | field value, allowing for very compact storage of | | ||
| | material-level properties. | | ||
+--------------------+----------------------------------------------------------+ | ||
| PER_CELL_MAT | The field contains up to ncells*nmats*ncomponents (for | | ||
| | dense storage). This mapping allows materials within a | | ||
| | cell to have their own unique values, which makes them | | ||
| | useful for tracking data at a sub-cell level. | | ||
+--------------------+----------------------------------------------------------+ | ||
|
||
####################### | ||
Data Layout | ||
####################### | ||
|
||
Simulation codes contain a variety of algorithms that may have a preference for how | ||
data are arranged in memory to ensure good performance. MultiMat supports | ||
fields with a ``PER_CELL_MAT`` mapping and there are two ways to organize such data. | ||
Fields are said to be **Cell-Dominant** (``CELL_DOM``) if they are stored such that | ||
each cell stores all of its material data to memory before proceeding to data for | ||
the next cell. Fields are **Material-Dominant** (``MAT_DOM``) if the data for all | ||
cells that use the material is stored before proceeding to the next material. | ||
The data layout for multi-material data can be thought of as 2 nested for-loops where | ||
the outer loop is the dominant loop. For example, if iterating over materials and | ||
then cells, the data are stored using ``MAT_DOM`` layout. | ||
|
||
+--------------------+----------------------------------------------------------+ | ||
| DataLayout | Meaning | | ||
+====================+==========================================================+ | ||
| CELL_DOM | Data are stored for each cell and then for each material | | ||
| | like this *(c=cell, m=material)*: | | ||
| | | | ||
| | ``{c0m0, c0m1, c0m2, ..., c1m0, c1m1, c1m2, ...}`` | | ||
+--------------------+----------------------------------------------------------+ | ||
| MAT_DOM | Data are stored for each material and then for each cell | | ||
| | like this *(c=cell, m=material)*: | | ||
BradWhitlock marked this conversation as resolved.
Show resolved
Hide resolved
|
||
| | | | ||
| | ``{m0c0, m0c1, m0c2, m0c3, ... , m1c0, m1c1, m1c2, ...}``| | ||
+--------------------+----------------------------------------------------------+ | ||
|
||
####################### | ||
Sparsity Layout | ||
####################### | ||
|
||
Sparsity primarily concerns fields with ``PER_CELL_MAT`` mapping. When initializing | ||
the MultiMat object, the CMR indicates how materials are distributed | ||
over the mesh. It is completely acceptable for materials to skip over certain cells, | ||
which makes sense if we think about materials as a way to divide up the mesh into | ||
various regions or parts. There are ncells*nmats pairs of data that could be entered | ||
for MultiMat fields. For ``DENSE`` fields, the field must contain ncells*nmats values, | ||
with values present for cell/material pairs even where the material is not present. | ||
BradWhitlock marked this conversation as resolved.
Show resolved
Hide resolved
|
||
This is an easy way to specify the data but it wastes memory due to the extra values | ||
that do nothing other than keep the rectangular shape of the data array. | ||
|
||
For large meshes, compressing out unnecessary values can save a lot of memory. MultiMat | ||
supports a ``SPARSE`` layout that does not include any unnecessary values. Going back | ||
to the CMR as a matrix of true/false values, one must only provide field values for | ||
BradWhitlock marked this conversation as resolved.
Show resolved
Hide resolved
|
||
``SPARSE`` data where the CMR contains true values. | ||
|
||
|
||
.. figure:: figures/sparsity.png | ||
:figwidth: 800px | ||
|
||
Mixed-material volume fraction field with both DENSE and SPARSE representations. | ||
|
||
|
||
|
||
+--------------------+----------------------------------------------------------+ | ||
| SparsityLayout | Meaning | | ||
+====================+==========================================================+ | ||
| DENSE | Data are provided for all ncells*nmats pairs, even if | | ||
| | there is no cell/material that is valid. | | ||
+--------------------+----------------------------------------------------------+ | ||
| SPARSE | Data are provided for only the cell/material pairs that | | ||
| | are valid according to the CMR. | | ||
+--------------------+----------------------------------------------------------+ |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,120 @@ | ||
.. ## Copyright (c) 2017-2024, Lawrence Livermore National Security, LLC and | ||
.. ## other Axom Project Developers. See the top-level LICENSE file for details. | ||
.. ## | ||
.. ## SPDX-License-Identifier: (BSD-3-Clause) | ||
|
||
****************************************************** | ||
Materials | ||
****************************************************** | ||
|
||
MultiMat defines materials over the cells in a mesh. This section describes how to | ||
use the MultiMat object to define materials. | ||
|
||
####################### | ||
Cell Material Relation | ||
####################### | ||
|
||
The distribution of materials over the mesh is determined using the **Cell-Material Relation** *(CMR)*. | ||
If a mesh has *N* cells and *M* materials then each cell can have *M* possible values | ||
if it contains all of the possible materials. There is a total of N*M values if each | ||
cell contains all materials. There are multiple ways to specify the CMR to MultiMat. A | ||
BradWhitlock marked this conversation as resolved.
Show resolved
Hide resolved
|
||
static material decomposition is described here, though the CMR can also be built | ||
:doc:`dynamically <multimat_dynamic_mode>`. The easiest method for defining the CMR is | ||
to provide a bool vector containing true/false values for whether a cell/material | ||
combination is valid. | ||
|
||
.. figure:: figures/relation.png | ||
:figwidth: 800px | ||
|
||
Diagram showing mixed-material mesh with CELL_DOM and MAT_DOM ways of defining the Cell-Material Relation. | ||
|
||
The following code shows how to initialize a MultiMat object with 9 cells and 3 materials | ||
and build the CMR by populating a bool vector that is given to the MultiMat object. | ||
In the following example, the relation is expressed using a **Cell-Dominant** | ||
data layout (``CELL_DOM``). This means that the data will be arranged such that all material | ||
values for cell 0 are given, followed by all of the material values for cell 1, until all | ||
cells have provided their flags. The bool vector contains *true* if a material is present | ||
in a cell and *false* if the material is not present. This CMR vector is essentially | ||
a mask for which cell/material combinations are valid. Data can also be transposed | ||
into a **Material-Dominant** data layout (``MAT_DOM``) in which the materials are | ||
iterated first, followed by cells that use the current material. | ||
|
||
.. code-block:: cpp | ||
|
||
constexpr int nmats = 3; | ||
constexpr int ncells = 9; | ||
|
||
// Create the MultiMat object | ||
axom::multimat::MultiMat mm; | ||
mm.setNumberOfMaterials(nmats); | ||
mm.setNumberOfCells(ncells); | ||
|
||
// Cell-Dominant data layout | ||
int rel[9][3] = {{1,1,0}, | ||
{1,1,1}, | ||
{0,1,1}, | ||
{1,1,1}, | ||
{0,1,1}, | ||
{0,0,1}, | ||
{0,1,1}, | ||
{0,0,1}, | ||
{0,0,1}}; | ||
std::vector<bool> relation(ncells * nmats, false); | ||
for(int c = 0; c < ncells; c++) | ||
{ | ||
for(int m = 0; m < nmats; m++) | ||
{ | ||
relation[c * nmats + m] = rel[c][m] > 0; | ||
} | ||
} | ||
mm.setCellMatRel(relation, axom::multimat::DataLayout::CELL_DOM); | ||
|
||
|
||
####################### | ||
Volume Fractions | ||
####################### | ||
|
||
The CMR determines how materials are allocated to each cell but it does not determine | ||
how much of each material is present in the cell. Volume fractions determine how much of each material | ||
exists in each cell and is given as a percentage. If a cell contains materials A and B | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Please consider rephrasing to "The CMR determines which materials are present in each cell; volume fractions determine how much of each material is present in each cell." This shortens the first two sentences to one sentence with two parallel phrases: to me, this helps with clarity. Also, I don't think you need "given as a percentage," since the next sentence gives an example. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Changed. |
||
at 20% and 80%, respectively, then the volume fractions for those materials in the | ||
cell are: *0.2* and *0.8*. Note that the sum of volume fractions in a cell must equal 1 | ||
to account for all of the cell. Volume fractions must be provided for every valid | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Will multimat itself object if the volume fractions don't sum to 1? Is there a consistency check for this error mode, or will it just wait until it bites your algorithm? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. It doesn't enforce it really, but it will flag the error if MultiMat::isValid() is called. I added a statement to this effect. |
||
cell/material pair in the CMR and they must be specified using the same data layout | ||
as data in the CMR. | ||
|
||
.. figure:: figures/volume_fractions.png | ||
:figwidth: 600px | ||
|
||
Diagram showing mixed-material mesh with volume fractions shown in CELL_DOM table. | ||
|
||
Volume fractions are stored in MultiMat as a field and fields have an added concept | ||
of sparsity. Fields can provide data for every possible cell/material pair; this is | ||
called a dense field. Dense fields are easy to understand since they have values for | ||
every cell/material pair and they take more memory since zeroes must be provided even | ||
for invalid cell/material pairs. Fields can also be sparse, which eliminates the zeroes | ||
where a material does not exist. | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Suggestion: rephrase to "Dense fields are easy to understand: they have values for every cell/material pair. Dense fields store zeros for cells where a material is not present. Fields can also be sparse, saving memory by eliminating the zeros where a material does not exist." (I think both "zeros" and "zeroes" are correct. Not sure on that.) There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Changed. |
||
|
||
Volume fraction data are provided to MultiMat wrapped in an ``axom::ArrayView`` object, | ||
which provides the default values for the volume fractions. The *ArrayView* is passed | ||
to MultiMat using the ``setVolfracField()`` method. The following example shows how to | ||
pass a dense volume fraction field to MultiMat. Note the zeroes where the material is | ||
not present. After adding volume fractions, the MultiMat object is fully constructed | ||
and it can be used to store field data. | ||
|
||
.. code-block:: cpp | ||
|
||
double volfracs[9][3] = {{0.9, 0.1, 0.}, | ||
{0.22, 0.5, 0.28}, | ||
{0., 0.3, 0.7}, | ||
{0.25, 0.5, 0.25}, | ||
{0., 0.05, 0.95}, | ||
{0., 0., 1.}, | ||
{0., 0.4, 0.6}, | ||
{0., 0., 1.}, | ||
{0., 0., 1.}}; | ||
axom::ArrayView<double> vfView(&volfracs[0][0], ncells * nmats); | ||
mm.setVolfracField(vfView, | ||
axom::multimat::DataLayout::CELL_DOM, | ||
axom::multimat::SparsityLayout::DENSE); | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This links to the top of core instead of multimat. Maybe the last bit needs to be
multimattop.html
?Doxygen multimat page: https://axom.readthedocs.io/en/feature-whitlock-multimat_documentation/doxygen/html/multimattop.html
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks - fixed it.