24 "NumberSciSourcesMetricTask",
"NumberSciSourcesMetricConfig",
25 "FractionDiaSourcesToSciSourcesMetricTask",
"FractionDiaSourcesToSciSourcesMetricConfig",
29 import astropy.units
as u
32 from lsst.verify
import Measurement
33 from lsst.verify.gen2tasks
import register
34 from lsst.verify.tasks
import MetricTask, MetricConfig, MetricConnections, \
35 MetricComputationError
40 defaultTemplates={
"package":
"ip_diffim",
41 "metric":
"numSciSources"},
42 dimensions={
"Instrument",
"Exposure",
"Detector"},
44 sources = connectionTypes.Input(
45 doc=
"The catalog of science sources.",
47 storageClass=
"SourceCatalog",
48 dimensions={
"Instrument",
"Exposure",
"Detector"},
52 class NumberSciSourcesMetricConfig(
54 pipelineConnections=NumberSciSourcesMetricConnections):
59 class NumberSciSourcesMetricTask(MetricTask):
60 """Task that computes the number of cataloged science sources.
62 _DefaultName =
"numSciSources"
63 ConfigClass = NumberSciSourcesMetricConfig
65 def run(self, sources):
66 """Count the number of science sources.
70 sources : `lsst.afw.table.SourceCatalog` or `None`
71 A science source catalog, which may be empty or `None`.
75 result : `lsst.pipe.base.Struct`
76 A `~lsst.pipe.base.Struct` containing the following component:
79 the total number of science sources (`lsst.verify.Measurement`
82 if sources
is not None:
83 nSciSources = len(sources)
84 meas = Measurement(self.config.metricName, nSciSources * u.count)
86 self.log.
info(
"Nothing to do: no catalogs found.")
88 return Struct(measurement=meas)
91 class FractionDiaSourcesToSciSourcesMetricConnections(
92 MetricTask.ConfigClass.ConnectionsClass,
93 dimensions={
"Instrument",
"Exposure",
"Detector"},
94 defaultTemplates={
"coaddName":
"deep",
95 "package":
"ip_diffim",
96 "metric":
"fracDiaSourcesToSciSources"}):
97 sciSources = connectionTypes.Input(
98 doc=
"The catalog of science sources.",
100 storageClass=
"SourceCatalog",
101 dimensions={
"Instrument",
"Exposure",
"Detector"},
103 diaSources = connectionTypes.Input(
104 doc=
"The catalog of DIASources.",
105 name=
"{coaddName}Diff_diaSrc",
106 storageClass=
"SourceCatalog",
107 dimensions={
"Instrument",
"Exposure",
"Detector"},
111 class FractionDiaSourcesToSciSourcesMetricConfig(
112 MetricTask.ConfigClass,
113 pipelineConnections=FractionDiaSourcesToSciSourcesMetricConnections):
117 @
register(
"fracDiaSourcesToSciSources")
118 class FractionDiaSourcesToSciSourcesMetricTask(MetricTask):
119 """Task that computes the ratio of difference image sources to science
120 sources in an image, visit, etc.
122 _DefaultName =
"fracDiaSourcesToSciSources"
123 ConfigClass = FractionDiaSourcesToSciSourcesMetricConfig
125 def run(self, sciSources, diaSources):
126 """Compute the ratio of DIASources to science sources.
130 sciSources : `lsst.afw.table.SourceCatalog` or `None`
131 A science source catalog, which may be empty or `None`.
132 diaSources : `lsst.afw.table.SourceCatalog` or `None`
133 A DIASource catalog for the same unit of processing
138 result : `lsst.pipe.base.Struct`
139 A `~lsst.pipe.base.Struct` containing the following component:
142 the ratio (`lsst.verify.Measurement` or `None`)
144 if diaSources
is not None and sciSources
is not None:
145 nSciSources = len(sciSources)
146 nDiaSources = len(diaSources)
147 metricName = self.config.metricName
148 if nSciSources <= 0.0:
149 raise MetricComputationError(
150 "No science sources found; ratio of DIASources to science sources ill-defined.")
152 meas = Measurement(metricName, nDiaSources / nSciSources * u.dimensionless_unscaled)
154 self.log.
info(
"Nothing to do: no catalogs found.")
156 return Struct(measurement=meas)