22 from __future__
import absolute_import, division, print_function
24 __all__ = [
'RefMatchConfig',
'RefMatchTask']
29 import lsst.pipe.base
as pipeBase
30 from lsst.meas.algorithms
import ScienceSourceSelectorTask, ReferenceSourceSelectorTask
31 from .matchOptimisticB
import MatchOptimisticBTask
32 from .display
import displayAstrometry
33 from .
import makeMatchStatistics
37 matcher = pexConfig.ConfigurableField(
38 target=MatchOptimisticBTask,
39 doc=
"reference object/source matcher",
41 matchDistanceSigma = pexConfig.RangeField(
42 doc=
"the maximum match distance is set to " 43 " mean_match_distance + matchDistanceSigma*std_dev_match_distance; " +
44 "ignored if not fitting a WCS",
49 sourceSelection = pexConfig.ConfigurableField(target=ScienceSourceSelectorTask,
50 doc=
"Selection of science sources")
51 referenceSelection = pexConfig.ConfigurableField(target=ReferenceSourceSelectorTask,
52 doc=
"Selection of reference sources")
64 """!Match an input source catalog with objects from a reference catalog 68 ConfigClass = RefMatchConfig
69 _DefaultName =
"calibrationBaseClass" 71 def __init__(self, refObjLoader, schema=None, **kwargs):
72 """!Construct a RefMatchTask 74 @param[in] refObjLoader A reference object loader object 75 @param[in] schema ignored; available for compatibility with an older astrometry task 76 @param[in] kwargs additional keyword arguments for pipe_base Task.\_\_init\_\_ 78 pipeBase.Task.__init__(self, **kwargs)
80 self.makeSubtask(
"matcher")
81 self.makeSubtask(
"sourceSelection")
82 self.makeSubtask(
"referenceSelection")
86 """!Load reference objects overlapping an exposure and match to sources detected on that exposure 88 @param[in] exposure exposure that the sources overlap 89 @param[in] sourceCat catalog of sources detected on the exposure (an lsst.afw.table.SourceCatalog) 91 @return an lsst.pipe.base.Struct with these fields: 92 - refCat reference object catalog of objects that overlap the exposure (with some margin) 93 (an lsst::afw::table::SimpleCatalog) 94 - matches a list of lsst.afw.table.ReferenceMatch 95 - matchMeta metadata needed to unpersist matches (an lsst.daf.base.PropertyList) 97 @note ignores config.matchDistanceSigma 104 sourceSelection = self.sourceSelection.selectSources(sourceCat)
109 filterName=expMd.filterName,
113 refSelection = self.referenceSelection.selectSources(loadRes.refCat)
118 filterName=expMd.filterName,
122 matchRes = self.matcher.matchObjectsToSources(
123 refCat=refSelection.sourceCat,
124 sourceCat=sourceSelection.sourceCat,
126 refFluxField=loadRes.fluxField,
127 match_tolerance=
None,
132 "Found %d matches with scatter = %0.3f +- %0.3f arcsec; " %
133 (len(matchRes.matches), distStats.distMean.asArcseconds(), distStats.distStdDev.asArcseconds())
137 frame = int(debug.frame)
139 refCat=refSelection.sourceCat,
140 sourceCat=sourceSelection.sourceCat,
141 matches=matchRes.matches,
148 return pipeBase.Struct(
149 refCat=loadRes.refCat,
150 refSelection=refSelection,
151 sourceSelection=sourceSelection,
152 matches=matchRes.matches,
156 def _computeMatchStatsOnSky(self, matchList):
157 """Compute on-sky radial distance statistics for a match list 159 @param[in] matchList list of matches between reference object and sources; 160 the distance field is the only field read and it must be set to distance in radians 162 @return a pipe_base Struct containing these fields: 163 - distMean clipped mean of on-sky radial separation 164 - distStdDev clipped standard deviation of on-sky radial separation 165 - maxMatchDist distMean + self.config.matchDistanceSigma*distStdDev 168 distMean = distStatsInRadians.getValue(afwMath.MEANCLIP)*afwGeom.radians
169 distStdDev = distStatsInRadians.getValue(afwMath.STDEVCLIP)*afwGeom.radians
170 return pipeBase.Struct(
172 distStdDev=distStdDev,
173 maxMatchDist=distMean + self.config.matchDistanceSigma*distStdDev,
176 def _getExposureMetadata(self, exposure):
177 """!Extract metadata from an exposure 179 @return an lsst.pipe.base.Struct containing the following exposure metadata: 180 - bbox: parent bounding box 181 - wcs: WCS (an lsst.afw.geom.Wcs) 182 - calib calibration (an lsst.afw.image.Calib), or None if unknown 183 - filterName: name of filter, or None if unknown 185 exposureInfo = exposure.getInfo()
186 filterName = exposureInfo.getFilter().getName()
or None 187 if filterName ==
"_unknown_":
189 return pipeBase.Struct(
190 bbox=exposure.getBBox(),
191 wcs=exposureInfo.getWcs(),
192 calib=exposureInfo.getCalib()
if exposureInfo.hasCalib()
else None,
193 filterName=filterName,
def _computeMatchStatsOnSky(self, matchList)
def __init__(self, refObjLoader, schema=None, kwargs)
Construct a RefMatchTask.
def _getExposureMetadata(self, exposure)
Extract metadata from an exposure.
Match an input source catalog with objects from a reference catalog.
def displayAstrometry(refCat=None, sourceCat=None, distortedCentroidKey=None, bbox=None, exposure=None, matches=None, frame=1, title="", pause=True)
def loadAndMatch(self, exposure, sourceCat)
Load reference objects overlapping an exposure and match to sources detected on that exposure...