def solve_image_arlexecute(vis: Visibility, model: Image, components=None, context='2d', **kwargs) -> \
        (Visibility, Image, Image):
    """Solve for image using deconvolve_cube and specified predict, invert

    This is the same as a majorcycle/minorcycle algorithm. The components are removed prior to deconvolution.
    
    See also arguments for predict, invert, deconvolve_cube functions.2d

    :param vis:
    :param model: Model image
    :param predict: Predict function e.g. predict_2d, predict_wstack
    :param invert: Invert function e.g. invert_2d, invert_wstack
    :return: Visibility, model
    """
    nmajor = get_parameter(kwargs, 'nmajor', 5)
    thresh = get_parameter(kwargs, "threshold", 0.0)
    log.info("solve_image_arlexecute: Performing %d major cycles" % nmajor)
    
    # The model is added to each major cycle and then the visibilities are
    # calculated from the full model
    vispred = copy_visibility(vis, zero=True)
    visres = copy_visibility(vis, zero=True)

    vispred = predict_arlexecute(vispred, model, context=context, **kwargs)
    
    if components is not None:
        vispred = predict_skycomponent_visibility(vispred, components)
    
    visres.data['vis'] = vis.data['vis'] - vispred.data['vis']
    dirty, sumwt = invert_arlexecute(visres, model, context=context, dopsf=False, **kwargs)
    assert sumwt.any() > 0.0, "Sum of weights is zero"
    psf, sumwt = invert_arlexecute(visres, model, context=context, dopsf=True, **kwargs)
    assert sumwt.any() > 0.0, "Sum of weights is zero"
    
    for i in range(nmajor):
        log.info("solve_image_arlexecute: Start of major cycle %d" % i)
        cc, res = deconvolve_cube(dirty, psf, **kwargs)
        model.data += cc.data
        vispred.data['vis'][...]=0.0
        vispred = predict_arlexecute(vispred, model, context=context, **kwargs)
        visres.data['vis'] = vis.data['vis'] - vispred.data['vis']
        dirty, sumwt = invert_arlexecute(visres, model, context=context, dopsf=False, **kwargs)
        if numpy.abs(dirty.data).max() < 1.1 * thresh:
            log.info("Reached stopping threshold %.6f Jy" % thresh)
            break
        log.info("solve_image_arlexecute: End of minor cycles")

    log.info("solve_image_arlexecute: End of major cycles")
    return visres, model, dirty
    def _predict_base(self, fluxthreshold=1.0, name='predict_ng', **kwargs):

        from processing_components.imaging.ng import predict_ng, invert_ng
        original_vis = copy_visibility(self.blockvis)
        vis = predict_ng(self.blockvis,
                         self.model,
                         verbosity=self.verbosity,
                         **kwargs)
        vis.data['vis'] = vis.data['vis'] - original_vis.data['vis']
        dirty = invert_ng(vis,
                          self.model,
                          dopsf=False,
                          normalize=True,
                          verbosity=self.verbosity,
                          **kwargs)

        # import matplotlib.pyplot as plt
        # from processing_components.image.operations import show_image
        # npol = dirty[0].shape[1]
        # for pol in range(npol):
        #     plt.clf()
        #     show_image(dirty[0], pol=pol)
        #     plt.show(block=False)

        if self.persist:
            export_image_to_fits(
                dirty[0],
                '%s/test_imaging_ng_%s_residual.fits' % (self.dir, name))

        # assert numpy.max(numpy.abs(dirty[0].data)), "Residual image is empty"

        maxabs = numpy.max(numpy.abs(dirty[0].data))
        assert maxabs < fluxthreshold, "Error %.3f greater than fluxthreshold %.3f " % (
            maxabs, fluxthreshold)
Пример #3
0
 def core_solve(self,
                spf,
                dpf,
                phase_error=0.1,
                amplitude_error=0.0,
                leakage=0.0,
                phase_only=True,
                niter=200,
                crosspol=False,
                residual_tol=1e-6,
                f=None,
                vnchan=3):
     if f is None:
         f = [100.0, 50.0, -10.0, 40.0]
     self.actualSetup(spf, dpf, f=f, vnchan=vnchan)
     gt = create_gaintable_from_blockvisibility(self.vis)
     log.info("Created gain table: %s" % (gaintable_summary(gt)))
     gt = simulate_gaintable(gt,
                             phase_error=phase_error,
                             amplitude_error=amplitude_error,
                             leakage=leakage)
     original = copy_visibility(self.vis)
     vis = apply_gaintable(self.vis, gt)
     gtsol = solve_gaintable(self.vis,
                             original,
                             phase_only=phase_only,
                             niter=niter,
                             crosspol=crosspol,
                             tol=1e-6)
     vis = apply_gaintable(vis, gtsol, inverse=True)
     residual = numpy.max(gtsol.residual)
     assert residual < residual_tol, "%s %s Max residual = %s" % (spf, dpf,
                                                                  residual)
     log.debug(qa_gaintable(gt))
     assert numpy.max(numpy.abs(gtsol.gain - 1.0)) > 0.1
