mirror of
https://github.com/openmc-dev/openmc.git
synced 2026-07-27 13:45:36 -04:00
allowing different volume methods for diff mat (#2691)
Co-authored-by: Paul Romano <paul.k.romano@gmail.com>
This commit is contained in:
parent
0f429e7ea7
commit
989875b070
4 changed files with 120 additions and 23 deletions
|
|
@ -164,6 +164,13 @@ class CoupledOperator(OpenMCOperator):
|
|||
``None`` implies no limit on the depth.
|
||||
|
||||
.. versionadded:: 0.12
|
||||
diff_volume_method : str
|
||||
Specifies how the volumes of the new materials should be found. Default
|
||||
is to 'divide equally' which divides the original material volume
|
||||
equally between the new materials, 'match cell' sets the volume of the
|
||||
material to volume of the cell they fill.
|
||||
|
||||
.. versionadded:: 0.13.4
|
||||
|
||||
Attributes
|
||||
----------
|
||||
|
|
@ -206,8 +213,8 @@ class CoupledOperator(OpenMCOperator):
|
|||
}
|
||||
|
||||
def __init__(self, model, chain_file=None, prev_results=None,
|
||||
diff_burnable_mats=False, normalization_mode="fission-q",
|
||||
fission_q=None,
|
||||
diff_burnable_mats=False, diff_volume_method="divide equally",
|
||||
normalization_mode="fission-q", fission_q=None,
|
||||
fission_yield_mode="constant", fission_yield_opts=None,
|
||||
reaction_rate_mode="direct", reaction_rate_opts=None,
|
||||
reduce_chain=False, reduce_chain_level=None):
|
||||
|
|
@ -257,15 +264,16 @@ class CoupledOperator(OpenMCOperator):
|
|||
}
|
||||
|
||||
super().__init__(
|
||||
model.materials,
|
||||
cross_sections,
|
||||
chain_file,
|
||||
prev_results,
|
||||
diff_burnable_mats,
|
||||
fission_q,
|
||||
helper_kwargs,
|
||||
reduce_chain,
|
||||
reduce_chain_level)
|
||||
materials=model.materials,
|
||||
cross_sections=cross_sections,
|
||||
chain_file=chain_file,
|
||||
prev_results=prev_results,
|
||||
diff_burnable_mats=diff_burnable_mats,
|
||||
diff_volume_method=diff_volume_method,
|
||||
fission_q=fission_q,
|
||||
helper_kwargs=helper_kwargs,
|
||||
reduce_chain=reduce_chain,
|
||||
reduce_chain_level=reduce_chain_level)
|
||||
|
||||
def _differentiate_burnable_mats(self):
|
||||
"""Assign distribmats for each burnable material"""
|
||||
|
|
@ -278,19 +286,30 @@ class CoupledOperator(OpenMCOperator):
|
|||
[mat for mat in self.materials
|
||||
if mat.depletable and mat.num_instances > 1])
|
||||
|
||||
for mat in distribmats:
|
||||
if mat.volume is None:
|
||||
raise RuntimeError("Volume not specified for depletable "
|
||||
"material with ID={}.".format(mat.id))
|
||||
mat.volume /= mat.num_instances
|
||||
if self.diff_volume_method == 'divide equally':
|
||||
for mat in distribmats:
|
||||
if mat.volume is None:
|
||||
raise RuntimeError("Volume not specified for depletable "
|
||||
f"material with ID={mat.id}.")
|
||||
mat.volume /= mat.num_instances
|
||||
|
||||
if distribmats:
|
||||
# Assign distribmats to cells
|
||||
for cell in self.geometry.get_all_material_cells().values():
|
||||
if cell.fill in distribmats:
|
||||
mat = cell.fill
|
||||
cell.fill = [mat.clone()
|
||||
for i in range(cell.num_instances)]
|
||||
if self.diff_volume_method == 'divide equally':
|
||||
cell.fill = [mat.clone() for _ in range(cell.num_instances)]
|
||||
elif self.diff_volume_method == 'match cell':
|
||||
for _ in range(cell.num_instances):
|
||||
cell.fill = mat.clone()
|
||||
if not cell.volume:
|
||||
raise ValueError(
|
||||
f"Volume of cell ID={cell.id} not specified. "
|
||||
"Set volumes of cells prior to using "
|
||||
"diff_volume_method='match cell'."
|
||||
)
|
||||
cell.fill.volume = cell.volume
|
||||
|
||||
self.materials = openmc.Materials(
|
||||
self.model.geometry.get_all_materials().values()
|
||||
|
|
|
|||
|
|
@ -148,10 +148,10 @@ class IndependentOperator(OpenMCOperator):
|
|||
|
||||
self.fluxes = fluxes
|
||||
super().__init__(
|
||||
materials,
|
||||
micros,
|
||||
chain_file,
|
||||
prev_results,
|
||||
materials=materials,
|
||||
cross_sections=micros,
|
||||
chain_file=chain_file,
|
||||
prev_results=prev_results,
|
||||
fission_q=fission_q,
|
||||
helper_kwargs=helper_kwargs,
|
||||
reduce_chain=reduce_chain,
|
||||
|
|
|
|||
|
|
@ -12,6 +12,7 @@ from typing import List, Tuple, Dict
|
|||
import numpy as np
|
||||
|
||||
import openmc
|
||||
from openmc.checkvalue import check_value
|
||||
from openmc.exceptions import DataError
|
||||
from openmc.mpi import comm
|
||||
from .abc import TransportOperator, OperatorResult
|
||||
|
|
@ -45,7 +46,6 @@ class OpenMCOperator(TransportOperator):
|
|||
in the previous results.
|
||||
diff_burnable_mats : bool, optional
|
||||
Whether to differentiate burnable materials with multiple instances.
|
||||
Volumes are divided equally from the original material volume.
|
||||
fission_q : dict, optional
|
||||
Dictionary of nuclides and their fission Q values [eV].
|
||||
helper_kwargs : dict
|
||||
|
|
@ -58,6 +58,14 @@ class OpenMCOperator(TransportOperator):
|
|||
if ``reduce_chain`` evaluates to true. The default value of
|
||||
``None`` implies no limit on the depth.
|
||||
|
||||
diff_volume_method : str
|
||||
Specifies how the volumes of the new materials should be found. Default
|
||||
is to 'divide equally' which divides the original material volume
|
||||
equally between the new materials, 'match cell' sets the volume of the
|
||||
material to volume of the cell they fill.
|
||||
|
||||
.. versionadded:: 0.13.4
|
||||
|
||||
Attributes
|
||||
----------
|
||||
materials : openmc.Materials
|
||||
|
|
@ -97,6 +105,7 @@ class OpenMCOperator(TransportOperator):
|
|||
chain_file=None,
|
||||
prev_results=None,
|
||||
diff_burnable_mats=False,
|
||||
diff_volume_method='divide equally',
|
||||
fission_q=None,
|
||||
helper_kwargs=None,
|
||||
reduce_chain=False,
|
||||
|
|
@ -116,6 +125,10 @@ class OpenMCOperator(TransportOperator):
|
|||
self.materials = materials
|
||||
self.cross_sections = cross_sections
|
||||
|
||||
check_value('diff volume method', diff_volume_method,
|
||||
{'divide equally', 'match cell'})
|
||||
self.diff_volume_method = diff_volume_method
|
||||
|
||||
# Reduce the chain to only those nuclides present
|
||||
if reduce_chain:
|
||||
init_nuclides = set()
|
||||
|
|
|
|||
|
|
@ -11,6 +11,7 @@ import numpy as np
|
|||
|
||||
CHAIN_PATH = Path(__file__).parents[1] / "chain_simple.xml"
|
||||
|
||||
|
||||
@pytest.fixture(scope="module")
|
||||
def model():
|
||||
fuel = openmc.Material(name="uo2")
|
||||
|
|
@ -48,8 +49,72 @@ def model():
|
|||
|
||||
return openmc.Model(geometry, materials, settings)
|
||||
|
||||
|
||||
@pytest.fixture()
|
||||
def model_with_volumes():
|
||||
mat1 = openmc.Material()
|
||||
mat1.add_element("Ag", 1, percent_type="ao")
|
||||
mat1.set_density("g/cm3", 10.49)
|
||||
mat1.depletable = True
|
||||
mat1.volume = 102
|
||||
|
||||
mat2 = openmc.Material()
|
||||
mat2.add_element("Ag", 1, percent_type="ao")
|
||||
mat2.set_density("g/cm3", 10.49)
|
||||
|
||||
sph1 = openmc.Sphere(r=1.0)
|
||||
sph2 = openmc.Sphere(r=2.0, x0=3)
|
||||
sph3 = openmc.Sphere(r=5.0, boundary_type="vacuum")
|
||||
|
||||
cell1 = openmc.Cell(region=-sph1, fill=mat1)
|
||||
cell1.volume = 4.19
|
||||
cell2 = openmc.Cell(region=-sph2, fill=mat1)
|
||||
cell2.volume = 33.51
|
||||
cell3 = openmc.Cell(region=-sph3 & +sph1 & +sph2, fill=mat2)
|
||||
cell3.volume = 485.9
|
||||
|
||||
geometry = openmc.Geometry([cell1, cell2, cell3])
|
||||
|
||||
return openmc.Model(geometry)
|
||||
|
||||
|
||||
def test_operator_init(model):
|
||||
"""The test uses a temporary dummy chain. This file will be removed
|
||||
at the end of the test, and only contains a depletion_chain node."""
|
||||
|
||||
CoupledOperator(model, CHAIN_PATH)
|
||||
|
||||
|
||||
def test_diff_volume_method_match_cell(model_with_volumes):
|
||||
"""Tests the volumes assigned to the materials match the cell volumes"""
|
||||
|
||||
operator = openmc.deplete.CoupledOperator(
|
||||
model=model_with_volumes,
|
||||
diff_burnable_mats=True,
|
||||
diff_volume_method='match cell',
|
||||
chain_file=CHAIN_PATH
|
||||
)
|
||||
|
||||
all_cells = list(operator.geometry.get_all_cells().values())
|
||||
assert all_cells[0].fill.volume == 4.19
|
||||
assert all_cells[1].fill.volume == 33.51
|
||||
# mat2 is not depletable
|
||||
assert all_cells[2].fill.volume is None
|
||||
|
||||
|
||||
def test_diff_volume_method_divide_equally(model_with_volumes):
|
||||
"""Tests the volumes assigned to the materials are divided equally"""
|
||||
|
||||
operator = openmc.deplete.CoupledOperator(
|
||||
model=model_with_volumes,
|
||||
diff_burnable_mats=True,
|
||||
diff_volume_method='divide equally',
|
||||
chain_file=CHAIN_PATH
|
||||
)
|
||||
|
||||
all_cells = list(operator.geometry.get_all_cells().values())
|
||||
assert all_cells[0].fill[0].volume == 51
|
||||
assert all_cells[1].fill[0].volume == 51
|
||||
# mat2 is not depletable
|
||||
assert all_cells[2].fill.volume is None
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue