Ejemplo n.º 1
0
 def test_center_and_dimensions(self):
     b = Box.fromDegrees(-90, -45, 90, 45)
     self.assertEqual(b.getCenter(), LonLat.fromDegrees(0, 0))
     self.assertEqual(b.getWidth(), Angle.fromDegrees(180))
     self.assertEqual(b.getHeight(), Angle.fromDegrees(90))
     self.assertEqual(b.getLon().getA(), NormalizedAngle.fromDegrees(-90))
     self.assertEqual(b.getLat().getB(), Angle.fromDegrees(45))
Ejemplo n.º 2
0
 def test_relationships(self):
     e = Ellipse(UnitVector3d.X(), Angle(math.pi / 3), Angle(math.pi / 6),
                 Angle(0))
     self.assertTrue(e.contains(UnitVector3d.X()))
     self.assertTrue(UnitVector3d.X() in e)
     c = Circle(UnitVector3d.X(), Angle(math.pi / 2))
     self.assertEqual(c.relate(e), CONTAINS)
     self.assertEqual(e.relate(c), WITHIN)
Ejemplo n.º 3
0
 def testComparisonOperators(self):
     a1 = Angle(1)
     a2 = Angle(2)
     self.assertNotEqual(a1, a2)
     self.assertLess(a1, a2)
     self.assertLessEqual(a1, a2)
     self.assertGreater(a2, a1)
     self.assertGreaterEqual(a2, a1)
Ejemplo n.º 4
0
 def test_center_and_dimensions(self):
     e = Ellipse(UnitVector3d.X(), UnitVector3d.Y(), Angle(2 * math.pi / 3))
     self.assertAlmostEqual(e.getF1().dot(UnitVector3d.X()), 1.0)
     self.assertAlmostEqual(e.getF2().dot(UnitVector3d.Y()), 1.0)
     self.assertAlmostEqual(e.getAlpha(), Angle(2 * math.pi / 3))
     f = Ellipse(UnitVector3d.X(), Angle(math.pi / 3), Angle(math.pi / 6),
                 Angle(0))
     self.assertEqual(f.getCenter(), UnitVector3d.X())
Ejemplo n.º 5
0
 def testConstruction(self):
     a1 = Angle(1.0)
     a2 = Angle.fromRadians(1.0)
     a3 = Angle.fromDegrees(57.29577951308232)
     self.assertEqual(a1, a2)
     self.assertEqual(a1.asRadians(), 1.0)
     self.assertEqual(a1, a3)
     self.assertEqual(a1.asDegrees(), 57.29577951308232)
Ejemplo n.º 6
0
 def testArithmeticOperators(self):
     a = Angle(1)
     b = -a
     self.assertEqual(a + b, Angle(0))
     self.assertEqual(a - b, 2.0 * a)
     self.assertEqual(a - b, a * 2.0)
     self.assertEqual(a / 1.0, a)
     self.assertEqual(a / a, 1.0)
     a += a
     a *= 2
     a -= b
     a /= 5
     self.assertEqual(a.asRadians(), 1)
Ejemplo n.º 7
0
 def testArithmeticOperators(self):
     a = Angle(1)
     b = -a
     self.assertEqual(a + b, Angle(0))
     self.assertEqual(a - b, 2.0 * a)
     self.assertEqual(a - b, a * 2.0)
     self.assertEqual(a / 1.0, a)
     self.assertEqual(a / a, 1.0)
     a += a
     a *= 2
     a -= b
     a /= 5
     self.assertEqual(a.asRadians(), 1)
Ejemplo n.º 8
0
 def test_relationships(self):
     c = Circle(UnitVector3d.X(), Angle.fromDegrees(0.1))
     d = Circle(UnitVector3d(1, 1, 1), Angle(math.pi / 2))
     e = Circle(-UnitVector3d.X())
     self.assertTrue(c.contains(UnitVector3d.X()))
     self.assertTrue(UnitVector3d.X() in c)
     self.assertTrue(d.contains(c))
     self.assertTrue(c.isWithin(d))
     self.assertTrue(c.intersects(d))
     self.assertTrue(c.intersects(UnitVector3d.X()))
     self.assertTrue(e.isDisjointFrom(d))
     self.assertEqual(d.relate(c), CONTAINS)
     self.assertEqual(e.relate(d), DISJOINT)
