Coverage for tests/test_chebyshevBoundedField.py: 13%

273 statements  

« prev     ^ index     » next       coverage.py v6.4, created at 2022-06-02 03:42 -0700

1# This file is part of afw. 

2# 

3# Developed for the LSST Data Management System. 

4# This product includes software developed by the LSST Project 

5# (https://www.lsst.org). 

6# See the COPYRIGHT file at the top-level directory of this distribution 

7# for details of code ownership. 

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 GNU General Public License 

20# along with this program. If not, see <https://www.gnu.org/licenses/>. 

21 

22""" 

23Tests for math.ChebyshevBoundedField 

24 

25Run with: 

26 python test_chebyshevBoundedField.py 

27or 

28 pytest test_chebyshevBoundedField.py 

29""" 

30 

31import os 

32import unittest 

33 

34import numpy as np 

35 

36import lsst.utils.tests 

37import lsst.pex.exceptions 

38import lsst.geom 

39import lsst.afw.image 

40import lsst.afw.math 

41import lsst.afw.geom 

42 

43testPath = os.path.abspath(os.path.dirname(__file__)) 

44 

45CHEBYSHEV_T = [ 45 ↛ exitline 45 didn't jump to the function exit

46 lambda x: x**0, 

47 lambda x: x, 

48 lambda x: 2*x**2 - 1, 

49 lambda x: (4*x**2 - 3)*x, 

50 lambda x: (8*x**2 - 8)*x**2 + 1, 

51 lambda x: ((16*x**2 - 20)*x**2 + 5)*x, 

52] 

53 

54 

55def multiply(image, field): 

56 """Return the product of image and field() at each point in image. 

57 """ 

58 box = image.getBBox() 

59 outImage = lsst.afw.image.ImageF(box) 

60 for i in range(box.getMinX(), box.getMaxX() + 1): 

61 for j in range(box.getMinY(), box.getMaxY() + 1): 

62 outImage[i, j] = image[i, j]*field.evaluate(i, j) 

63 return outImage 

64 

65 

66class ChebyshevBoundedFieldTestCase(lsst.utils.tests.TestCase): 

67 

68 def setUp(self): 

69 self.longMessage = True 

70 np.random.seed(5) 

71 self.bbox = lsst.geom.Box2I( 

72 lsst.geom.Point2I(-5, -5), lsst.geom.Point2I(5, 5)) 

73 self.x1d = np.linspace(self.bbox.getBeginX(), self.bbox.getEndX()) 

74 self.y1d = np.linspace(self.bbox.getBeginY(), self.bbox.getEndY()) 

75 self.x2d, self.y2d = np.meshgrid(self.x1d, self.y1d) 

76 self.xFlat = np.ravel(self.x2d) 

77 self.yFlat = np.ravel(self.y2d) 

78 self.cases = [] 

79 for orderX in range(0, 5): 

80 for orderY in range(0, 5): 

81 indexX, indexY = np.meshgrid(np.arange(orderX + 1, dtype=int), 

82 np.arange(orderY + 1, dtype=int)) 

83 for triangular in (True, False): 

84 ctrl = lsst.afw.math.ChebyshevBoundedFieldControl() 

85 ctrl.orderX = orderX 

86 ctrl.orderY = orderY 

87 ctrl.triangular = triangular 

88 coefficients = np.random.randn(orderY + 1, orderX + 1) 

89 if triangular: 

90 coefficients[indexX + indexY > max(orderX, orderY)] = 0.0 

91 self.cases.append((ctrl, coefficients)) 

92 

93 array = np.arange(self.bbox.getArea(), dtype=np.float32).reshape(self.bbox.getDimensions()) 

94 self.image = lsst.afw.image.ImageF(array) 

95 self.fields = [lsst.afw.math.ChebyshevBoundedField(self.bbox, coeffs) for _, coeffs in self.cases] 

96 self.product = lsst.afw.math.ProductBoundedField(self.fields) 

97 

98 def tearDown(self): 

