Coverage for tests/test_detection.py: 20%
84 statements
« prev ^ index » next coverage.py v7.1.0, created at 2023-02-05 18:13 -0800
« prev ^ index » next coverage.py v7.1.0, created at 2023-02-05 18:13 -0800
1#
2# LSST Data Management System
3#
4# Copyright 2008-2016 AURA/LSST.
5#
6# This product includes software developed by the
7# LSST Project (http://www.lsst.org/).
8#
9# This program is free software: you can redistribute it and/or modify
10# it under the terms of the GNU General Public License as published by
11# the Free Software Foundation, either version 3 of the License, or
12# (at your option) any later version.
13#
14# This program is distributed in the hope that it will be useful,
15# but WITHOUT ANY WARRANTY; without even the implied warranty of
16# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17# GNU General Public License for more details.
18#
19# You should have received a copy of the LSST License Statement and
20# the GNU General Public License along with this program. If not,
21# see <https://www.lsstcorp.org/LegalNotices/>.
22#
23import unittest
24import numpy as np
26import lsst.geom
27import lsst.afw.table as afwTable
28import lsst.afw.image as afwImage
29from lsst.meas.algorithms import SourceDetectionTask
30from lsst.meas.algorithms.testUtils import plantSources
31import lsst.utils.tests
33display = False
36class DetectionTestCase(lsst.utils.tests.TestCase):
37 """Test the aperture correction."""
39 def testBasics(self):
40 bbox = lsst.geom.Box2I(lsst.geom.Point2I(256, 100), lsst.geom.Extent2I(128, 127))
41 minCounts = 5000
42 maxCounts = 50000
43 starSigma = 1.5
44 numX = 5
45 numY = 5
46 coordList = self.makeCoordList(
47 bbox=bbox,
48 numX=numX,
49 numY=numY,
50 minCounts=minCounts,
51 maxCounts=maxCounts,
52 sigma=starSigma,
53 )
54 kwid = 11
55 sky = 2000
56 addPoissonNoise = True
57 exposure = plantSources(bbox=bbox, kwid=kwid, sky=sky, coordList=coordList,
58 addPoissonNoise=addPoissonNoise)
60 schema = afwTable.SourceTable.makeMinimalSchema()
61 config = SourceDetectionTask.ConfigClass()
62 config.reEstimateBackground = False
63 task = SourceDetectionTask(config=config, schema=schema)
64 for doSmooth in (False, True):
65 taskSigma = 2.2
66 res = task.detectFootprints(exposure, doSmooth=doSmooth, sigma=taskSigma)
67 self.assertEqual(res.numPos, numX * numY)
68 self.assertEqual(res.numNeg, 0)
69 self.assertEqual(task.metadata.getScalar("sigma"), taskSigma)
70 self.assertEqual(task.metadata.getScalar("doSmooth"), doSmooth)
71 self.assertEqual(task.metadata.getScalar("nGrow"), int(taskSigma * config.nSigmaToGrow + 0.5))
73 res = task.detectFootprints(exposure, doSmooth=doSmooth, sigma=None)
74 taskSigma = task.metadata.getScalar("sigma")
75 self.assertLess(abs(taskSigma - starSigma), 0.1)
76 self.assertEqual(res.numPos, numX * numY)
77 self.assertEqual(res.numNeg, 0)
79 def makeCoordList(self, bbox, numX, numY, minCounts, maxCounts, sigma):
80 """Make a coordList for plantSources."""
81 """
82 Coords are uniformly spaced in a rectangular grid, with linearly increasing counts
83 """
84 dX = bbox.getWidth() / float(numX)
85 dY = bbox.getHeight() / float(numY)
86 minX = bbox.getMinX() + (dX / 2.0)
87 minY = bbox.getMinY() + (dY / 2.0)
88 dCounts = (maxCounts - minCounts) / (numX * numY - 1)
90 coordList = []
91 counts = minCounts
92 for i in range(numX):
93 x = minX + (dX * i)
94 for j in range(numY):
95 y = minY + (dY * j)
96 coordList.append([x, y, counts, sigma])
97 counts += dCounts
98 return coordList
100 def testTempBackgrounds(self):
101 """Test that the temporary backgrounds we remove are properly restored"""
102 bbox = lsst.geom.Box2I(lsst.geom.Point2I(12345, 67890), lsst.geom.Extent2I(128, 127))
103 original = afwImage.ExposureF(bbox)
104 rng = np.random.RandomState(123)
105 original.image.array[:] = rng.normal(size=original.image.array.shape)
106 original.mask.set(0)
107 original.variance.set(1.0)
109 def checkExposure(original, doTempLocalBackground, doTempWideBackground):
110 config = SourceDetectionTask.ConfigClass()
111 config.reEstimateBackground = False
112 config.thresholdType = "pixel_stdev"
113 config.doTempLocalBackground = doTempLocalBackground
114 config.doTempWideBackground = doTempWideBackground
115 schema = afwTable.SourceTable.makeMinimalSchema()
116 task = SourceDetectionTask(config=config, schema=schema)
118 exposure = original.clone()
119 task.detectFootprints(exposure, sigma=3.21)
121 self.assertFloatsEqual(exposure.image.array, original.image.array)
122 # Mask is permitted to vary: DETECTED bit gets set
123 self.assertFloatsEqual(exposure.variance.array, original.variance.array)
125 checkExposure(original, False, False)
126 checkExposure(original, True, False)
127 checkExposure(original, False, True)
128 checkExposure(original, True, True)
131class TestMemory(lsst.utils.tests.MemoryTestCase):
132 pass
135def setup_module(module):
136 lsst.utils.tests.init()
139if __name__ == "__main__": 139 ↛ 140line 139 didn't jump to line 140, because the condition on line 139 was never true
140 lsst.utils.tests.init()
141 unittest.main()