Ejemplo n.º 9
0
 def test_construction(self):
     self.assertTrue(Circle.empty().isEmpty())
     self.assertTrue(Circle().isEmpty())
     self.assertTrue(Circle.full().isFull())
     c = Circle(UnitVector3d.X())
     self.assertEqual(c.getOpeningAngle(), Angle(0))
     self.assertEqual(c.getSquaredChordLength(), 0)
     c = Circle(UnitVector3d.Z(), 2.0)
     self.assertTrue(c.contains(UnitVector3d.Z()))
     c = Circle(UnitVector3d.Z(), Angle(math.pi))
     self.assertTrue(c.isFull())
     d = c.clone()
     self.assertEqual(c, d)
     self.assertNotEqual(id(c), id(d))
     e = Circle(d)
     self.assertEqual(d, e)
Ejemplo n.º 10
0
 def test_construction(self):
     self.assertTrue(Ellipse.empty().isEmpty())
     self.assertTrue(Ellipse().isEmpty())
     self.assertTrue(Ellipse.full().isFull())
     e = Ellipse(Circle(UnitVector3d.X(), Angle(math.pi / 2)))
     f = Ellipse(UnitVector3d.X(), Angle(math.pi / 2))
     self.assertEqual(e, f)
     self.assertEqual(e.getAlpha(), e.getBeta())
     self.assertTrue(e.isCircle())
     self.assertTrue(e.isGreatCircle())
     g = Ellipse(e)
     h = e.clone()
     self.assertEqual(e, g)
     self.assertEqual(g, h)
     self.assertNotEqual(id(e), id(g))
     self.assertNotEqual(id(g), id(h))
Ejemplo n.º 11
0
 def test_dilation_and_erosion(self):
     a = Angle(math.pi / 2)
     c = Circle(UnitVector3d.X())
     d = c.dilatedBy(a).erodedBy(a)
     c.dilateBy(a).erodeBy(a)
     self.assertEqual(c, d)
     self.assertEqual(c, Circle(UnitVector3d.X()))
Ejemplo n.º 12
0
 def testArithmeticOperators(self):
     a = NormalizedAngle(1)
     b = -a
     self.assertEqual(a + b, Angle(0))
     self.assertEqual(a - b, 2.0 * a)
     self.assertEqual(a - b, a * 2.0)
     self.assertEqual(a / 1.0, a)
     self.assertEqual(a / a, 1.0)
Ejemplo n.º 13
0
def _makePixelRanges():
    """Generate pixel ID ranges for some envelope region"""
    pointing_v = UnitVector3d(1., 1., -1.)
    fov = 0.05  # radians
    region = Circle(pointing_v, Angle(fov / 2))
    pixelator = HtmPixelization(HTM_LEVEL)
    indices = pixelator.envelope(region, 128)
    return indices.ranges()
Ejemplo n.º 14
0
 def test_string(self):
     c = Circle(UnitVector3d.Z(), Angle(1.0))
     self.assertEqual(str(c), 'Circle([0.0, 0.0, 1.0], 1.0)')
     self.assertEqual(repr(c),
                      'Circle(UnitVector3d(0.0, 0.0, 1.0), Angle(1.0))')
     self.assertEqual(
         c,
         eval(repr(c),
              dict(Angle=Angle, Circle=Circle, UnitVector3d=UnitVector3d)))
Ejemplo n.º 15
0
 def testConstruction(self):
     v = Vector3d(1, 1, 1)
     u = UnitVector3d.orthogonalTo(v)
     self.assertAlmostEqual(u.dot(v), 0.0, places=15)
     u = UnitVector3d(1, 1, 1)
     self.assertEqual(u, UnitVector3d(Vector3d(1, 1, 1)))
     self.assertAlmostEqual(u.x(), math.sqrt(3.0) / 3.0, places=15)
     self.assertAlmostEqual(u.y(), math.sqrt(3.0) / 3.0, places=15)
     self.assertAlmostEqual(u.z(), math.sqrt(3.0) / 3.0, places=15)
     u = UnitVector3d(Angle.fromDegrees(45), Angle.fromDegrees(45))
     self.assertEqual(u, UnitVector3d(LonLat.fromDegrees(45, 45)))
     self.assertAlmostEqual(u.x(), 0.5, places=15)
     self.assertAlmostEqual(u.y(), 0.5, places=15)
     self.assertAlmostEqual(u.z(), 0.5 * math.sqrt(2.0), places=15)
     u = UnitVector3d.northFrom(u.asVector3d())
     w = UnitVector3d(LonLat.fromDegrees(225, 45))
     self.assertAlmostEqual(u.x(), w.x(), places=15)
     self.assertAlmostEqual(u.y(), w.y(), places=15)
     self.assertAlmostEqual(u.z(), w.z(), places=15)