Пример #4
0
 def zero(vis):
     if vis is not None:
         zerovis = copy_visibility(vis)
         zerovis.data['vis'][...] = 0.0
         return zerovis
     else:
         return None
Пример #5
0
 def subtract_vis(vis, model_vis):
     if vis is not None and model_vis is not None:
         assert vis.vis.shape == model_vis.vis.shape
         subvis = copy_visibility(vis)
         subvis.data['vis'][...] -= model_vis.data['vis'][...]
         return subvis
     else:
         return None
 def test_copy_visibility(self):
     self.vis = create_visibility(self.lowcore, self.times, self.frequency,
                                  channel_bandwidth=self.channel_bandwidth, phasecentre=self.phasecentre, weight=1.0,
                                  polarisation_frame=PolarisationFrame("stokesIQUV"))
     vis = copy_visibility(self.vis)
     self.vis.data['vis'] = 0.0
     vis.data['vis'] = 1.0
     assert (vis.data['vis'][0, 0].real == 1.0)
     assert (self.vis.data['vis'][0, 0].real == 0.0)
 def test_apply_gaintable_null(self):
     for spf, dpf in[('stokesI', 'stokesI'), ('stokesIQUV', 'linear'), ('stokesIQUV', 'circular')]:
         self.actualSetup(spf, dpf)
         gt = create_gaintable_from_blockvisibility(self.vis, timeslice='auto')
         gt.data['gain']*=0.0
         original = copy_visibility(self.vis)
         vis = apply_gaintable(self.vis, gt, inverse=True)
         error = numpy.max(numpy.abs(vis.vis[:,0,1,...] - original.vis[:,0,1,...]))
         assert error < 1e-12, "Error = %s" % (error)
 def test_apply_gaintable_only(self):
     for spf, dpf in[('stokesI', 'stokesI'), ('stokesIQUV', 'linear'), ('stokesIQUV', 'circular')]:
         self.actualSetup(spf, dpf)
         gt = create_gaintable_from_blockvisibility(self.vis, timeslice='auto')
         log.info("Created gain table: %s" % (gaintable_summary(gt)))
         gt = simulate_gaintable(gt, phase_error=0.1, amplitude_error=0.01)
         original = copy_visibility(self.vis)
         vis = apply_gaintable(self.vis, gt)
         error = numpy.max(numpy.abs(vis.vis - original.vis))
         assert error > 10.0, "Error = %f" % (error)
 def test_solve_gaintable_scalar_bandpass(self):
     self.actualSetup('stokesI', 'stokesI', f=[100.0], vnchan=128)
     gt = create_gaintable_from_blockvisibility(self.vis)
     log.info("Created gain table: %s" % (gaintable_summary(gt)))
     gt = simulate_gaintable(gt, phase_error=10.0, amplitude_error=0.01, smooth_channels=8)
     original = copy_visibility(self.vis)
     self.vis = apply_gaintable(self.vis, gt)
     gtsol = solve_gaintable(self.vis, original, phase_only=False, niter=200)
     residual = numpy.max(gtsol.residual)
     assert residual < 3e-8, "Max residual = %s" % (residual)
     assert numpy.max(numpy.abs(gtsol.gain - 1.0)) > 0.1
 def test_solve_gaintable_scalar_timeslice(self):
     self.actualSetup('stokesI', 'stokesI', f=[100.0], ntimes=10)
     gt = create_gaintable_from_blockvisibility(self.vis, timeslice=120.0)
     log.info("Created gain table: %s" % (gaintable_summary(gt)))
     gt = simulate_gaintable(gt, phase_error=10.0, amplitude_error=0.0)
     original = copy_visibility(self.vis)
     self.vis = apply_gaintable(self.vis, gt)
     gtsol = solve_gaintable(self.vis, original, phase_only=True, niter=200)
     residual = numpy.max(gtsol.residual)
     assert residual < 3e-8, "Max residual = %s" % (residual)
     assert numpy.max(numpy.abs(gtsol.gain - 1.0)) > 0.1
 def test_solve_gaintable_scalar_normalise(self):
     self.actualSetup('stokesI', 'stokesI', f=[100.0])
     gt = create_gaintable_from_blockvisibility(self.vis)
     log.info("Created gain table: %s" % (gaintable_summary(gt)))
     gt = simulate_gaintable(gt, phase_error=0.0, amplitude_error=0.1)
     gt.data['gain'] *= 2.0
     original = copy_visibility(self.vis)
     self.vis = apply_gaintable(self.vis, gt)
     gtsol = solve_gaintable(self.vis, original, phase_only=False, niter=200, normalise_gains=True)
     residual = numpy.max(gtsol.residual)
     assert residual < 3e-8, "Max residual = %s" % (residual)
     assert numpy.max(numpy.abs(gtsol.gain - 1.0)) > 0.1
 def test_create_gaintable_from_visibility_interval(self):
     for timeslice in [10.0, 'auto', 1e5]:
         for spf, dpf in[('stokesIQUV', 'linear')]:
             self.actualSetup(spf, dpf)
             gt = create_gaintable_from_blockvisibility(self.vis, timeslice=timeslice)
             log.info("Created gain table: %s" % (gaintable_summary(gt)))
             gt = simulate_gaintable(gt, phase_error=1.0)
             original = copy_visibility(self.vis)
             vis = apply_gaintable(self.vis, gt)
             assert numpy.max(numpy.abs(original.vis)) > 0.0
             assert numpy.max(numpy.abs(vis.vis)) > 0.0
             assert numpy.max(numpy.abs(vis.vis - original.vis)) > 0.0
