Skip to content

Commit

Permalink
Raise error when data is insufficient
Browse files Browse the repository at this point in the history
  • Loading branch information
cmsaunders committed Dec 4, 2023
1 parent 44a7e41 commit 30a98e8
Showing 1 changed file with 66 additions and 1 deletion.
67 changes: 66 additions & 1 deletion python/lsst/drp/tasks/gbdesAstrometricFit.py
Original file line number Diff line number Diff line change
Expand Up @@ -436,6 +436,11 @@ def run(
``outputCatalog`` : `pyarrow.Table`
Catalog with fit residuals of all sources used.
"""
if (len(inputVisitSummaries) == 1) and (self.config.deviceModel and self.config.exposureModel):
raise RuntimeError(
"More than one exposure is necessary to break the degeneracy between the"
" device model and the exposure model."
)
self.log.info("Gathering instrument, exposure, and field info")
# Set up an instrument object
instrument = wcsfit.Instrument(instrumentName)
Expand Down Expand Up @@ -469,6 +474,7 @@ def run(
sourceIndices, usedColumns = self._load_catalogs_and_associate(
associations, inputCatalogRefs, extensionInfo
)
self._check_degeneracies(associations, extensionInfo)

self.log.info("Fit the WCSs")
# Set up a YAML-type string using the config variables and a sample
Expand Down Expand Up @@ -854,7 +860,8 @@ class `wcsfit.FoFClass`, associating them into matches as you go.
Parameters
----------
associations : `wcsfit.FoFClass`
Object to which to add the catalog of reference objects.
Object to which to add the catalog of source and which performs
the source association.
inputCatalogRefs : `list`
List of DeferredDatasetHandles pointing to visit-level source
tables.
Expand Down Expand Up @@ -948,6 +955,64 @@ class `wcsfit.FoFClass`, associating them into matches as you go.

return sourceIndices, columns

def _check_degeneracies(self, associations, extensionInfo):
"""Check that the minimum number of visits and sources needed to
constrain the model are present.
This does not guarantee that the Hessian matrix of the chi-square,
which is used to fit the model, will be positive-definite, but if the
checks here do not pass, the matrix is certain to not be
positive-definite and the model cannot be fit.
Parameters
----------
associations : `wcsfit.FoFClass`
Object holding the source association information.
extensionInfo : `lsst.pipe.base.Struct`
Struct containing properties for each extension.
"""
# As a baseline, need to have more stars per detector than per-detector
# parameters, and more stars per visit than per-visit parameters.
whichExtension = np.array(associations.extn)
whichDetector = np.zeros(len(whichExtension))
whichVisit = np.zeros(len(whichExtension))

for extension, (detector, visit) in enumerate(zip(extensionInfo.detector, extensionInfo.visit)):
ex_ind = whichExtension == extension
whichDetector[ex_ind] = detector
whichVisit[ex_ind] = visit

nCoeffVisitModel = int(((2 * self.config.exposurePolyOrder + 3) ** 2 - 1) / 8)

if "BAND/DEVICE/poly" in self.config.deviceModel:
nCoeffDetectorModel = int(((2 * self.config.devicePolyOrder + 3) ** 2 - 1) / 8)
unconstrainedDetectors = []
for detector in np.unique(extensionInfo.detector):
numSources = (whichDetector == detector).sum()
if numSources < nCoeffDetectorModel:
unconstrainedDetectors.append(str(detector))

if unconstrainedDetectors:
raise RuntimeError(
"The model is not constrained. The following detectors do not have enough "
f"sources ({nCoeffDetectorModel} required): " + ", ".join(unconstrainedDetectors)
)

if "EXPOSURE/poly" in self.config.exposureModel:
nCoeffVisitModel = int(((2 * self.config.exposurePolyOrder + 3) ** 2 - 1) / 8)

unconstrainedVisits = []
for visit in np.unique(extensionInfo.visit):
numSources = (whichVisit == visit).sum()
if numSources < nCoeffVisitModel:
unconstrainedVisits.append(str(visit))

if unconstrainedVisits:
raise RuntimeError(
"The model is not constrained. The following visits do not have enough "
f"sources ({nCoeffVisitModel} required):" + ", ".join(unconstrainedVisits)
)

def make_yaml(self, inputVisitSummary, inputFile=None):
"""Make a YAML-type object that describes the parameters of the fit
model.
Expand Down

0 comments on commit 30a98e8

Please sign in to comment.