99 del self.bbox 

100 

101 def testFillImageInterpolation(self): 

102 ctrl, coefficients = self.cases[-2] 

103 bbox = lsst.geom.Box2I(lsst.geom.Point2I(10, 15), 

104 lsst.geom.Extent2I(360, 350)) 

105 field = lsst.afw.math.ChebyshevBoundedField(bbox, coefficients) 

106 image1 = lsst.afw.image.ImageF(bbox) 

107 image2 = lsst.afw.image.ImageF(bbox) 

108 image3 = lsst.afw.image.ImageF(bbox) 

109 image4 = lsst.afw.image.ImageF(bbox) 

110 field.fillImage(image1) 

111 field.fillImage(image2, xStep=3) 

112 field.fillImage(image3, yStep=4) 

113 field.fillImage(image4, xStep=3, yStep=4) 

114 self.assertFloatsAlmostEqual(image1.array, image2.array, rtol=1E-2, atol=1E-2) 

115 self.assertFloatsAlmostEqual(image1.array, image3.array, rtol=1.5E-2, atol=1.5E-2) 

116 self.assertFloatsAlmostEqual(image1.array, image4.array, rtol=2E-2, atol=2E-2) 

117 

118 def testEvaluate(self): 

119 """Test the single-point evaluate method against explicitly-defined 1-d Chebyshevs 

120 (at the top of this file). 

121 """ 

122 factor = 12.345 

123 boxD = lsst.geom.Box2D(self.bbox) 

124 # sx, sy: transform from self.bbox range to [-1, -1] 

125 sx = 2.0/boxD.getWidth() 

126 sy = 2.0/boxD.getHeight() 

127 nPoints = 50 

128 for ctrl, coefficients in self.cases: 

129 field = lsst.afw.math.ChebyshevBoundedField( 

130 self.bbox, coefficients) 

131 x = np.random.rand(nPoints)*boxD.getWidth() + boxD.getMinX() 

132 y = np.random.rand(nPoints)*boxD.getHeight() + boxD.getMinY() 

133 z1 = field.evaluate(x, y) 

134 tx = np.array([CHEBYSHEV_T[i](sx*x) 

135 for i in range(coefficients.shape[1])]) 

136 ty = np.array([CHEBYSHEV_T[i](sy*y) 

137 for i in range(coefficients.shape[0])]) 

138 self.assertEqual(tx.shape, (coefficients.shape[1], x.size)) 

139 self.assertEqual(ty.shape, (coefficients.shape[0], y.size)) 

140 z2 = np.array([np.dot(ty[:, i], np.dot(coefficients, tx[:, i])) 

141 for i in range(nPoints)]) 

142 self.assertFloatsAlmostEqual(z1, z2, rtol=1E-12) 

143 

144 scaled = field*factor 

145 self.assertFloatsAlmostEqual(scaled.evaluate(x, y), 

146 factor*z2, 

147 rtol=factor*1E-13) 

148 self.assertFloatsEqual( 

149 scaled.getCoefficients(), factor*field.getCoefficients()) 

150 

151 def testProductEvaluate(self): 

152 """Test that ProductBoundedField.evaluate is equivalent to multiplying 

153 its nested BoundedFields. 

154 """ 

155 zFlat1 = self.product.evaluate(self.xFlat, self.yFlat) 

156 zFlat2 = np.array([self.product.evaluate(x, y) for x, y in zip(self.xFlat, self.yFlat)]) 

157 self.assertFloatsAlmostEqual(zFlat1, zFlat2) 

158 zFlat3 = np.ones(zFlat1.shape, dtype=float) 

159 for field in self.fields: 

160 zFlat3 *= field.evaluate(self.xFlat, self.yFlat) 

161 self.assertFloatsAlmostEqual(zFlat1, zFlat3) 

162 

163 def testMultiplyImage(self): 

164 """Test Multiplying in place an image. 

165 """ 

166 _, coefficients = self.cases[-2] 