Ejemplo n.º 16
0
 def testConstruction(self):
     v = Vector3d(1, 1, 1)
     u = UnitVector3d.orthogonalTo(v)
     self.assertAlmostEqual(u.dot(v), 0.0, places=15)
     a = UnitVector3d(1, 1, 1)
     self.assertEqual(a, UnitVector3d(Vector3d(1, 1, 1)))
     self.assertAlmostEqual(a.x(), math.sqrt(3.0) / 3.0, places=15)
     self.assertAlmostEqual(a.y(), math.sqrt(3.0) / 3.0, places=15)
     self.assertAlmostEqual(a.z(), math.sqrt(3.0) / 3.0, places=15)
     b = UnitVector3d(Angle.fromDegrees(45), Angle.fromDegrees(45))
     self.assertEqual(b, UnitVector3d(LonLat.fromDegrees(45, 45)))
     self.assertAlmostEqual(b.x(), 0.5, places=15)
     self.assertAlmostEqual(b.y(), 0.5, places=15)
     self.assertAlmostEqual(b.z(), 0.5 * math.sqrt(2.0), places=15)
     c = UnitVector3d.northFrom(b)
     d = UnitVector3d(LonLat.fromDegrees(225, 45))
     self.assertAlmostEqual(c.x(), d.x(), places=15)
     self.assertAlmostEqual(c.y(), d.y(), places=15)
     self.assertAlmostEqual(c.z(), d.z(), places=15)
Ejemplo n.º 17
0
 def test_envelope_and_interior(self):
     pixelization = HtmPixelization(3)
     c = Circle(UnitVector3d(1, 1, 1), Angle.fromDegrees(0.1))
     rs = pixelization.envelope(c)
     self.assertTrue(rs == RangeSet(0x3ff))
     rs = pixelization.envelope(c, 1)
     self.assertTrue(rs == RangeSet(0x3ff))
     self.assertTrue(rs.isWithin(pixelization.universe()))
     rs = pixelization.interior(c)
     self.assertTrue(rs.empty())
 def test_envelope_and_interior(self):
     pixelization = Mq3cPixelization(1)
     c = Circle(UnitVector3d(1.0, -0.5, -0.5), Angle.fromDegrees(0.1))
     rs = pixelization.envelope(c)
     self.assertTrue(rs == RangeSet(44))
     rs = pixelization.envelope(c, 1)
     self.assertTrue(rs == RangeSet(44))
     self.assertTrue(rs.isWithin(pixelization.universe()))
     rs = pixelization.interior(c)
     self.assertTrue(rs.empty())
Ejemplo n.º 19
0
 def testConstruction(self):
     p = LonLat.fromDegrees(45, 45)
     self.assertEqual(p, LonLat(NormalizedAngle.fromDegrees(45),
                                Angle.fromDegrees(45)))
     u = UnitVector3d(p)
     q = LonLat(u)
     self.assertAlmostEqual(p.getLon().asRadians(), q.getLon().asRadians(), places=13)
     self.assertAlmostEqual(p.getLat().asRadians(), q.getLat().asRadians(), places=13)
     self.assertAlmostEqual(p.getLon().asRadians(), LonLat.latitudeOf(u).asRadians(), places=13)
     self.assertAlmostEqual(p.getLon().asRadians(), LonLat.longitudeOf(u).asRadians(), places=13)
Ejemplo n.º 20
0
 def test_construction(self):
     b = Box(Box.allLongitudes(), Box.allLatitudes())
     self.assertTrue(b.isFull())
     b = Box.fromDegrees(-90, -45, 90, 45)
     self.assertEqual(b, Box(b.getLon(), b.getLat()))
     a = Box.fromRadians(-0.5 * math.pi, -0.25 * math.pi, 0.5 * math.pi,
                         0.25 * math.pi)
     b = Box(LonLat.fromRadians(-0.5 * math.pi, -0.25 * math.pi),
             LonLat.fromRadians(0.5 * math.pi, 0.25 * math.pi))
     c = Box(LonLat.fromRadians(0, 0), Angle(0.5 * math.pi),
             Angle(0.25 * math.pi))
     d = c.clone()
     self.assertEqual(a, b)
     self.assertEqual(b, c)
     self.assertEqual(c, d)
     self.assertNotEqual(id(c), id(d))
     b = Box()
     self.assertTrue(b.isEmpty())
     self.assertTrue(Box.empty().isEmpty())
     self.assertTrue(Box.full().isFull())
