LSSTApplications  19.0.0-10-g920eed2,19.0.0-11-g48a0200+2,19.0.0-18-gfc4e62b+17,19.0.0-2-g3b2f90d+2,19.0.0-2-gd671419+5,19.0.0-20-g5a5a17ab+15,19.0.0-21-g2644856+18,19.0.0-23-g84eeccb+6,19.0.0-24-g878c510+5,19.0.0-25-g6c8df7140,19.0.0-25-gb330496+5,19.0.0-3-g2b32d65+5,19.0.0-3-g8227491+16,19.0.0-3-g9c54d0d+16,19.0.0-3-gca68e65+12,19.0.0-3-gcfc5f51+5,19.0.0-3-ge110943+15,19.0.0-3-ge74d124,19.0.0-3-gfe04aa6+16,19.0.0-30-g9c3fd16+6,19.0.0-4-g06f5963+5,19.0.0-4-g3d16501+18,19.0.0-4-g4a9c019+5,19.0.0-4-g5a8b323,19.0.0-4-g66397f0+1,19.0.0-4-g8278b9b+1,19.0.0-4-g8557e14,19.0.0-4-g8964aba+17,19.0.0-4-ge404a01+16,19.0.0-5-g40f3a5a,19.0.0-5-g4db63b3,19.0.0-5-gfb03ce7+17,19.0.0-6-gbaebbfb+16,19.0.0-61-gec4c6e08+6,19.0.0-7-g039c0b5+16,19.0.0-7-gbea9075+4,19.0.0-7-gc567de5+17,19.0.0-70-g334bf3e+1,19.0.0-9-g463f923+16,b.20.0.x-g5487ab2134,v20.0.0.rc1
LSSTDataManagementBasePackage
testUtils.py
Go to the documentation of this file.
1 #
2 # Developed for the LSST Data Management System.
3 # This product includes software developed by the LSST Project
4 # (https://www.lsst.org).
5 # See the COPYRIGHT file at the top-level directory of this distribution
6 # for details of code ownership.
7 #
8 # This program is free software: you can redistribute it and/or modify
9 # it under the terms of the GNU General Public License as published by
10 # the Free Software Foundation, either version 3 of the License, or
11 # (at your option) any later version.
12 #
13 # This program is distributed in the hope that it will be useful,
14 # but WITHOUT ANY WARRANTY; without even the implied warranty of
15 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 # GNU General Public License for more details.
17 #
18 # You should have received a copy of the GNU General Public License
19 # along with this program. If not, see <https://www.gnu.org/licenses/>.
20 #
21 
22 """Utilities that should be imported into the lsst.geom namespace when
23 lsst.geom is used
24 
25 In the case of the assert functions, importing them makes them available in lsst.utils.tests.TestCase
26 """
27 __all__ = []
28 
29 import math
30 
31 import numpy as np
32 
33 import lsst.utils.tests
34 from ._geom import arcseconds
35 
36 
37 def extraMsg(msg):
38  """Format extra error message, if any
39  """
40  if msg:
41  return ": " + msg
42  return ""
43 
44 
45 @lsst.utils.tests.inTestCase
46 def assertAnglesAlmostEqual(testCase, ang0, ang1, maxDiff=0.001*arcseconds,
47  ignoreWrap=True, msg="Angles differ"):
48  r"""Assert that two `~lsst.geom.Angle`\ s are almost equal, ignoring
49  wrap differences by default.
50 
51  If both arguments are NaN the assert will pass. If one of the arguments
52  is NaN but the other is not the assert will fail.
53 
54  Parameters
55  ----------
56  testCase : `unittest.TestCase`
57  test case the test is part of; an object supporting one method:
58  fail(self, msgStr)
59  ang0 : `lsst.geom.Angle`
60  angle 0
61  ang1 : `lsst.geom.Angle`
62  angle 1
63  maxDiff : `lsst.geom.Angle`
64  maximum difference between the two angles
65  ignoreWrap : `bool`
66  ignore wrap when comparing the angles?
67  - if True then wrap is ignored, e.g. 0 and 360 degrees are considered
68  equal
69  - if False then wrap matters, e.g. 0 and 360 degrees are considered
70  different
71  msg : `str`
72  exception message prefix; details of the error are appended after ": "
73 
74  Raises
75  ------
76  AssertionError
77  Raised if the difference is greater than ``maxDiff``
78  """
79  isNan0 = math.isnan(ang0.asRadians())
80  isNan1 = math.isnan(ang1.asRadians())
81  if isNan0 and isNan1:
82  return
83  if isNan0:
84  testCase.fail("ang0 is NaN")
85  if isNan1:
86  testCase.fail("ang1 is NaN")
87  measDiff = ang1 - ang0
88  if ignoreWrap:
89  measDiff = measDiff.wrapCtr()
90  if abs(measDiff) > maxDiff:
91  testCase.fail("%s: measured difference %s arcsec > max allowed %s arcsec" %
92  (msg, measDiff.asArcseconds(), maxDiff.asArcseconds()))
93 
94 
95 @lsst.utils.tests.inTestCase
96 def assertPairsAlmostEqual(testCase, pair0, pair1, maxDiff=1e-7, msg="Pairs differ"):
97  """Assert that two Cartesian points are almost equal.
98 
99  Each point can be any indexable pair of two floats, including
100  Point2D or Extent2D, a list or a tuple.
101 
102  Parameters
103  ----------
104  testCase : `unittest.TestCase`
105  test case the test is part of; an object supporting one method: fail(self, msgStr)
106  pair0 : pair of `float`
107  pair 0
108  pair1 : pair of `floats`
109  pair 1
110  maxDiff : `float`
111  maximum radial separation between the two points
112  msg : `str`
113  exception message prefix; details of the error are appended after ": "
114 
115  Raises
116  ------
117  AssertionError
118  Raised if the radial difference is greater than ``maxDiff``
119 
120  Notes
121  -----
122  .. warning::
123 
124  Does not compare types, just compares values.
125  """
126  if len(pair0) != 2:
127  raise RuntimeError("len(pair0)=%s != 2" % (len(pair0),))
128  if len(pair1) != 2:
129  raise RuntimeError("len(pair1)=%s != 2" % (len(pair1),))
130 
131  pairDiff = [float(pair1[i] - pair0[i]) for i in range(2)]
132  measDiff = math.hypot(*pairDiff)
133  if measDiff > maxDiff:
134  testCase.fail("%s: measured radial distance = %s > maxDiff = %s, pair0=(%r, %r), pair1=(%r, %r)" %
135  (msg, measDiff, maxDiff, pair0[0], pair0[1], pair1[0], pair1[1]))
136 
137 
138 @lsst.utils.tests.inTestCase
139 def assertPairListsAlmostEqual(testCase, list0, list1, maxDiff=1e-7, msg=None):
140  """Assert that two lists of Cartesian points are almost equal
141 
142  Each point can be any indexable pair of two floats, including
143  Point2D or Extent2D, a list or a tuple.
144 
145  Parameters
146  ----------
147  testCase : `unittest.TestCase`
148  test case the test is part of; an object supporting one method: fail(self, msgStr)
149  list0 : `list` of pairs of `float`
150  list of pairs 0
151  list1 : `list` of pairs of `float`
152  list of pairs 1
153  maxDiff : `float`
154  maximum radial separation between the two points
155  msg : `str`
156  additional information for the error message; appended after ": "
157 
158  Raises
159  ------
160  AssertionError
161  Raised if the radial difference is greater than ``maxDiff``
162 
163  Notes
164  -----
165  .. warning::
166 
167  Does not compare types, just values.
168  """
169  testCase.assertEqual(len(list0), len(list1))
170  lenList1 = np.array([len(val) for val in list0])
171  lenList2 = np.array([len(val) for val in list1])
172  testCase.assertTrue(np.all(lenList1 == 2))
173  testCase.assertTrue(np.all(lenList2 == 2))
174 
175  diffArr = np.array([(val0[0] - val1[0], val0[1] - val1[1])
176  for val0, val1 in zip(list0, list1)], dtype=float)
177  sepArr = np.hypot(diffArr[:, 0], diffArr[:, 1])
178  badArr = sepArr > maxDiff
179  if np.any(badArr):
180  maxInd = np.argmax(sepArr)
181  testCase.fail("PairLists differ in %s places; max separation is at %s: %s > %s%s" %
182  (np.sum(badArr), maxInd, sepArr[maxInd], maxDiff, extraMsg(msg)))
183 
184 
185 @lsst.utils.tests.inTestCase
186 def assertSpherePointsAlmostEqual(testCase, sp0, sp1, maxSep=0.001*arcseconds, msg=""):
187  r"""Assert that two `~lsst.geom.SpherePoint`\ s are almost equal
188 
189  Parameters
190  ----------
191  testCase : `unittest.TestCase`
192  test case the test is part of; an object supporting one method:
193  fail(self, msgStr)
194  sp0 : `lsst.geom.SpherePoint`
195  SpherePoint 0
196  sp1 : `lsst.geom.SpherePoint`
197  SpherePoint 1
198  maxSep : `lsst.geom.Angle`
199  maximum separation
200  msg : `str`
201  extra information to be printed with any error message
202 
203  Raises
204  ------
205  AssertionError
206  The SpherePoints are not equal.
207  """
208  if sp0.separation(sp1) > maxSep:
209  testCase.fail("Angular separation between %s and %s = %s\" > maxSep = %s\"%s" %
210  (sp0, sp1, sp0.separation(sp1).asArcseconds(), maxSep.asArcseconds(), extraMsg(msg)))
211 
212 
213 @lsst.utils.tests.inTestCase
214 def assertSpherePointListsAlmostEqual(testCase, splist0, splist1, maxSep=0.001*arcseconds, msg=None):
215  r"""Assert that two lists of `~lsst.geom.SpherePoint`\ s are almost equal
216 
217  Parameters
218  ----------
219  testCase : `unittest.TestCase`
220  test case the test is part of; an object supporting one method:
221  fail(self, msgStr)
222  splist0 : `list` of `lsst.geom.SpherePoint`
223  list of SpherePoints 0
224  splist1 : `list` of `lsst.geom.SpherePoint`
225  list of SpherePoints 1
226  maxSep : `lsst.geom.Angle`
227  maximum separation
228  msg : `str`
229  exception message prefix; details of the error are appended after ": "
230 
231  Raises
232  ------
233  AssertionError
234  The SpherePoint lists are not equal.
235  """
236  testCase.assertEqual(len(splist0), len(splist1), msg=msg)
237  sepArr = np.array([sp0.separation(sp1)
238  for sp0, sp1 in zip(splist0, splist1)])
239  badArr = sepArr > maxSep
240  if np.any(badArr):
241  maxInd = np.argmax(sepArr)
242  testCase.fail("SpherePointLists differ in %s places; max separation is at %s: %s\" > %s\"%s" %
243  (np.sum(badArr), maxInd, sepArr[maxInd].asArcseconds(),
244  maxSep.asArcseconds(), extraMsg(msg)))
245 
246 
247 @lsst.utils.tests.inTestCase
248 def assertBoxesAlmostEqual(testCase, box0, box1, maxDiff=1e-7, msg="Boxes differ"):
249  """Assert that two boxes (`~lsst.geom.Box2D` or `~lsst.geom.Box2I`) are
250  almost equal
251 
252  Parameters
253  ----------
254  testCase : `unittest.TestCase`
255  test case the test is part of; an object supporting one method:
256  fail(self, msgStr)
257  box0 : `lsst.geom.Box2D` or `lsst.geom.Box2I`
258  box 0
259  box1 : `lsst.geom.Box2D` or `lsst.geom.Box2I`
260  box 1
261  maxDiff : `float`
262  maximum radial separation between the min points and max points
263  msg : `str`
264  exception message prefix; details of the error are appended after ": "
265 
266  Raises
267  ------
268  AssertionError
269  Raised if the radial difference of the min points or max points is
270  greater than maxDiff
271 
272  Notes
273  -----
274  .. warning::
275 
276  Does not compare types, just compares values.
277  """
278  assertPairsAlmostEqual(testCase, box0.getMin(),
279  box1.getMin(), maxDiff=maxDiff, msg=msg + ": min")
280  assertPairsAlmostEqual(testCase, box0.getMax(),
281  box1.getMax(), maxDiff=maxDiff, msg=msg + ": max")
lsst::geom.testUtils.assertBoxesAlmostEqual
def assertBoxesAlmostEqual(testCase, box0, box1, maxDiff=1e-7, msg="Boxes differ")
Definition: testUtils.py:248
lsst::sphgeom::abs
Angle abs(Angle const &a)
Definition: Angle.h:106
lsst::geom.testUtils.assertSpherePointListsAlmostEqual
def assertSpherePointListsAlmostEqual(testCase, splist0, splist1, maxSep=0.001 *arcseconds, msg=None)
Definition: testUtils.py:214
lsst::utils.tests
Definition: tests.py:1
lsst::geom.testUtils.assertSpherePointsAlmostEqual
def assertSpherePointsAlmostEqual(testCase, sp0, sp1, maxSep=0.001 *arcseconds, msg="")
Definition: testUtils.py:186
lsst::geom.testUtils.assertPairListsAlmostEqual
def assertPairListsAlmostEqual(testCase, list0, list1, maxDiff=1e-7, msg=None)
Definition: testUtils.py:139
lsst::geom.testUtils.extraMsg
def extraMsg(msg)
Definition: testUtils.py:37
lsst::geom.testUtils.assertPairsAlmostEqual
def assertPairsAlmostEqual(testCase, pair0, pair1, maxDiff=1e-7, msg="Pairs differ")
Definition: testUtils.py:96
lsst::geom.testUtils.assertAnglesAlmostEqual
def assertAnglesAlmostEqual(testCase, ang0, ang1, maxDiff=0.001 *arcseconds, ignoreWrap=True, msg="Angles differ")
Definition: testUtils.py:46