167 field = lsst.afw.math.ChebyshevBoundedField(self.image.getBBox(), coefficients) 

168 # multiplyImage() is in-place, so we have to make the expected result first. 

169 expect = multiply(self.image, field) 

170 field.multiplyImage(self.image) 

171 self.assertImagesAlmostEqual(self.image, expect) 

172 

173 def testMultiplyImageRaisesUnequalBBox(self): 

174 """Multiplying an image with a different bbox should raise. 

175 """ 

176 _, coefficients = self.cases[-2] 

177 field = lsst.afw.math.ChebyshevBoundedField(self.image.getBBox(), coefficients) 

178 subBox = lsst.geom.Box2I(lsst.geom.Point2I(0, 3), lsst.geom.Point2I(3, 4)) 

179 subImage = self.image.subset(subBox) 

180 with(self.assertRaises(RuntimeError)): 

181 field.multiplyImage(subImage) 

182 

183 def testMultiplyImageOverlapSubImage(self): 

184 """Multiplying a subimage with overlapOnly=true should only modify 

185 the subimage, when a subimage is passed in. 

186 """ 

187 _, coefficients = self.cases[-2] 

188 field = lsst.afw.math.ChebyshevBoundedField(self.image.getBBox(), coefficients) 

189 subBox = lsst.geom.Box2I(lsst.geom.Point2I(0, 3), lsst.geom.Point2I(3, 4)) 

190 subImage = self.image.subset(subBox) 

191 expect = self.image.clone() 

192 expect[subBox] = multiply(subImage, field) 

193 field.multiplyImage(subImage, overlapOnly=True) 

194 self.assertImagesAlmostEqual(self.image, expect) 

195 

196 def testMultiplyImageOverlapSmallerBoundedField(self): 

197 """Multiplying a subimage with overlapOnly=true should only modify 

198 the subimage if the boundedField bbox is smaller than the image. 

199 

200 This is checking for a bug where the bounded field was writing outside 

201 the overlap bbox. 

202 """ 

203 _, coefficients = self.cases[-2] 

204 subBox = lsst.geom.Box2I(lsst.geom.Point2I(0, 3), lsst.geom.Point2I(3, 4)) 

205 # The BF is only defined on the subBox, not the whole image bbox. 

206 field = lsst.afw.math.ChebyshevBoundedField(subBox, coefficients) 

207 subImage = self.image.subset(subBox) 

208 expect = self.image.clone() 

209 expect[subBox] = multiply(subImage, field) 

210 field.multiplyImage(self.image, overlapOnly=True) 

211 self.assertImagesAlmostEqual(self.image, expect) 

212 

213 def _testIntegrateBox(self, bbox, coeffs, expect): 

214 field = lsst.afw.math.ChebyshevBoundedField(bbox, coeffs) 

215 self.assertFloatsAlmostEqual(field.integrate(), expect, rtol=1E-14) 

216 

217 def testIntegrateTrivialBox(self): 

218 """Test integrating over a "trivial" [-1,1] box. 

219 

220 NOTE: a "trivial" BBox can't be constructed exactly, given that Box2I 

221 is inclusive, but the [0,1] box has the same area (because it is 

222 actually (-0.5, 1.5) when converted to a Box2D), and the translation 

223 doesn't affect the integral. 

224 """ 

225 bbox = lsst.geom.Box2I(lsst.geom.Point2I(0, 0), 

226 lsst.geom.Point2I(1, 1)) 

227 

228 # 0th order polynomial 

229 coeffs = np.array([[5.0]]) 

230 self._testIntegrateBox(bbox, coeffs, 4.0*coeffs[0, 0]) 

231 

232 # 1st order polynomial: odd orders drop out of integral 

233 coeffs = np.array([[5.0, 2.0], [3.0, 4.0]]) 

234 self._testIntegrateBox(bbox, coeffs, 4.0*coeffs[0, 0]) 

235 

236 # 2nd order polynomial in x, 0th in y 

