Skip to content

Commit c1a4d43

Browse files
Add methods on Material class for waste disposal rating / classification (#3366)
Co-authored-by: Ethan Peterson <eepeterson3@gmail.com>
1 parent bd95b52 commit c1a4d43

File tree

4 files changed

+475
-8
lines changed

4 files changed

+475
-8
lines changed

openmc/material.py

Lines changed: 92 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@
1818
from ._xml import clean_indentation, reorder_attributes
1919
from .mixin import IDManagerMixin
2020
from .utility_funcs import input_path
21+
from . import waste
2122
from openmc.checkvalue import PathLike
2223
from openmc.stats import Univariate, Discrete, Mixture
2324
from openmc.data.data import _get_element_symbol
@@ -30,6 +31,7 @@
3031
# Smallest normalized floating point number
3132
_SMALLEST_NORMAL = sys.float_info.min
3233

34+
_BECQUEREL_PER_CURIE = 3.7e10
3335

3436
NuclideTuple = namedtuple('NuclideTuple', ['name', 'percent', 'percent_type'])
3537

@@ -1058,7 +1060,6 @@ def get_nuclide_atom_densities(self, nuclide: str | None = None) -> dict[str, fl
10581060
nuc_densities.append(nuc.percent)
10591061
nuc_density_types.append(nuc.percent_type)
10601062

1061-
nucs = np.array(nucs)
10621063
nuc_densities = np.array(nuc_densities)
10631064
nuc_density_types = np.array(nuc_density_types)
10641065

@@ -1137,17 +1138,16 @@ def get_element_atom_densities(self, element: str | None = None) -> dict[str, fl
11371138

11381139
def get_activity(self, units: str = 'Bq/cm3', by_nuclide: bool = False,
11391140
volume: float | None = None) -> dict[str, float] | float:
1140-
"""Returns the activity of the material or for each nuclide in the
1141-
material in units of [Bq], [Bq/g], [Bq/kg] or [Bq/cm3].
1141+
"""Returns the activity of the material or of each nuclide within.
11421142
11431143
.. versionadded:: 0.13.1
11441144
11451145
Parameters
11461146
----------
1147-
units : {'Bq', 'Bq/g', 'Bq/kg', 'Bq/cm3'}
1147+
units : {'Bq', 'Bq/g', 'Bq/kg', 'Bq/cm3', 'Ci', 'Ci/m3'}
11481148
Specifies the type of activity to return, options include total
1149-
activity [Bq], specific [Bq/g, Bq/kg] or volumetric activity
1150-
[Bq/cm3]. Default is volumetric activity [Bq/cm3].
1149+
activity [Bq,Ci], specific [Bq/g, Bq/kg] or volumetric activity
1150+
[Bq/cm3,Ci/m3]. Default is volumetric activity [Bq/cm3].
11511151
by_nuclide : bool
11521152
Specifies if the activity should be returned for the material as a
11531153
whole or per nuclide. Default is False.
@@ -1165,17 +1165,24 @@ def get_activity(self, units: str = 'Bq/cm3', by_nuclide: bool = False,
11651165
of the material is returned as a float.
11661166
"""
11671167

1168-
cv.check_value('units', units, {'Bq', 'Bq/g', 'Bq/kg', 'Bq/cm3'})
1168+
cv.check_value('units', units, {'Bq', 'Bq/g', 'Bq/kg', 'Bq/cm3', 'Ci', 'Ci/m3'})
11691169
cv.check_type('by_nuclide', by_nuclide, bool)
11701170

1171+
if volume is None:
1172+
volume = self.volume
1173+
11711174
if units == 'Bq':
1172-
multiplier = volume if volume is not None else self.volume
1175+
multiplier = volume
11731176
elif units == 'Bq/cm3':
11741177
multiplier = 1
11751178
elif units == 'Bq/g':
11761179
multiplier = 1.0 / self.get_mass_density()
11771180
elif units == 'Bq/kg':
11781181
multiplier = 1000.0 / self.get_mass_density()
1182+
elif units == 'Ci':
1183+
multiplier = volume / _BECQUEREL_PER_CURIE
1184+
elif units == 'Ci/m3':
1185+
multiplier = 1e6 / _BECQUEREL_PER_CURIE
11791186

11801187
activity = {}
11811188
for nuclide, atoms_per_bcm in self.get_nuclide_atom_densities().items():
@@ -1316,6 +1323,83 @@ def get_mass(self, nuclide: str | None = None, volume: float | None = None) -> f
13161323
raise ValueError("Volume must be set in order to determine mass.")
13171324
return volume*self.get_mass_density(nuclide)
13181325

1326+
def waste_classification(self, metal: bool = False) -> str:
1327+
"""Classify the material for near-surface waste disposal.
1328+
1329+
This method determines a waste classification for the material based on
1330+
the NRC regulations (10 CFR 61.55). Note that the NRC regulations do not
1331+
consider many long-lived radionuclides relevant to fusion systems; for
1332+
fusion applications, it is recommended to calculate a waste disposal
1333+
rating based on limits by Fetter et al. using the
1334+
:meth:`~openmc.Material.waste_disposal_rating` method.
1335+
1336+
Parameters
1337+
----------
1338+
metal : bool, optional
1339+
Whether or not the material is in metal form.
1340+
1341+
Returns
1342+
-------
1343+
str
1344+
The waste disposal classification, which can be "Class A", "Class
1345+
B", "Class C", or "GTCC" (greater than class C).
1346+
1347+
"""
1348+
return waste._waste_classification(self, metal=metal)
1349+
1350+
def waste_disposal_rating(
1351+
self,
1352+
limits: str | dict[str, float] = 'Fetter',
1353+
metal: bool = False,
1354+
) -> float:
1355+
"""Return the waste disposal rating for the material.
1356+
1357+
This method returns a waste disposal rating for the material based on a
1358+
set of specific activity limits. The waste disposal rating is a single
1359+
number that represents the sum of the ratios of the specific activity
1360+
for each radionuclide in the material against a nuclide-specific limit.
1361+
A value less than 1.0 indicates that the material "meets" the limits
1362+
whereas a value greater than 1.0 exceeds the limits.
1363+
1364+
Note that the limits for NRC do not consider many long-lived
1365+
radionuclides relevant to fusion systems. A paper by `Fetter et al.
1366+
<https://doi.org/10.1016/0920-3796(90)90104-E>`_ applies the NRC
1367+
methodology to calculate specific activity limits for an expanded set of
1368+
radionuclides.
1369+
1370+
Parameters
1371+
----------
1372+
limits : str or dict, optional
1373+
The name of a predefined set of specific activity limits or a
1374+
dictionary that contains specific activity limits for radionuclides,
1375+
where keys are nuclide names and values are activities in units of
1376+
[Ci/m3]. The predefined options are:
1377+
1378+
- 'Fetter': Uses limits from Fetter et al. (1990)
1379+
- 'NRC_long': Uses the 10 CFR 61.55 limits for long-lived
1380+
radionuclides
1381+
- 'NRC_short_A': Uses the 10 CFR 61.55 class A limits for
1382+
short-lived radionuclides
1383+
- 'NRC_short_B': Uses the 10 CFR 61.55 class B limits for
1384+
short-lived radionuclides
1385+
- 'NRC_short_C': Uses the 10 CFR 61.55 class C limits for
1386+
short-lived radionuclides
1387+
metal : bool, optional
1388+
Whether or not the material is in metal form (only applicable for
1389+
NRC based limits)
1390+
1391+
Returns
1392+
-------
1393+
float
1394+
The waste disposal rating for the material.
1395+
1396+
See also
1397+
--------
1398+
Material.waste_classification()
1399+
1400+
"""
1401+
return waste._waste_disposal_rating(self, limits, metal)
1402+
13191403
def clone(self, memo: dict | None = None) -> Material:
13201404
"""Create a copy of this material with a new unique ID.
13211405

0 commit comments

Comments
 (0)