Ejemplo n.º 21
0
 def test_string(self):
     c = Ellipse(UnitVector3d.Z(), Angle(1.0))
     self.assertEqual(str(c),
                      'Ellipse([0.0, 0.0, 1.0], [0.0, 0.0, 1.0], 1.0)')
     self.assertEqual(
         repr(c), 'Ellipse(UnitVector3d(0.0, 0.0, 1.0), '
         'UnitVector3d(0.0, 0.0, 1.0), Angle(1.0))')
     self.assertEqual(
         c,
         eval(repr(c),
              dict(Angle=Angle, Ellipse=Ellipse,
                   UnitVector3d=UnitVector3d)))
Ejemplo n.º 22
0
 def testConstruction(self):
     a1 = Angle(1.0)
     a2 = Angle.fromRadians(1.0)
     a3 = Angle.fromDegrees(57.29577951308232)
     self.assertEqual(a1, a2)
     self.assertEqual(a1.asRadians(), 1.0)
     self.assertEqual(a1, a3)
     self.assertEqual(a1.asDegrees(), 57.29577951308232)
Ejemplo n.º 23
0
 def testConstruction(self):
     p = LonLat.fromDegrees(45, 45)
     self.assertEqual(p, LonLat(NormalizedAngle.fromDegrees(45),
                                Angle.fromDegrees(45)))
     u = UnitVector3d(p)
     q = LonLat(u)
     self.assertAlmostEqual(
         p.getLon().asRadians(), q.getLon().asRadians(), places=13)
     self.assertAlmostEqual(
         p.getLat().asRadians(), q.getLat().asRadians(), places=13)
     self.assertAlmostEqual(p.getLon().asRadians(),
                            LonLat.latitudeOf(u).asRadians(),
                            places=13)
     self.assertAlmostEqual(p.getLon().asRadians(),
                            LonLat.longitudeOf(u).asRadians(),
                            places=13)
Ejemplo n.º 24
0
 def testRotation(self):
     v = UnitVector3d.Y().rotatedAround(UnitVector3d.X(),
                                        Angle(0.5 * math.pi))
     self.assertAlmostEqual(v.x(), 0.0, places=15)
     self.assertAlmostEqual(v.y(), 0.0, places=15)
     self.assertAlmostEqual(v.z(), 1.0, places=15)
Ejemplo n.º 25
0
 def test_dilation_and_erosion(self):
     a = Box.fromRadians(0.5, -0.5, 1.5, 0.5)
     b = a.dilatedBy(Angle(0.5), Angle(0.5)).erodedBy(Angle(1), Angle(1))
     a.dilateBy(Angle(0.5), Angle(0.5)).erodeBy(Angle(1), Angle(1))
     self.assertEqual(a, b)
     self.assertEqual(a, LonLat.fromRadians(1, 0))
Ejemplo n.º 26
0
 def test_complement(self):
     e = Ellipse(UnitVector3d.X(), Angle(math.pi / 3), Angle(math.pi / 6),
                 Angle(0))
     f = e.complemented().complement()
     self.assertEqual(e, f)
Ejemplo n.º 27
0
 def test_codec(self):
     e = Ellipse(UnitVector3d.X(), UnitVector3d.Y(), Angle(2 * math.pi / 3))
     s = e.encode()
     self.assertEqual(Ellipse.decode(s), e)
     self.assertEqual(Region.decode(s), e)