237 coeffs = np.array([[5.0, 0.0, 7.0]]) 

238 self._testIntegrateBox( 

239 bbox, coeffs, 4.0*coeffs[0, 0] - (4.0/3.0)*coeffs[0, 2]) 

240 

241 # 2nd order polynomial in y, 0th in x 

242 coeffs = np.zeros((3, 3)) 

243 coeffs[0, 0] = 5.0 

244 coeffs[2, 0] = 7.0 

245 self._testIntegrateBox( 

246 bbox, coeffs, 4.0*coeffs[0, 0] - (4.0/3.0)*coeffs[2, 0]) 

247 

248 # 2nd order polynomial in x and y, no cross-term 

249 coeffs = np.zeros((3, 3)) 

250 coeffs[0, 0] = 5.0 

251 coeffs[1, 0] = 7.0 

252 coeffs[0, 2] = 3.0 

253 self._testIntegrateBox(bbox, coeffs, 

254 4.0*coeffs[0, 0] - (4.0/3.0)*coeffs[2, 0] - (4.0/3.0)*coeffs[0, 2]) 

255 

256 def testIntegrateBox(self): 

257 r"""Test integrating over an "interesting" box. 

258 

259 The values of these integrals were checked in Mathematica. The code 

260 block below can be pasted into Mathematica to re-do those calculations. 

261 

262 :: 

263 

264 f[x_, y_, n_, m_] := \!\( 

265 \*UnderoverscriptBox[\(\[Sum]\), \(i = 0\), \(n\)]\( 

266 \*UnderoverscriptBox[\(\[Sum]\), \(j = 0\), \(m\)] 

267 \*SubscriptBox[\(a\), \(i, j\)]*ChebyshevT[i, x]*ChebyshevT[j, y]\)\) 

268 integrate2dBox[n_, m_, x0_, x1_, y0_, y1_] := \!\( 

269 \*SubsuperscriptBox[\(\[Integral]\), \(y0\), \(y1\)]\( 

270 \*SubsuperscriptBox[\(\[Integral]\), \(x0\), \(x1\)]f[ 

271 \*FractionBox[\(2 x - x0 - x1\), \(x1 - x0\)], 

272 \*FractionBox[\(2 y - y0 - y1\), \(y1 - y0\)], n, 

273 m] \[DifferentialD]x \[DifferentialD]y\)\) 

274 integrate2dBox[0, 0, -2.5, 5.5, -3.5, 7.5] 

275 integrate2dBox[1, 0, -2.5, 5.5, -3.5, 7.5] 

276 integrate2dBox[0, 1, -2.5, 5.5, -3.5, 7.5] 

277 integrate2dBox[1, 1, -2.5, 5.5, -3.5, 7.5] 

278 integrate2dBox[1, 2, -2.5, 5.5, -3.5, 7.5] 

279 integrate2dBox[2, 2, -2.5, 5.5, -3.5, 7.5] 

280 """ 

281 bbox = lsst.geom.Box2I( 

282 lsst.geom.Point2I(-2, -3), lsst.geom.Point2I(5, 7)) 

283 

284 # 0th order polynomial 

285 coeffs = np.array([[5.0]]) 

286 self._testIntegrateBox(bbox, coeffs, 88.0*coeffs[0, 0]) 

287 

288 # 1st order polynomial: odd orders drop out of integral 

289 coeffs = np.array([[5.0, 2.0], [3.0, 4.0]]) 

290 self._testIntegrateBox(bbox, coeffs, 88.0*coeffs[0, 0]) 

291 

292 # 2nd order polynomial in x, 0th in y 

293 coeffs = np.array([[5.0, 0.0, 7.0]]) 

294 self._testIntegrateBox( 

295 bbox, coeffs, 88.0*coeffs[0, 0] - (88.0/3.0)*coeffs[0, 2]) 

296 

297 # 2nd order polynomial in y, 0th in x 

298 coeffs = np.zeros((3, 3)) 

299 coeffs[0, 0] = 5.0 

