Tally merging now consolidates moment scores

This commit is contained in:
Will Boyd 2017-03-08 14:23:49 -05:00
parent 23e0207ff2
commit 0c3e586dd2
3 changed files with 126 additions and 17 deletions

View file

@ -1089,8 +1089,8 @@ class Library(object):
using_multiplicity = True
# multiplicity will fall back to using scatter and nu-scatter
elif ((('scatter matrix' in self.mgxs_types) and
('nu-scatter matrix' in self.mgxs_types))):
elif 'scatter matrix' in self.mgxs_types and \
'nu-scatter matrix' in self.mgxs_types:
scatt_mgxs = self.get_mgxs(domain, 'scatter matrix')
nuscatt_mgxs = self.get_mgxs(domain, 'nu-scatter matrix')
xsdata.set_multiplicity_matrix_mgxs(nuscatt_mgxs, scatt_mgxs,
@ -1099,17 +1099,38 @@ class Library(object):
subdomain=subdomain)
using_multiplicity = True
# multiplicity will fall back to using scatter and nu-scatter
elif 'consistent scatter matrix' in self.mgxs_types and \
'consistent nu-scatter matrix' in self.mgxs_types:
scatt_mgxs = self.get_mgxs(domain, 'consistent scatter matrix')
nuscatt_mgxs = \
self.get_mgxs(domain, 'consistent nu-scatter matrix')
xsdata.set_multiplicity_matrix_mgxs(nuscatt_mgxs, scatt_mgxs,
xs_type=xs_type,
nuclide=[nuclide],
subdomain=subdomain)
using_multiplicity = True
else:
using_multiplicity = False
if using_multiplicity:
nuscatt_mgxs = self.get_mgxs(domain, 'nu-scatter matrix')
if 'nu-scatter matrix' in self.mgxs_types:
nuscatt_mgxs = self.get_mgxs(domain, 'nu-scatter matrix')
else:
nuscatt_mgxs = \
self.get_mgxs(domain, 'consistent nu-scatter matrix')
xsdata.set_scatter_matrix_mgxs(nuscatt_mgxs, xs_type=xs_type,
nuclide=[nuclide],
subdomain=subdomain)
else:
if 'nu-scatter matrix' in self.mgxs_types:
nuscatt_mgxs = self.get_mgxs(domain, 'nu-scatter matrix')
if 'nu-scatter matrix' in self.mgxs_types or \
'consistent nu-scatter matrix' in self.mgxs_types:
if 'nu-scatter matrix' in self.mgxs_types:
nuscatt_mgxs = self.get_mgxs(domain, 'nu-scatter matrix')
else:
nuscatt_mgxs = \
self.get_mgxs(domain, 'consistent nu-scatter matrix')
xsdata.set_scatter_matrix_mgxs(nuscatt_mgxs, xs_type=xs_type,
nuclide=[nuclide],
subdomain=subdomain)
@ -1409,13 +1430,15 @@ class Library(object):
error_flag = True
warn('An "absorption" MGXS type is required but not provided.')
# Ensure nu-scattering matrix is required
if 'nu-scatter matrix' not in self.mgxs_types:
if 'nu-scatter matrix' not in self.mgxs_types and \
'consistent nu-scatter matrix' not in self.mgxs_types:
error_flag = True
warn('A "nu-scatter matrix" MGXS type is required but not provided.')
else:
# Ok, now see the status of scatter and/or multiplicity
if ((('scatter matrix' not in self.mgxs_types) and
('multiplicity matrix' not in self.mgxs_types))):
if 'scatter matrix' not in self.mgxs_types or \
'consistent scatter matrix' not in self.mgxs_types and \
'multiplicity matrix' not in self.mgxs_types:
# We dont have data needed for multiplicity matrix, therefore
# we need total, and not transport.
if 'total' not in self.mgxs_types:
@ -1424,14 +1447,12 @@ class Library(object):
'scattering matrix is not provided.')
# Total or transport can be present, but if using
# self.correction=="P0", then we should use transport.
if (((self.correction == "P0") and
('nu-transport' not in self.mgxs_types))):
if self.correction == "P0" and 'nu-transport' not in self.mgxs_types:
error_flag = True
warn('A "nu-transport" MGXS type is required since a "P0" '
'correction is applied, but a "nu-transport" MGXS is '
'not provided.')
elif (((self.correction is None) and
('total' not in self.mgxs_types))):
elif self.correction is None and 'total' not in self.mgxs_types:
error_flag = True
warn('A "total" MGXS type is required, but not provided.')