Ejemplo n.º 28
0
    def run(self) -> Optional[int]:
        """Run whole shebang.
        """

        # load configurations
        if self.args.app_config:
            self.config.load(self.args.app_config)

        if self.args.backend == "sql":
            self.dbconfig = ApdbSqlConfig()
            if self.args.config:
                self.dbconfig.load(self.args.config)
        elif self.args.backend == "cassandra":
            self.dbconfig = ApdbCassandraConfig()
            if self.args.config:
                self.dbconfig.load(self.args.config)

        if self.args.dump_config:
            self.config.saveToStream(sys.stdout)
            self.dbconfig.saveToStream(sys.stdout)
            return 0

        # instantiate db interface
        db: Apdb
        if self.args.backend == "sql":
            db = ApdbSql(config=self.dbconfig)
        elif self.args.backend == "cassandra":
            db = ApdbCassandra(config=self.dbconfig)

        visitInfoStore = VisitInfoStore(self.args.visits_file)

        num_tiles = 1
        if self.config.divide != 1:

            tiles = geom.make_tiles(self.config.FOV_rad, self.config.divide)
            num_tiles = len(tiles)

            # check that we have reasonable MPI setup
            if self.config.mp_mode == "mpi":
                comm = MPI.COMM_WORLD
                num_proc = comm.Get_size()
                rank = comm.Get_rank()
                node = MPI.Get_processor_name()
                _LOG.info(
                    COLOR_YELLOW + "MPI job rank=%d size=%d, node %s" +
                    COLOR_RESET, rank, num_proc, node)
                if num_proc != num_tiles:
                    raise ValueError(
                        f"Number of MPI processes ({num_proc}) "
                        f"does not match number of tiles ({num_tiles})")
                if rank != 0:
                    # run simple loop for all non-master processes
                    self.run_mpi_tile_loop(db, comm)
                    return None

        # Initialize starting values from database visits table
        last_visit = visitInfoStore.lastVisit()
        if last_visit is not None:
            start_visit_id = last_visit.visitId + 1
            nsec = last_visit.visitTime.nsecs(
                DateTime.TAI) + self.config.interval * 1_000_000_000
            start_time = DateTime(nsec, DateTime.TAI)
        else:
            start_visit_id = self.config.start_visit_id
            start_time = self.config.start_time_dt

        if self.config.divide > 1:
            _LOG.info("Will divide FOV into %d regions", num_tiles)

        src_read_period = self.config.src_read_period
        src_read_visits = round(self.config.src_read_period *
                                self.config.src_read_duty_cycle)
        _LOG.info("Will read sources for %d visits out of %d", src_read_visits,
                  src_read_period)

        # read sources file
        _LOG.info("Start loading variable sources from %r",
                  self.config.sources_file)
        var_sources = numpy.load(self.config.sources_file)
        _LOG.info("Finished loading variable sources, count = %s",
                  len(var_sources))

        # diaObjectId for last new DIA object, for variable sources we use their
        # index as objectId, for transients we want to use ID outside that range
        if last_visit is not None and last_visit.lastObjectId is not None:
            self.lastObjectId = max(self.lastObjectId, last_visit.lastObjectId)
        if self.lastObjectId < len(var_sources):
            _LOG.error('next object id is too low: %s', self.lastObjectId)
            return 1
        _LOG.debug("lastObjectId: %s", self.lastObjectId)

        # diaSourceId for last DIA source stored in database
        if last_visit is not None and last_visit.lastSourceId is not None:
            self.lastSourceId = max(self.lastSourceId, last_visit.lastSourceId)
        _LOG.info("lastSourceId: %s", self.lastSourceId)

        # loop over visits
        visitTimes = _visitTimes(start_time, self.config.interval,
                                 self.args.num_visits)
        for visit_id, dt in enumerate(visitTimes, start_visit_id):

            if visit_id % 1000 == 0:
                _LOG.info(COLOR_YELLOW + "+++ Start daily activities" +
                          COLOR_RESET)
                db.dailyJob()
                _LOG.info(COLOR_YELLOW + "+++ Done with daily activities" +
                          COLOR_RESET)

            _LOG.info(
                COLOR_GREEN + "+++ Start processing visit %s at %s" +
                COLOR_RESET, visit_id, dt)
            loop_timer = timer.Timer().start()

            with timer.Timer("DIA"):
                # point telescope in random southern direction
                pointing_xyz = generators.rand_sphere_xyz(1, -1)[0]
                pointing_v = UnitVector3d(pointing_xyz[0], pointing_xyz[1],
                                          pointing_xyz[2])
                ra = LonLat.longitudeOf(pointing_v).asDegrees()
                decl = LonLat.latitudeOf(pointing_v).asDegrees()

                # sphgeom.Circle opening angle is actually a half of opening angle
                region = Circle(pointing_v, Angle(self.config.FOV_rad / 2))

                _LOG.info("Pointing ra, decl = %s, %s; xyz = %s", ra, decl,
                          pointing_xyz)

                # Simulating difference image analysis
                dia = DIA.DIA(
                    pointing_xyz, self.config.FOV_rad, var_sources,
                    self.config.false_per_visit +
                    self.config.transient_per_visit)
                sources, indices = dia.makeSources()
                _LOG.info("DIA generated %s sources", len(sources))

                # assign IDs to transients
                for i in range(len(sources)):
                    if indices[i] < 0:
                        self.lastObjectId += 1
                        indices[i] = self.lastObjectId

            # print current database row counts, this takes long time
            # so only do it once in a while
            modu = 200 if visit_id <= 10000 else 1000
            if visit_id % modu == 0:
                if hasattr(db, "tableRowCount"):
                    counts = db.tableRowCount()  # type: ignore
                    for tbl, count in sorted(counts.items()):
                        _LOG.info('%s row count: %s', tbl, count)

            # numpy seems to do some multi-threaded stuff which "leaks" CPU cycles to the code below
            # and it gets counted as resource usage in timers, add a short delay here so that threads
            # finish and don't influence our timers below.
            time.sleep(0.1)

            if self.config.divide == 1:

                # do it in-process
                with timer.Timer("VisitProcessing"):
                    self.visit(db, visit_id, dt, region, sources, indices)

            else:

                if self.config.mp_mode == "fork":

                    tiles = geom.make_tiles(self.config.FOV_rad,
                                            self.config.divide, pointing_v)

                    with timer.Timer("VisitProcessing"):
                        # spawn subprocesses to handle individual tiles
                        children = []
                        for ix, iy, region in tiles:

                            # make sure lastSourceId is unique in in each process
                            self.lastSourceId += len(sources)
                            tile = (ix, iy)

                            pid = os.fork()
                            if pid == 0:
                                # child

                                self.visit(db, visit_id, dt, region, sources,
                                           indices, tile)
                                # stop here
                                sys.exit(0)

                            else:
                                _LOG.debug("Forked process %d for tile %s",
                                           pid, tile)
                                children.append(pid)

                        # wait until all children finish
                        for pid in children:
                            try:
                                pid, status = os.waitpid(pid, 0)
                                if status != 0:
                                    _LOG.warning(
                                        COLOR_RED +
                                        "Child process PID=%s failed: %s" +
                                        COLOR_RESET, pid, status)
                            except OSError as exc:
                                _LOG.warning(
                                    COLOR_RED + "wait failed for PID=%s: %s" +
                                    COLOR_RESET, pid, exc)

                elif self.config.mp_mode == "mpi":

                    tiles = geom.make_tiles(self.config.FOV_rad,
                                            self.config.divide, pointing_v)
                    _LOG.info("Split FOV into %d tiles for MPI", len(tiles))

                    # spawn subprocesses to handle individual tiles, special
                    # care needed for self.lastSourceId because it's
                    # propagated back from (0, 0)
                    lastSourceId = self.lastSourceId
                    tile_data = []
                    for ix, iy, region in tiles:
                        lastSourceId += len(sources)
                        tile = (ix, iy)
                        tile_data += [(visit_id, dt, region, sources, indices,
                                       tile, lastSourceId)]
                        # make sure lastSourceId is unique in in each process

                    with timer.Timer("VisitProcessing"):
                        _LOG.info("Scatter sources to %d tile processes",
                                  len(tile_data))
                        self.run_mpi_tile(db, MPI.COMM_WORLD, tile_data)
                    self.lastSourceId = lastSourceId

            if not self.args.no_update:
                # store last visit info
                visitInfoStore.saveVisit(visit_id, dt, self.lastObjectId,
                                         self.lastSourceId)

            _LOG.info(
                COLOR_BLUE + "--- Finished processing visit %s, time: %s" +
                COLOR_RESET, visit_id, loop_timer)

        # stop MPI slaves
        if num_tiles > 1 and self.config.mp_mode == "mpi":
            _LOG.info("Stopping MPI tile processes")
            tile_data_stop = [None] * self.config.divide**2
            self.run_mpi_tile(db, MPI.COMM_WORLD, tile_data_stop)

        return 0