Пример #13
0
 def test_addnoise_blockvisibility(self):
     self.vis = create_blockvisibility(
         self.config,
         self.times,
         self.frequency,
         phasecentre=self.phasecentre,
         weight=1.0,
         polarisation_frame=PolarisationFrame('stokesIQUV'),
         channel_bandwidth=self.channel_bandwidth)
     original = copy_visibility(self.vis)
     self.vis = addnoise_visibility(self.vis)
     actual = numpy.std(numpy.abs(self.vis.vis - original.vis))
     assert abs(actual - 0.01077958403015586) < 1e-4, actual
 def test_calibrate_T_function(self):
     self.actualSetup('stokesI', 'stokesI', f=[100.0])
     # Prepare the corrupted visibility data_models
     gt = create_gaintable_from_blockvisibility(self.vis)
     log.info("Created gain table: %s" % (gaintable_summary(gt)))
     gt = simulate_gaintable(gt, phase_error=10.0, amplitude_error=0.0)
     original = copy_visibility(self.vis)
     self.vis = apply_gaintable(self.vis, gt, vis_slices=None)
     # Now get the control dictionary and calibrate
     controls = create_calibration_controls()
     controls['T']['first_selfcal'] = 0
     calibrated_vis, gaintables = calibrate_function(
         self.vis, original, calibration_context='T', controls=controls)
     residual = numpy.max(gaintables['T'].residual)
     assert residual < 1e-8, "Max T residual = %s" % (residual)
def sum_predict_results(results):
    """ Sum a set of predict results of the same shape

    :param results: List of visibilities to be summed
    :return: summed visibility
    """
    sum_results = None
    for result in results:
        if result is not None:
            if sum_results is None:
                sum_results = copy_visibility(result)
            else:
                assert sum_results.data['vis'].shape == result.data['vis'].shape
                sum_results.data['vis'] += result.data['vis']
    
    return sum_results
def predict_serial(vis, model: Image, context='2d', vis_slices=1, facets=1, overlap=0, taper=None,
                   **kwargs) -> Visibility:
    """Predict visibilities using algorithm specified by context
    
     * 2d: Two-dimensional transform
     * wstack: wstacking with either vis_slices or wstack (spacing between w planes) set
     * wprojection: w projection with wstep (spacing between w places) set, also kernel='wprojection'
     * timeslice: snapshot imaging with either vis_slices or timeslice set. timeslice='auto' does every time
     * facets: Faceted imaging with facets facets on each axis
     * facets_wprojection: facets AND wprojection
     * facets_wstack: facets AND wstacking
     * wprojection_wstack: wprojection and wstacking

    
    :param vis:
    :param model: Model image, used to determine image characteristics
    :param context: Imaging context e.g. '2d', 'timeslice', etc.
    :param inner: Inner loop 'vis'|'image'
    :param kwargs:
    :return:


    """
    c = imaging_context(context)
    vis_iter = c['vis_iterator']
    predict = c['predict']
    
    if not isinstance(vis, Visibility):
        svis = convert_blockvisibility_to_visibility(vis)
    else:
        svis = vis
    
    result = copy_visibility(vis, zero=True)
    
    for rows in vis_iter(svis, vis_slices=vis_slices):
        if numpy.sum(rows):
            visslice = create_visibility_from_rows(svis, rows)
            visslice.data['vis'][...] = 0.0
            for dpatch in image_scatter_facets(model, facets=facets, overlap=overlap, taper=taper):
                result.data['vis'][...] = 0.0
                result = predict(visslice, dpatch, **kwargs)
                svis.data['vis'][rows] += result.data['vis']

    if not isinstance(vis, Visibility):
        svis = convert_visibility_to_blockvisibility(svis)

    return svis
