Skip to content

Commit

Permalink
Implemented searching for materials by components.
Browse files Browse the repository at this point in the history
  • Loading branch information
MicahGale committed Sep 17, 2024
1 parent 05961d0 commit 9252022
Show file tree
Hide file tree
Showing 2 changed files with 48 additions and 23 deletions.
24 changes: 24 additions & 0 deletions montepy/data_inputs/material.py
Original file line number Diff line number Diff line change
Expand Up @@ -236,6 +236,30 @@ def add_nuclide(self, nuclide, fraction):
nuclide = Nuclide.get_from_fancy_name(nuclide)
self.append((nuclide, fraction))

def contains(self, nuclide, *args, threshold):
nuclides = []
for nuclide in [nuclide] + args:
if not isinstance(nuclide, (str, int, Element, Nucleus, Nuclide)):
raise TypeError("") # foo
if isinstance(nuclide, (str, int)):
nuclide = montepy.Nuclide.get_from_fancy_name(nuclide)
nuclides.append(nuclide)

# fail fast
for nuclide in nuclides:
if isinstance(nuclide, (Nucleus, Element)):
if nuclide not in self:
return False

# do exhaustive search
nuclides_search = {str(nuclide): False for nuclide in nuclides}

for nuclide, fraction in self:
if str(nuclide) in nuclides_search:
if fraction >= threshold:
nuclides_search[str(nuclide)] = True
return all(nuclide_search)

def __prep_element_filter(self, filter_obj):
if isinstance(filter_obj, "str"):
filter_obj = Element.get_by_symbol(filter_obj).Z
Expand Down
47 changes: 24 additions & 23 deletions montepy/materials.py
Original file line number Diff line number Diff line change
Expand Up @@ -20,27 +20,28 @@ class Materials(NumberedDataObjectCollection):
def __init__(self, objects=None, problem=None):
super().__init__(Material, objects, problem)


def __create_mat_generator(element):
""" """

def closure(obj):
for material in obj:
if element in material:
def get_containing(self, nuclide, *args, threshold=0.0):
""" """
nuclides = []
for nuclide in [nuclide] + args:
if not isinstance(nuclide, (str, int, Element, Nucleus, Nuclide)):
raise TypeError("") # foo
if isinstance(nuclide, (str, int)):
nuclide = montepy.Nuclide.get_from_fancy_name(nuclide)
nuclides.append(nuclide)

def sort_by_type(nuclide):
type_map = {
montepy.data_inputs.element.Element: 0,
montepy.data_inputs.nuclide.Nucleus: 1,
montepy.data_inputs.nuclide.Nuclide: 2,
}
return type_map[type(nuclide)]

# optimize by most hashable and fail fast
nuclides = sorted(nuclides, key=sort_by_type)
for material in self:
if material.contains(*nuclides, threshold):
# maybe? Maybe not?
# should Materials act like a set?
yield material

return closure


def __setup_element_generators():
elements = [
montepy.data_inputs.element.Element(z)
for z in range(1, montepy.data_inputs.element.MAX_Z_NUM + 1)
]
for element in elements:
doc = f"Generator for all material containing element: {element.name}"
getter = property(__create_mat_generator(element), doc=doc)
setattr(Materials, element.symbol, getter)


__setup_element_generators()

0 comments on commit 9252022

Please sign in to comment.