Ejemplo n.º 29
0
    def index(self, exposure_or_metadata, data_id, database):
        """Spatially index an |exposure| or |metadata| object.

        Parameters
        ----------

        exposure_or_metadata : lsst.afw.image.Exposure[DFILU] or lsst.daf.base.PropertySet
            An afw |exposure| or corresponding |metadata| object.

        data_id : object
            An object identifying a single exposure (e.g. as used by the
            butler). It must be possible to pickle `data_id`.

        database : sqlite3.Connection or str
            A connection to (or filename of) a SQLite 3 database.

        Returns
        -------

        ``None``, unless the |defer_writes| coniguration parameter is ``True``.
        In that case, an :class:`.ExposureInfo` object containing a pickled
        data-id and an |encoded| |polygon| is returned.
        """
        # Get a pixel index bounding box for the exposure.
        if isinstance(exposure_or_metadata, daf_base.PropertySet):
            md = exposure_or_metadata
            # Map (LTV1, LTV2) to LSST (x0, y0). LSST convention says that
            # (x0, y0) is the location of the sub-image origin (the bottom-left
            # corner) relative to the origin of the parent, whereas LTVi encode
            # the origin of the parent relative to the origin of the subimage.
            pixel_bbox = afw_image.bboxFromMetadata(md)
            wcs = afw_image.makeWcs(md, False)
        else:
            pixel_bbox = exposure_or_metadata.getBBox()
            wcs = exposure_or_metadata.getWcs()
        # Pad the box by a configurable amount and bail if the result is empty.
        pixel_bbox.grow(self.config.pad_pixels)
        if pixel_bbox.isEmpty():
            self.log.warn("skipping exposure indexing for dataId=%s: "
                          "empty bounding box", data_id)
            return
        corners = []
        for c in pixel_bbox.getCorners():
            # Convert the box corners from pixel indexes to pixel positions,
            # and then to sky coordinates.
            c = wcs.pixelToSky(afw_image.indexToPosition(c.getX()),
                               afw_image.indexToPosition(c.getY()))
            c = (c.getLongitude().asRadians(), c.getLatitude().asRadians())
            # Bail if any coordinate is not finite.
            if any(math.isinf(x) or math.isnan(x) for x in c):
                self.log.warn("skipping exposure indexing for dataId=%s: "
                              "NaN or Inf in bounding box sky coordinate(s)"
                              " - bad WCS?", data_id)
                return
            # Convert from sky coordinates to unit vectors.
            corners.append(UnitVector3d(Angle.fromRadians(c[0]),
                                        Angle.fromRadians(c[1])))
        # Create a convex polygon containing the exposure pixels. When sphgeom
        # gains support for non-convex polygons, this could be changed to map
        # exposure.getPolygon() to a spherical equivalent, or to subdivide box
        # edges in pixel space to account for non linear projections. This
        # would have higher accuracy than the current approach of connecting
        # corner sky coordinates with great circles.
        poly = ConvexPolygon(corners)
        # Finally, persist or return the exposure information.
        info = ExposureInfo(pickle.dumps(data_id), poly.encode())
        if self.config.defer_writes:
            return info
        store_exposure_info(database, self.config.allow_replace, info)