def rcal_serial(vis: BlockVisibility, components, **kwargs) -> GainTable:
    """ Real-time calibration pipeline.

    Reads visibilities through a BlockVisibility iterator, calculates model visibilities according to a
    component-based sky model, and performs calibration solution, writing a gaintable for each chunk of
    visibilities.

    :param vis: Visibility or Union(Visibility, Iterable)
    :param components: Component-based sky model
    :param kwargs: Parameters
    :return: gaintable
   """

    if not isinstance(vis, collections.Iterable):
        vis = [vis]

    for ichunk, vischunk in enumerate(vis):
        vispred = copy_visibility(vischunk, zero=True)
        vispred = predict_skycomponent_visibility(vispred, components)
        gt = solve_gaintable(vischunk, vispred, **kwargs)
        yield gt
    def test_create_vis_iter(self):
        vis_iter = create_blockvisibility_iterator(
            self.config,
            self.times,
            self.frequency,
            channel_bandwidth=self.channel_bandwidth,
            phasecentre=self.phasecentre,
            weight=1.0,
            polarisation_frame=PolarisationFrame('stokesI'),
            integration_time=30.0,
            number_integrations=3)

        fullvis = None
        totalnvis = 0
        for i, vis in enumerate(vis_iter):
            assert vis.nvis
            if i == 0:
                fullvis = copy_visibility(vis)
                totalnvis = vis.nvis
            else:
                fullvis = append_visibility(fullvis, vis)
                totalnvis += vis.nvis

        assert fullvis.nvis == totalnvis
    def actualSetup(self,
                    vnchan=1,
                    doiso=True,
                    ntimes=5,
                    flux_limit=2.0,
                    zerow=True,
                    fixed=False):

        nfreqwin = vnchan
        rmax = 300.0
        npixel = 512
        cellsize = 0.001
        frequency = numpy.linspace(0.8e8, 1.2e8, nfreqwin)
        if nfreqwin > 1:
            channel_bandwidth = numpy.array(nfreqwin *
                                            [frequency[1] - frequency[0]])
        else:
            channel_bandwidth = [0.4e8]
        times = numpy.linspace(-numpy.pi / 3.0, numpy.pi / 3.0, ntimes)

        phasecentre = SkyCoord(ra=-60.0 * u.deg,
                               dec=-60.0 * u.deg,
                               frame='icrs',
                               equinox='J2000')

        lowcore = create_named_configuration('LOWBD2', rmax=rmax)

        block_vis = create_blockvisibility(
            lowcore,
            times,
            frequency=frequency,
            channel_bandwidth=channel_bandwidth,
            weight=1.0,
            phasecentre=phasecentre,
            polarisation_frame=PolarisationFrame("stokesI"),
            zerow=zerow)

        block_vis.data['uvw'][..., 2] = 0.0
        self.beam = create_image_from_visibility(
            block_vis,
            npixel=npixel,
            frequency=[numpy.average(frequency)],
            nchan=nfreqwin,
            channel_bandwidth=[numpy.sum(channel_bandwidth)],
            cellsize=cellsize,
            phasecentre=phasecentre)

        self.components = create_low_test_skycomponents_from_gleam(
            flux_limit=flux_limit,
            phasecentre=phasecentre,
            frequency=frequency,
            polarisation_frame=PolarisationFrame('stokesI'),
            radius=npixel * cellsize)
        self.beam = create_low_test_beam(self.beam)
        self.components = apply_beam_to_skycomponent(self.components,
                                                     self.beam,
                                                     flux_limit=flux_limit)

        self.vis = copy_visibility(block_vis, zero=True)
        gt = create_gaintable_from_blockvisibility(block_vis, timeslice='auto')
        for i, sc in enumerate(self.components):
            if sc.flux[0, 0] > 10:
                sc.flux[...] /= 10.0
            component_vis = copy_visibility(block_vis, zero=True)
            gt = simulate_gaintable(gt,
                                    amplitude_error=0.0,
                                    phase_error=0.1,
                                    seed=None)
            component_vis = predict_skycomponent_visibility(component_vis, sc)
            component_vis = apply_gaintable(component_vis, gt)
            self.vis.data['vis'][...] += component_vis.data['vis'][...]

        # Do an isoplanatic selfcal
        self.model_vis = copy_visibility(self.vis, zero=True)
        self.model_vis = predict_skycomponent_visibility(
            self.model_vis, self.components)
        if doiso:
            gt = solve_gaintable(self.vis,
                                 self.model_vis,
                                 phase_only=True,
                                 timeslice='auto')
            self.vis = apply_gaintable(self.vis, gt, inverse=True)

        self.model_vis = convert_blockvisibility_to_visibility(self.model_vis)
        self.model_vis, _, _ = weight_visibility(self.model_vis, self.beam)
        self.dirty_model, sumwt = invert_function(self.model_vis,
                                                  self.beam,
                                                  context='2d')
        export_image_to_fits(self.dirty_model,
                             "%s/test_skymodel-model_dirty.fits" % self.dir)

        lvis = convert_blockvisibility_to_visibility(self.vis)
        lvis, _, _ = weight_visibility(lvis, self.beam)
        dirty, sumwt = invert_function(lvis, self.beam, context='2d')
        if doiso:
            export_image_to_fits(
                dirty, "%s/test_skymodel-initial-iso-residual.fits" % self.dir)
        else:
            export_image_to_fits(
                dirty,
                "%s/test_skymodel-initial-noiso-residual.fits" % self.dir)

        self.skymodels = [
            SkyModel(components=[cm], fixed=fixed) for cm in self.components
        ]