300 coeffs[2, 0] = 7.0 

301 self._testIntegrateBox( 

302 bbox, coeffs, 88.0*coeffs[0, 0] - (88.0/3.0)*coeffs[2, 0]) 

303 

304 # 2nd order polynomial in x,y 

305 coeffs = np.zeros((3, 3)) 

306 coeffs[2, 2] = 11.0 

307 self._testIntegrateBox(bbox, coeffs, (88.0/9.0)*coeffs[2, 2]) 

308 

309 def testMean(self): 

310 """The mean of the nth 1d Chebyshev (a_n*T_n(x)) on [-1,1] is 

311 0 for odd n 

312 a_n / (1-n^2) for even n 

313 

314 Similarly, the mean of the (n,m)th 2d Chebyshev is the appropriate 

315 product of the above. 

316 """ 

317 bbox = lsst.geom.Box2I( 

318 lsst.geom.Point2I(-2, -3), lsst.geom.Point2I(5, 7)) 

319 

320 coeffs = np.array([[5.0]]) 

321 field = lsst.afw.math.ChebyshevBoundedField(bbox, coeffs) 

322 self.assertEqual(field.mean(), coeffs[0, 0]) 

323 

324 coeffs = np.array([[5.0, 0.0, 3.0]]) 

325 field = lsst.afw.math.ChebyshevBoundedField(bbox, coeffs) 

326 self.assertEqual(field.mean(), coeffs[0, 0] - coeffs[0, 2]/3.0) 

327 

328 # 2nd order polynomial in x,y 

329 coeffs = np.zeros((3, 3)) 

330 coeffs[0, 0] = 7.0 

331 coeffs[1, 0] = 31.0 

332 coeffs[0, 2] = 13.0 

333 coeffs[2, 2] = 11.0 

334 field = lsst.afw.math.ChebyshevBoundedField(bbox, coeffs) 

335 self.assertFloatsAlmostEqual( 

336 field.mean(), coeffs[0, 0] - coeffs[0, 2]/3.0 + coeffs[2, 2]/9.0) 

337 

338 def testImageFit(self): 

339 """Test that we can fit an image produced by a ChebyshevBoundedField and 

340 get the same coefficients back. 

341 """ 

342 for ctrl, coefficients in self.cases: 

343 inField = lsst.afw.math.ChebyshevBoundedField( 

344 self.bbox, coefficients) 

345 for Image in (lsst.afw.image.ImageF, lsst.afw.image.ImageD): 

346 image = Image(self.bbox) 

347 inField.fillImage(image) 

348 outField = lsst.afw.math.ChebyshevBoundedField.fit(image, ctrl) 

349 self.assertFloatsAlmostEqual( 

350 outField.getCoefficients(), coefficients, rtol=1E-6, atol=1E-7) 

351 

352 def testArrayFit(self): 

353 """Test that we can fit 1-d arrays produced by a ChebyshevBoundedField and 

354 get the same coefficients back. 

355 """ 

356 for ctrl, coefficients in self.cases: 

357 inField = lsst.afw.math.ChebyshevBoundedField( 

358 self.bbox, coefficients) 

359 for Image in (lsst.afw.image.ImageF, lsst.afw.image.ImageD): 

360 array = inField.evaluate(self.xFlat, self.yFlat) 

361 outField1 = lsst.afw.math.ChebyshevBoundedField.fit(self.bbox, self.xFlat, self.yFlat, 

362 array, ctrl) 

363 self.assertFloatsAlmostEqual( 

364 outField1.getCoefficients(), coefficients, rtol=1E-6, atol=1E-7) 

365 weights = (1.0 + np.random.randn(array.size)**2) 

366 # Should get same results with different weights, since we still have no noise 

367 # and a model that can exactly reproduce the data. 

368 outField2 = lsst.afw.math.ChebyshevBoundedField.fit(self.bbox, self.xFlat, self.yFlat, 

369 array, weights, ctrl) 