Ejemplo n.º 30
0
 def test_comparison_operators(self):
     e = Ellipse(UnitVector3d.X(), UnitVector3d.Y(), Angle(2 * math.pi / 3))
     f = Ellipse(UnitVector3d.X(), Angle(math.pi / 3), Angle(math.pi / 6),
                 Angle(0))
     self.assertEqual(e, e)
     self.assertNotEqual(e, f)
Ejemplo n.º 31
0
 def testString(self):
     self.assertEqual(str(Angle(1)), '1.0')
     self.assertEqual(repr(Angle(1)), 'Angle(1.0)')
     a = Angle(2.5)
     self.assertEqual(a, eval(repr(a), dict(Angle=Angle)))
Ejemplo n.º 32
0
 def test_yaml(self):
     a = Ellipse(UnitVector3d.X(), UnitVector3d.Y(), Angle(2 * math.pi / 3))
     b = yaml.safe_load(yaml.dump(a))
     self.assertEqual(a, b)
Ejemplo n.º 33
0
 def test_pickle(self):
     a = Ellipse(UnitVector3d.X(), UnitVector3d.Y(), Angle(2 * math.pi / 3))
     b = pickle.loads(pickle.dumps(a, pickle.HIGHEST_PROTOCOL))
     self.assertEqual(a, b)
Ejemplo n.º 34
0
 def testPickle(self):
     a = Angle(1.5)
     b = pickle.loads(pickle.dumps(a))
     self.assertEqual(a, b)