def ical_serial(block_vis: BlockVisibility,
                model: Image,
                components=None,
                context='2d',
                controls=None,
                **kwargs):
    """ Post observation image, deconvolve, and self-calibrate

    :param vis:
    :param model: Model image
    :param components: Initial components
    :param context: Imaging context
    :param controls: calibration controls dictionary
    :return: model, residual, restored
    """
    nmajor = get_parameter(kwargs, 'nmajor', 5)
    log.info("ical_serial: Performing %d major cycles" % nmajor)

    do_selfcal = get_parameter(kwargs, "do_selfcal", False)

    if controls is None:
        controls = create_calibration_controls(**kwargs)

    # The model is added to each major cycle and then the visibilities are
    # calculated from the full model
    vis = convert_blockvisibility_to_visibility(block_vis)
    block_vispred = copy_visibility(block_vis, zero=True)
    vispred = convert_blockvisibility_to_visibility(block_vispred)
    vispred.data['vis'][...] = 0.0
    visres = copy_visibility(vispred)

    vispred = predict_serial(vispred, model, context=context, **kwargs)

    if components is not None:
        vispred = predict_skycomponent_visibility(vispred, components)

    if do_selfcal:
        vis, gaintables = calibrate_function(vis,
                                             vispred,
                                             'TGB',
                                             controls,
                                             iteration=-1)

    visres.data['vis'] = vis.data['vis'] - vispred.data['vis']
    dirty, sumwt = invert_serial(visres, model, context=context, **kwargs)
    log.info("Maximum in residual image is %.6f" %
             (numpy.max(numpy.abs(dirty.data))))

    psf, sumwt = invert_serial(visres,
                               model,
                               dopsf=True,
                               context=context,
                               **kwargs)

    thresh = get_parameter(kwargs, "threshold", 0.0)

    for i in range(nmajor):
        log.info("ical_serial: Start of major cycle %d of %d" % (i, nmajor))
        cc, res = deconvolve_cube(dirty, psf, **kwargs)
        model.data += cc.data
        vispred.data['vis'][...] = 0.0
        vispred = predict_serial(vispred, model, context=context, **kwargs)
        if do_selfcal:
            vis, gaintables = calibrate_function(vis,
                                                 vispred,
                                                 'TGB',
                                                 controls,
                                                 iteration=i)
        visres.data['vis'] = vis.data['vis'] - vispred.data['vis']

        dirty, sumwt = invert_serial(visres, model, context=context, **kwargs)
        log.info("Maximum in residual image is %s" %
                 (numpy.max(numpy.abs(dirty.data))))
        if numpy.abs(dirty.data).max() < 1.1 * thresh:
            log.info("ical_serial: Reached stopping threshold %.6f Jy" %
                     thresh)
            break
        log.info("ical_serial: End of major cycle")

    log.info("ical_serial: End of major cycles")
    restored = restore_cube(model, psf, dirty, **kwargs)

    return model, dirty, restored