370 self.assertFloatsAlmostEqual( 

371 outField2.getCoefficients(), coefficients, rtol=1E-7, atol=1E-7) 

372 

373 def testApproximate(self): 

374 """Test the approximate instantiation with the example of 

375 fitting a PixelAreaBoundedField to reasonable precision. 

376 """ 

377 

378 # This HSC-R band wcs was chosen arbitrarily from the edge of 

379 # field-of-view (ccd 4) for the w_2019_38 processing of RC2 as it 

380 # represents the typical use case of the approxBoundedField method. 

381 skyWcs = lsst.afw.geom.SkyWcs.readFits(os.path.join(testPath, 

382 "data/jointcal_wcs-0034772-004.fits")) 

383 bbox = lsst.geom.Box2I(lsst.geom.Point2I(0, 0), 

384 lsst.geom.Point2I(2047, 4175)) 

385 

386 pixelAreaField = lsst.afw.math.PixelAreaBoundedField(bbox, skyWcs, 

387 unit=lsst.geom.arcseconds) 

388 approxField = lsst.afw.math.ChebyshevBoundedField.approximate(pixelAreaField) 

389 

390 # Choose random points to test rather than a grid to ensure that 

391 # we are not using the same gridded points as used for the 

392 # approximation. 

393 np.random.seed(seed=1000) 

394 xTest = np.random.uniform(low=0.0, high=bbox.getMaxX(), size=10000) 

395 yTest = np.random.uniform(low=0.0, high=bbox.getMaxY(), size=10000) 

396 

397 # The evaluation of approxField is ~80x faster than the 

398 # evaluation of pixelAreaField. 

399 expect = pixelAreaField.evaluate(xTest, yTest) 

400 result = approxField.evaluate(xTest, yTest) 

401 

402 # The approximation is good to the 1e-7 level (absolute) 

403 self.assertFloatsAlmostEqual(result, expect, atol=1e-7) 

404 # and to the 1e-5 level (relative). This is < 0.01 mmag. 

405 self.assertFloatsAlmostEqual(result, expect, rtol=1e-5) 

406 

407 def testPersistence(self): 

408 """Test that we can round-trip a ChebyshevBoundedField through 

409 persistence. 

410 """ 

411 boxD = lsst.geom.Box2D(self.bbox) 

412 nPoints = 50 

413 with lsst.utils.tests.getTempFilePath(".fits") as filename: 

414 for ctrl, coefficients in self.cases: 

415 inField = lsst.afw.math.ChebyshevBoundedField( 

416 self.bbox, coefficients) 

417 inField.writeFits(filename) 

418 outField = lsst.afw.math.ChebyshevBoundedField.readFits(filename) 

419 self.assertEqual(inField.getBBox(), outField.getBBox()) 

420 self.assertFloatsAlmostEqual( 

421 inField.getCoefficients(), outField.getCoefficients()) 

422 x = np.random.rand(nPoints)*boxD.getWidth() + boxD.getMinX() 

423 y = np.random.rand(nPoints)*boxD.getHeight() + boxD.getMinY() 

424 z1 = inField.evaluate(x, y) 

425 z2 = inField.evaluate(x, y) 

426 self.assertFloatsAlmostEqual(z1, z2, rtol=1E-13) 

427 

428 # test with an empty bbox 

429 inField = lsst.afw.math.ChebyshevBoundedField(lsst.geom.Box2I(), 

430 np.array([[1.0, 2.0], [3.0, 4.0]])) 

431 inField.writeFits(filename) 

432 outField = lsst.afw.math.ChebyshevBoundedField.readFits(filename) 

433 self.assertEqual(inField.getBBox(), outField.getBBox()) 

434 

435 def testProductPersistence(self): 

436 """Test that we can round-trip a ProductBoundedField through 

437 persistence. 

438 """ 

439 with lsst.utils.tests.getTempFilePath(".fits") as filename: 

440 self.product.writeFits(filename) 

441 out = lsst.afw.math.ProductBoundedField.readFits(filename) 