View file

@ -2747,8 +2747,18 @@ class TransportXS(MGXS):
@property
def rxn_rate_tally(self):
raise NotImplementedError('The reaction rate tally is poorly defined' \
' for the transport cross section')
if self._rxn_rate_tally is None:
# Switch EnergyoutFilter to EnergyFilter.
old_filt = self.tallies['scatter-1'].filters[-1]
new_filt = openmc.EnergyFilter(old_filt.bins)
new_filt.stride = old_filt.stride
self.tallies['scatter-1'].filters[-1] = new_filt
self._rxn_rate_tally = \
self.tallies['total'] - self.tallies['scatter-1']
self._rxn_rate_tally.sparse = self.sparse
return self._rxn_rate_tally
@property
def xs_tally(self):

View file

@ -2,12 +2,10 @@ from __future__ import division
from collections import Iterable, MutableSequence
import copy
import re
from functools import partial
import os
import pickle
import itertools
from numbers import Integral, Real
import sys
import warnings
from xml.etree import ElementTree as ET
@ -1013,8 +1011,88 @@ class Tally(object):
# Sparsify merged tally if both tallies are sparse
merged_tally.sparse = self.sparse and other.sparse
# Consolidate scatter and flux Legendre moment scores
merged_tally._consolidate_moment_scores()
return merged_tally
def _consolidate_moment_scores(self):
"""Remove redundant scattering moment scores from a merged Tally."""
# FIXME: This should also work for flux moments
# Use regex to find (nu-)scatter-(P)n scores
scatt_n = [x for x in self.scores if
re.search(r'^((?!nu-)scatter-\d)', x)]
scatt_pn = [x for x in self.scores if
re.search(r'^((?!nu-)scatter-(P|p)\d)', x)]
nuscatt_n = [x for x in self.scores if
re.search(r'nu-scatter-\d', x)]
nuscatt_pn = [x for x in self.scores if
re.search(r'nu-scatter-(P|p)\d', x)]
flux_n = [x for x in self.scores if
re.search(r'flux-\d', x)]
flux_pn = [x for x in self.scores if
re.search(r'flux-(P|p)\d', x)]
# Find all other non-scattering moment scores
# FIXME: this should also find non-flux moment scores
scores = [x for x in self.scores if
re.search(r'^((?!scatter-).)*$', x)]
# Consolidate scatter moment scores
if len(scatt_pn) > 0:
# Only keep the highest scatter-PN score
high_pn = sorted([x.lower() for x in scatt_pn])[-1]
pn = int(high_pn.split('-')[1].replace('p', ''))
# Only keep the scatter-N scores with N > PN
scatt_n = sorted([x.lower() for x in scatt_n])
scatt_n = [x for x in scatt_n if (int(x.split('-')[1]) > pn)]
# Append highest scatter-PN and any higher scatter-N scores
scores.extend([high_pn] + scatt_n)
else:
scores.extend(scatt_n)
# Consolidate nu-scatter moment scores
if len(nuscatt_pn) > 0:
# Only keep the highest nu-scatter-PN score
high_nupn = sorted([x.lower() for x in nuscatt_pn])[-1]
pn = int(high_nupn.split('-')[1].replace('p', ''))
# Only keep the nu-scatter-N scores with N > PN
nuscatt_n = sorted([x.lower() for x in nuscatt_n])
nuscatt_n = [x for x in nuscatt_n if (int(x.split('-')[1]) > pn)]
# Append highest nu-scatter-PN and any higher nu-scatter-N scores
scores.extend([high_pn] + nuscatt_n)
else:
scores.extend(nuscatt_n)
# Consolidate flux moment scores
if len(flux_pn) > 0:
# Only keep the highest flux-PN score
high_pn = sorted([x.lower() for x in flux_pn])[-1]
pn = int(high_pn.split('-')[1].replace('p', ''))
# Only keep the flux-N scores with N > PN
flux_n = sorted([x.lower() for x in flux_n])
flux_n = [x for x in flux_n if (int(x.split('-')[1]) > pn)]
# Append highest flux_n-PN and any higher flux_n-N scores
scores.extend([high_pn] + flux_n)
else:
scores.extend(flux_n)
# Override Tally's scores with consolidated list of scores
self.scores = scores
def to_xml_element(self):
"""Return XML representation of the tally