mirror of
https://github.com/openmc-dev/openmc.git
synced 2026-07-21 14:35:27 -04:00
180 lines
7.3 KiB
ReStructuredText
180 lines
7.3 KiB
ReStructuredText
.. _usersguide_processing:
|
|
|
|
=================================
|
|
Data Processing and Visualization
|
|
=================================
|
|
|
|
.. currentmodule:: openmc
|
|
|
|
This section is intended to explain procedures for carrying out common
|
|
post-processing tasks with OpenMC. While several utilities of varying complexity
|
|
are provided to help automate the process, the most powerful capabilities for
|
|
post-processing derive from use of the :ref:`Python API <pythonapi>`.
|
|
|
|
.. _usersguide_statepoint:
|
|
|
|
-------------------------
|
|
Working with State Points
|
|
-------------------------
|
|
|
|
Tally results are saved in both a text file (tallies.out) as well as an HDF5
|
|
statepoint file. While the tallies.out file may be fine for simple tallies, in
|
|
many cases the user requires more information about the tally or the run, or has
|
|
to deal with a large number of result values (e.g. for mesh tallies). In these
|
|
cases, extracting data from the statepoint file via the :ref:`pythonapi` is the
|
|
preferred method of data analysis and visualization.
|
|
|
|
Data Extraction
|
|
---------------
|
|
|
|
A great deal of information is available in statepoint files (See
|
|
:ref:`io_statepoint`), all of which is accessible through the Python
|
|
API. The :class:`openmc.StatePoint` class can load statepoints and access data
|
|
as requested; it is used in many of the provided plotting utilities, OpenMC's
|
|
regression test suite, and can be used in user-created scripts to carry out
|
|
manipulations of the data.
|
|
|
|
An `example notebook`_ demonstrates how to extract data from a statepoint using
|
|
the Python API.
|
|
|
|
Plotting in 2D
|
|
--------------
|
|
|
|
The `example notebook`_ also demonstrates how to plot a structured mesh tally in
|
|
two dimensions using the Python API. One can also use the `openmc-plotter
|
|
<https://github.com/openmc-dev/plotter/>`_ application that provides an
|
|
interactive GUI to explore and plot a much wider variety of tallies.
|
|
|
|
.. _usersguide_track:
|
|
|
|
----------------------------
|
|
Particle Track Visualization
|
|
----------------------------
|
|
|
|
.. image:: ../_images/Tracks.png
|
|
:width: 400px
|
|
|
|
OpenMC can dump particle tracks—the position of particles as they are
|
|
transported through the geometry. There are two ways to make OpenMC output
|
|
tracks: all particle tracks through a command line argument or specific particle
|
|
tracks through settings.xml.
|
|
|
|
Running :ref:`scripts_openmc` with the argument ``-t`` or ``--track`` will cause
|
|
a track file to be created for every particle transported in the code. Be
|
|
careful as this will produce as many files as there are source particles in your
|
|
simulation. To identify a specific particle for which a track should be created,
|
|
set the :attr:`Settings.track` attribute to a tuple containing the batch,
|
|
generation, and particle number of the desired particle. For example, to create
|
|
a track file for particle 4 of batch 1 and generation 2::
|
|
|
|
settings = openmc.Settings()
|
|
settings.track = [(1, 2, 4)]
|
|
|
|
To specify multiple particles, specify a list of tuples, e.g., if we wanted
|
|
particles 3 and 4 from batch 1 and generation 2::
|
|
|
|
settings.track = [(1, 2, 3), (1, 2, 4)]
|
|
|
|
After running OpenMC (now, without the ``-t`` argument), the working directory
|
|
will contain a file named `tracks.h5`, which contains a collection of particle
|
|
tracks. These track files can be converted into VTK poly data files or
|
|
matplotlib plots with the :class:`openmc.Tracks` class.
|
|
|
|
----------------------
|
|
Source Site Processing
|
|
----------------------
|
|
|
|
For eigenvalue problems, OpenMC will store information on the fission source
|
|
sites in the statepoint file by default. For each source site, the weight,
|
|
position, sampled direction, and sampled energy are stored. To extract this data
|
|
from a statepoint file, the ``openmc.statepoint`` module can be used. An
|
|
`example notebook`_ demontrates how to analyze and plot source information.
|
|
|
|
.. _example notebook: https://nbviewer.jupyter.org/github/openmc-dev/openmc-notebooks/blob/main/post-processing.ipynb
|
|
|
|
------------------------
|
|
VTK Mesh File Generation
|
|
------------------------
|
|
|
|
VTK files of OpenMC meshes can be created using the
|
|
:meth:`openmc.Mesh.write_data_to_vtk` method. This method supports several VTK
|
|
formats depending on the mesh type. Structured meshes
|
|
(:class:`~openmc.RegularMesh`, :class:`~openmc.RectilinearMesh`,
|
|
:class:`~openmc.CylindricalMesh`, and :class:`~openmc.SphericalMesh`) can be
|
|
exported to legacy VTK format (``.vtk``). The :class:`~openmc.UnstructuredMesh`
|
|
class supports VTK unstructured grid formats (``.vtu``) as well as an HDF5-based
|
|
format (``.vtkhdf``) that does not require the ``vtk`` module to write.
|
|
|
|
Data can be applied to the
|
|
elements of the resulting mesh from mesh filter objects. This data can be
|
|
provided either as a flat array or, in the case of structured meshes
|
|
(:class:`~openmc.RegularMesh`, :class:`~openmc.RectilinearMesh`,
|
|
:class:`~openmc.CylindricalMesh`, or :class:`SphericalMesh`), the data can be
|
|
shaped with dimensions that match the dimensions of the mesh itself.
|
|
|
|
|
|
.. image:: ../_images/sphere-mesh-vtk.png
|
|
:width: 400px
|
|
:align: center
|
|
:alt: OpenMC spherical mesh exported to VTK
|
|
|
|
|
|
For all mesh types, if a flat data array is provided to the mesh, it is expected
|
|
that the data is ordered in the same ordering as the :attr:`openmc.Mesh.indices`
|
|
for that mesh object. When providing data directly from a tally, as shown below,
|
|
a flat array for a given dataset can be passed directly to this method.
|
|
|
|
::
|
|
|
|
# create model above
|
|
|
|
# create a mesh tally
|
|
mesh = openmc.RegularMesh()
|
|
mesh.dimension = [10, 20, 30]
|
|
mesh.lower_left = [-5, -10, -15]
|
|
mesh.upper_right = [5, 10, 15]
|
|
mesh_filter = openmc.MeshFilter(mesh)
|
|
tally = openmc.Tally()
|
|
tally.filters = [mesh_filter]
|
|
tally.scores = ['flux']
|
|
|
|
model.tallies = [tally]
|
|
model.run(apply_tally_results=True)
|
|
|
|
# provide the data as-is to the method
|
|
mesh.write_data_to_vtk('flux.vtk', {'flux-mean': tally.mean})
|
|
|
|
The :class:`~openmc.Tally` object also provides a way to expand the dimensions
|
|
of the mesh filter into a meaningful form where indexing the mesh filter
|
|
dimensions results in intuitive slicing of structured meshes by setting
|
|
``expand_dims=True`` when using :meth:`openmc.Tally.get_reshaped_data`. This
|
|
reshaping does cause flat indexing of the data to change, however. As noted
|
|
above, provided datasets are allowed to be shaped so long as such datasets have
|
|
shapes that match the mesh dimensions. The ability to pass datasets in this way
|
|
is useful when additional filters are applied to a tally. The example below
|
|
demonstrates such a case for tally with both a :class:`~openmc.MeshFilter` and
|
|
:class:`~openmc.EnergyFilter` applied.
|
|
|
|
::
|
|
|
|
# create model above
|
|
|
|
# create a mesh tally with energy filter
|
|
mesh = openmc.RegularMesh()
|
|
mesh.dimension = [10, 20, 30]
|
|
mesh.lower_left = [-5, -10, -15]
|
|
mesh.upper_right = [5, 10, 15]
|
|
mesh_filter = openmc.MeshFilter(mesh)
|
|
energy_filter = openmc.EnergyFilter([0.0, 1.0, 20.0e6])
|
|
tally = openmc.Tally()
|
|
tally.filters = [mesh_filter, energy_filter]
|
|
tally.scores = ['flux']
|
|
|
|
model.tallies = [tally]
|
|
model.run(apply_tally_results=True)
|
|
|
|
# get the data with mesh dimensions expanded, squeeze out length-one dimensions (nuclides, scores)
|
|
flux = tally.get_reshaped_data(expand_dims=True).squeeze() # shape: (10, 20, 30, 2)
|
|
|
|
# write the lowest energy group to a VTK file
|
|
mesh.write_data_to_vtk('flux-group1.vtk', datasets={'flux-mean': flux[..., 0]})
|