442 self.assertEqual(self.product, out) 

443 

444 def testTruncate(self): 

445 """Test that truncate() works as expected. 

446 """ 

447 for ctrl, coefficients in self.cases: 

448 field1 = lsst.afw.math.ChebyshevBoundedField( 

449 self.bbox, coefficients) 

450 field2 = field1.truncate(ctrl) 

451 self.assertFloatsAlmostEqual( 

452 field1.getCoefficients(), field2.getCoefficients()) 

453 self.assertEqual(field1.getBBox(), field2.getBBox()) 

454 config3 = lsst.afw.math.ChebyshevBoundedField.ConfigClass() 

455 config3.readControl(ctrl) 

456 if ctrl.orderX > 0: 

457 config3.orderX -= 1 

458 if ctrl.orderY > 0: 

459 config3.orderY -= 1 

460 field3 = field1.truncate(config3.makeControl()) 

461 for i in range(config3.orderY + 1): 

462 for j in range(config3.orderX + 1): 

463 if config3.triangular and i + j > max(config3.orderX, config3.orderY): 

464 self.assertEqual(field3.getCoefficients()[i, j], 0.0) 

465 else: 

466 self.assertEqual(field3.getCoefficients()[i, j], 

467 field1.getCoefficients()[i, j]) 

468 

469 def testEquality(self): 

470 for ctrl, coefficients in self.cases: 

471 field1 = lsst.afw.math.ChebyshevBoundedField(self.bbox, coefficients) 

472 field2 = lsst.afw.math.ChebyshevBoundedField(self.bbox, coefficients) 

473 self.assertEqual(field1, field2, msg=coefficients) 

474 

475 # same coefficients, instantiated from different arrays 

476 field1 = lsst.afw.math.ChebyshevBoundedField(self.bbox, np.array([[1.0]])) 

477 field2 = lsst.afw.math.ChebyshevBoundedField(self.bbox, np.array([[1.0]])) 

478 self.assertEqual(field1, field2) 

479 field1 = lsst.afw.math.ChebyshevBoundedField(self.bbox, np.array([[1.0, 2.0], [3., 4.]])) 

480 field2 = lsst.afw.math.ChebyshevBoundedField(self.bbox, np.array([[1.0, 2.0], [3., 4.]])) 

481 self.assertEqual(field1, field2) 

482 

483 # different coefficient(s) 

484 field1 = lsst.afw.math.ChebyshevBoundedField(self.bbox, np.array([[1.0]])) 

485 field2 = lsst.afw.math.ChebyshevBoundedField(self.bbox, np.array([[2.0]])) 

486 self.assertNotEqual(field1, field2) 

487 field1 = lsst.afw.math.ChebyshevBoundedField(self.bbox, np.array([[1.0, 0.0]])) 

488 field2 = lsst.afw.math.ChebyshevBoundedField(self.bbox, np.array([[1.0], [0.0]])) 

489 self.assertNotEqual(field1, field2) 

490 

491 # different bbox 

492 bbox1 = lsst.geom.Box2I(lsst.geom.Point2I(-10, -10), lsst.geom.Point2I(5, 5)) 

493 bbox2 = lsst.geom.Box2I(lsst.geom.Point2I(-5, -5), lsst.geom.Point2I(5, 5)) 

494 field1 = lsst.afw.math.ChebyshevBoundedField(bbox1, np.array([[1.0]])) 

495 field2 = lsst.afw.math.ChebyshevBoundedField(bbox2, np.array([[1.0]])) 

496 self.assertNotEqual(field1, field2) 

497 

498 

499class MemoryTester(lsst.utils.tests.MemoryTestCase): 

500 pass 

501 

502 

503def setup_module(module): 

504 lsst.utils.tests.init() 

505 

506 

507if __name__ == "__main__": 507 ↛ 508line 507 didn't jump to line 508, because the condition on line 507 was never true

508 lsst.utils.tests.init() 

509 unittest.main()