Skip to content
Snippets Groups Projects
Commit 4c87d005 authored by Kevin Kuns's avatar Kevin Kuns
Browse files

make BudgetItem.freq a property; setter recurses and clears precomp cache

parent c606f75b
No related branches found
No related tags found
No related merge requests found
Pipeline #337957 passed
......@@ -44,8 +44,8 @@ def freq_from_spec(spec=None):
return spec
elif spec is None:
spec = DEFAULT_FREQ
fspec = spec.split(':')
try:
fspec = spec.split(':')
if len(fspec) == 2:
fspec = fspec[0], DEFAULT_FREQ.split(':')[1], fspec[1]
return np.logspace(
......@@ -53,7 +53,7 @@ def freq_from_spec(spec=None):
np.log10(float(fspec[2])),
int(fspec[1]),
)
except (ValueError, IndexError):
except (ValueError, IndexError, AttributeError):
raise InvalidFrequencySpec(f'Improper frequency specification: {spec}')
......@@ -154,7 +154,7 @@ def load_budget(name_or_path, freq=None, bname=None):
mod, modpath = load_module(modname)
Budget = getattr(mod, bname)
if freq is None:
freq = getattr(Budget, 'freq', None)
freq = getattr(Budget, '_freq', None)
freq = freq_from_spec(freq)
ifopath = os.path.join(modpath, 'ifo.yaml')
if not ifo and os.path.exists(ifopath):
......
......@@ -139,9 +139,8 @@ class BudgetItem:
variables to the initialized object.
"""
if freq is not None:
assert isinstance(freq, np.ndarray)
self.freq = freq
assert isinstance(freq, np.ndarray) or freq is None
self._freq = freq
self.ifo = None
for key, val in kwargs.items():
setattr(self, key, val)
......@@ -153,6 +152,20 @@ class BudgetItem:
""""Name of this BudgetItem class."""
return self.__class__.__name__
@property
def freq(self):
"""Frequency array [Hz]"""
return self._freq
@freq.setter
def freq(self, val):
assert isinstance(val, np.ndarray)
# clear the precomp cache
self._precomp = dict()
# use update instead of setting _freq directly so that Budget.update
# recurses through all cal_objs and noise_objs
self.update(_freq=val)
def __str__(self):
# FIXME: provide info on internal state (load/update/calc/etc.)
return '<{} {}>'.format(
......@@ -353,7 +366,7 @@ class Budget(Noise):
if freq is not None:
self.kwargs['freq'] = freq
else:
self.kwargs['freq'] = getattr(self, 'freq', None)
self.kwargs['freq'] = getattr(self, '_freq', None)
# FIXME: special casing the ifo kwarg here, in case it's
# defined as a class attribute rather than passed at
# initialization. we do this because we're not defining a
......@@ -498,7 +511,7 @@ class Budget(Noise):
logger.debug("load {}".format(item))
item.load()
def update(self, _precomp=None, **kwargs):
def update(self, **kwargs):
"""Recursively update all noise and cal objects with supplied kwargs.
See BudgetItem.update() for more info.
......
......@@ -47,3 +47,39 @@ def test_change_ifo_struct():
assert np.all(
tr2.Seismic.SeismicVertical.asd == 2*tr1.Seismic.SeismicVertical.asd)
@pytest.mark.logic
@pytest.mark.fast
def test_update_freq():
"""
Test three methods of updating a Budget frequency
"""
freq1 = np.logspace(1, 3, 10)
freq2 = np.logspace(0.8, 3.5, 11)
freq3 = np.logspace(0.5, 3.6, 12)
budget = gwinc.load_budget('Aplus', freq=freq1)
traces1 = budget.run()
traces2 = budget.run(freq=freq2)
budget.freq = freq3
traces3 = budget.run()
assert np.all(traces1.freq == freq1)
assert np.all(traces2.freq == freq2)
assert np.all(traces3.freq == freq3)
@pytest.mark.logic
@pytest.mark.fast
def test_freq_spec_error():
"""
Test that three methods of setting Budget frequencies raise errors
"""
freq = [1, 2, 3]
with pytest.raises(gwinc.InvalidFrequencySpec):
budget = gwinc.load_budget('Aplus', freq=freq)
with pytest.raises(AssertionError):
budget = gwinc.load_budget('Aplus')
traces = budget.run(freq=freq)
with pytest.raises(AssertionError):
budget = gwinc.load_budget('Aplus')
budget.freq = freq
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment