Ejemplo n.º 1
0
class TestLightModel(object):
    """
    tests the source model routines
    """

    def setup(self):
        self.light_model_list = ['GAUSSIAN', 'MULTI_GAUSSIAN', 'SERSIC', 'SERSIC_ELLIPSE', 'DOUBLE_SERSIC',
                                 'CORE_SERSIC', 'DOUBLE_CORE_SERSIC', 'BULDGE_DISK', 'SHAPELETS', 'HERNQUIST',
                                 'HERNQUIST_ELLIPSE', 'PJAFFE', 'PJAFFE_ELLIPSE', 'UNIFORM', 'NONE'
                                 ]
        self.kwargs = [
            {'amp': 1., 'sigma_x': 1, 'sigma_y': 1., 'center_x': 0, 'center_y': 0},  # 'GAUSSIAN'
            {'amp': [1., 2], 'sigma': [1, 3], 'center_x': 0, 'center_y': 0},  # 'MULTI_GAUSSIAN'
            {'I0_sersic': 1, 'R_sersic': 0.5, 'n_sersic': 1, 'center_x': 0, 'center_y': 0},  # 'SERSIC'
            {'I0_sersic': 1, 'R_sersic': 0.5, 'n_sersic': 1, 'q': 0.8, 'phi_G': 0.5, 'center_x': 0, 'center_y': 0},  # 'SERSIC_ELLIPSE'
            {'I0_sersic': 1, 'R_sersic': 0.5, 'n_sersic': 1, 'q': 0.8, 'phi_G': 0.5, 'center_x': 0, 'center_y': 0,
             'I0_2': 1, 'R_2': 0.05, 'n_2': 2, 'phi_G_2': 0, 'q_2': 1},  # 'DOUBLE_SERSIC'
            {'I0_sersic': 1, 'R_sersic': 0.5, 'Re': 0.1, 'gamma': 2., 'n_sersic': 1, 'q': 0.8, 'phi_G': 0.5, 'center_x': 0, 'center_y': 0},
            # 'CORE_SERSIC'
            {'I0_sersic': 1, 'R_sersic': 0.5, 'Re': 0.1, 'gamma': 2., 'n_sersic': 1, 'q': 0.8, 'phi_G': 0.5,
             'center_x': 0, 'center_y': 0, 'I0_2': 1, 'R_2': 0.05, 'n_2': 2, 'phi_G_2': 0, 'q_2': 1},
            # 'DOUBLE_CORE_SERSIC'
            {'I0_b': 1, 'R_b': 0.1, 'phi_G_b': 0, 'q_b': 1, 'I0_d': 2, 'R_d': 1, 'phi_G_d': 0.5, 'q_d': 0.7, 'center_x': 0, 'center_y': 0},  # BULDGE_DISK
            {'amp': [1, 1, 1], 'beta': 0.5, 'n_max': 1, 'center_x': 0, 'center_y': 0},  # 'SHAPELETS'
            {'sigma0': 1, 'Rs': 0.5, 'center_x': 0, 'center_y': 0},  # 'HERNQUIST'
            {'sigma0': 1, 'Rs': 0.5, 'center_x': 0, 'center_y': 0, 'q': 0.8, 'phi_G': 0},  # 'HERNQUIST_ELLIPSE'
            {'sigma0': 1, 'Ra': 1, 'Rs': 0.5, 'center_x': 0, 'center_y': 0},  # 'PJAFFE'
            {'sigma0': 1, 'Ra': 1, 'Rs': 0.5, 'center_x': 0, 'center_y': 0, 'q': 0.8, 'phi_G': 0},  # 'PJAFFE_ELLIPSE'
            {'mean': 1},  # 'UNIFORM'
            {}]# 'NONE'

        self.LightModel = LightModel(light_model_list=self.light_model_list)

    def test_init(self):
        model_list = ['CORE_SERSIC', 'DOUBLE_CORE_SERSIC', 'BULDGE_DISK', 'SHAPELETS', 'UNIFORM']
        lightModel = LightModel(light_model_list=model_list)
        assert len(lightModel.profile_type_list) == len(model_list)

    def test_surface_brightness(self):
        output = self.LightModel.surface_brightness(x=1, y=1, kwargs_list=self.kwargs)
        npt.assert_almost_equal(output, 2.544428612985992, decimal=6)

    def test_surface_brightness_array(self):
        output = self.LightModel.surface_brightness(x=[1], y=[1], kwargs_list=self.kwargs)
        npt.assert_almost_equal(output[0], 2.544428612985992, decimal=6)

    def test_functions_split(self):
        output = self.LightModel.functions_split(x=1., y=1., kwargs_list=self.kwargs)
        assert output[0][0] == 0.058549831524319168

    def test_re_normalize_flux(self):
        kwargs_out = self.LightModel.re_normalize_flux(kwargs_list=self.kwargs, norm_factor=2)
        assert kwargs_out[0]['amp'] == 2 * self.kwargs[0]['amp']
Ejemplo n.º 2
0
 def test_raise(self):
     with self.assertRaises(ValueError):
         lighModel = LightModel(light_model_list=['WRONG'])
     with self.assertRaises(ValueError):
         lighModel = LightModel(light_model_list=['UNIFORM'])
         lighModel.light_3d(r=1, kwargs_list=[{'amp': 1}])
     with self.assertRaises(ValueError):
         lighModel = LightModel(light_model_list=['UNIFORM'])
         lighModel.profile_type_list = ['WRONG']
         lighModel.functions_split(x=0, y=0, kwargs_list=[{}])
     with self.assertRaises(ValueError):
         lighModel = LightModel(light_model_list=['UNIFORM'])
         lighModel.profile_type_list = ['WRONG']
         lighModel.num_param_linear(kwargs_list=[{}])
     with self.assertRaises(ValueError):
         lighModel = LightModel(light_model_list=['UNIFORM'])
         lighModel.profile_type_list = ['WRONG']
         lighModel.update_linear(param=[1], i=0, kwargs_list=[{}])
     with self.assertRaises(ValueError):
         lighModel = LightModel(light_model_list=['UNIFORM'])
         lighModel.profile_type_list = ['WRONG']
         lighModel.total_flux(kwargs_list=[{}])
Ejemplo n.º 3
0
class TestLightModel(object):
    """
    tests the source model routines
    """
    def setup(self):
        self.light_model_list = [
            'GAUSSIAN', 'MULTI_GAUSSIAN', 'SERSIC', 'SERSIC_ELLIPSE',
            'CORE_SERSIC', 'SHAPELETS', 'HERNQUIST', 'HERNQUIST_ELLIPSE',
            'PJAFFE', 'PJAFFE_ELLIPSE', 'UNIFORM', 'POWER_LAW', 'NIE',
            'INTERPOL', 'SHAPELETS_POLAR_EXP', 'ELLIPSOID'
        ]
        phi_G, q = 0.5, 0.8
        e1, e2 = param_util.phi_q2_ellipticity(phi_G, q)
        self.kwargs = [
            {
                'amp': 1.,
                'sigma': 1.,
                'center_x': 0,
                'center_y': 0
            },  # 'GAUSSIAN'
            {
                'amp': [1., 2],
                'sigma': [1, 3],
                'center_x': 0,
                'center_y': 0
            },  # 'MULTI_GAUSSIAN'
            {
                'amp': 1,
                'R_sersic': 0.5,
                'n_sersic': 1,
                'center_x': 0,
                'center_y': 0
            },  # 'SERSIC'
            {
                'amp': 1,
                'R_sersic': 0.5,
                'n_sersic': 1,
                'e1': e1,
                'e2': e2,
                'center_x': 0,
                'center_y': 0
            },  # 'SERSIC_ELLIPSE'
            {
                'amp': 1,
                'R_sersic': 0.5,
                'Rb': 0.1,
                'gamma': 2.,
                'n_sersic': 1,
                'e1': e1,
                'e2': e2,
                'center_x': 0,
                'center_y': 0
            },
            # 'CORE_SERSIC'
            {
                'amp': [1, 1, 1],
                'beta': 0.5,
                'n_max': 1,
                'center_x': 0,
                'center_y': 0
            },  # 'SHAPELETS'
            {
                'amp': 1,
                'Rs': 0.5,
                'center_x': 0,
                'center_y': 0
            },  # 'HERNQUIST'
            {
                'amp': 1,
                'Rs': 0.5,
                'center_x': 0,
                'center_y': 0,
                'e1': e1,
                'e2': e2
            },  # 'HERNQUIST_ELLIPSE'
            {
                'amp': 1,
                'Ra': 1,
                'Rs': 0.5,
                'center_x': 0,
                'center_y': 0
            },  # 'PJAFFE'
            {
                'amp': 1,
                'Ra': 1,
                'Rs': 0.5,
                'center_x': 0,
                'center_y': 0,
                'e1': e1,
                'e2': e2
            },  # 'PJAFFE_ELLIPSE'
            {
                'amp': 1
            },  # 'UNIFORM'
            {
                'amp': 1.,
                'gamma': 2.,
                'e1': e1,
                'e2': e2,
                'center_x': 0,
                'center_y': 0
            },  # 'POWER_LAW'
            {
                'amp': .001,
                'e1': 0,
                'e2': 1.,
                'center_x': 0,
                'center_y': 0,
                's_scale': 1.
            },  # 'NIE'
            {
                'image': np.zeros((20, 5)),
                'scale': 1,
                'phi_G': 0,
                'center_x': 0,
                'center_y': 0
            },
            {
                'amp': [1],
                'n_max': 0,
                'beta': 1,
                'center_x': 0,
                'center_y': 0
            },
            {
                'amp': 1,
                'radius': 1.,
                'e1': 0,
                'e2': 0.1,
                'center_x': 0,
                'center_y': 0
            }  # 'ELLIPSOID'
        ]

        self.LightModel = LightModel(light_model_list=self.light_model_list)

    def test_init(self):
        model_list = [
            'CORE_SERSIC', 'SHAPELETS', 'SHAPELETS_POLAR',
            'SHAPELETS_POLAR_EXP', 'UNIFORM', 'CHAMELEON', 'DOUBLE_CHAMELEON',
            'TRIPLE_CHAMELEON'
        ]
        lightModel = LightModel(light_model_list=model_list)
        assert len(lightModel.profile_type_list) == len(model_list)

    def test_surface_brightness(self):
        output = self.LightModel.surface_brightness(x=1.,
                                                    y=1.,
                                                    kwargs_list=self.kwargs)
        npt.assert_almost_equal(output, 2.5886852663397137, decimal=6)

    def test_surface_brightness_array(self):
        output = self.LightModel.surface_brightness(x=[1],
                                                    y=[1],
                                                    kwargs_list=self.kwargs)
        npt.assert_almost_equal(output[0], 2.5886852663397137, decimal=6)

    def test_functions_split(self):
        output = self.LightModel.functions_split(x=1.,
                                                 y=1.,
                                                 kwargs_list=self.kwargs)
        npt.assert_almost_equal(output[0][0], 0.058549831524319168, decimal=6)

    def test_param_name_list(self):
        param_name_list = self.LightModel.param_name_list
        assert len(self.light_model_list) == len(param_name_list)

    def test_num_param_linear(self):
        num = self.LightModel.num_param_linear(self.kwargs, list_return=False)
        assert num == 19

        num_list = self.LightModel.num_param_linear(self.kwargs,
                                                    list_return=True)
        assert num_list[0] == 1

    def test_update_linear(self):
        response, n = self.LightModel.functions_split(1, 1, self.kwargs)
        param = np.ones(n) * 2
        kwargs_out, i = self.LightModel.update_linear(param,
                                                      i=0,
                                                      kwargs_list=self.kwargs)
        assert i == n
        assert kwargs_out[0]['amp'] == 2

    def test_total_flux(self):
        light_model_list = [
            'SERSIC', 'SERSIC_ELLIPSE', 'INTERPOL', 'GAUSSIAN',
            'GAUSSIAN_ELLIPSE', 'MULTI_GAUSSIAN', 'MULTI_GAUSSIAN_ELLIPSE'
        ]
        kwargs_list = [
            {
                'amp': 1,
                'R_sersic': 0.5,
                'n_sersic': 1,
                'center_x': 0,
                'center_y': 0
            },  # 'SERSIC'
            {
                'amp': 1,
                'R_sersic': 0.5,
                'n_sersic': 1,
                'e1': 0.1,
                'e2': 0,
                'center_x': 0,
                'center_y': 0
            },  # 'SERSIC_ELLIPSE'
            {
                'image': np.ones((20, 5)),
                'scale': 1,
                'phi_G': 0,
                'center_x': 0,
                'center_y': 0
            },  # 'INTERPOL'
            {
                'amp': 2,
                'sigma': 2,
                'center_x': 0,
                'center_y': 0
            },  # 'GAUSSIAN'
            {
                'amp': 2,
                'sigma': 2,
                'e1': 0.1,
                'e2': 0,
                'center_x': 0,
                'center_y': 0
            },  # 'GAUSSIAN_ELLIPSE'
            {
                'amp': [1, 1],
                'sigma': [2, 1],
                'center_x': 0,
                'center_y': 0
            },  # 'MULTI_GAUSSIAN'
            {
                'amp': [1, 1],
                'sigma': [2, 1],
                'e1': 0.1,
                'e2': 0,
                'center_x': 0,
                'center_y': 0
            }  # 'MULTI_GAUSSIAN_ELLIPSE'
        ]
        lightModel = LightModel(light_model_list=light_model_list)
        total_flux_list = lightModel.total_flux(kwargs_list)
        assert total_flux_list[2] == 100
        assert total_flux_list[3] == 2
        assert total_flux_list[4] == 2
        assert total_flux_list[5] == 2
        assert total_flux_list[6] == 2

        total_flux_list = lightModel.total_flux(kwargs_list, norm=True)
        assert total_flux_list[2] == 100
        assert total_flux_list[3] == 1
        assert total_flux_list[4] == 1
        assert total_flux_list[5] == 2
        assert total_flux_list[6] == 2

    def test_delete_interpol_caches(self):
        x, y = util.make_grid(numPix=20, deltapix=1.)
        gauss = Gaussian()
        flux = gauss.function(x, y, amp=1., center_x=0., center_y=0., sigma=1.)
        image = util.array2image(flux)

        light_model_list = ['INTERPOL', 'INTERPOL']
        kwargs_list = [{
            'image': image,
            'scale': 1,
            'phi_G': 0,
            'center_x': 0,
            'center_y': 0
        }, {
            'image': image,
            'scale': 1,
            'phi_G': 0,
            'center_x': 0,
            'center_y': 0
        }]
        lightModel = LightModel(light_model_list=light_model_list)
        output = lightModel.surface_brightness(x, y, kwargs_list)
        for func in lightModel.func_list:
            assert hasattr(func, '_image_interp')
        lightModel.delete_interpol_caches()
        for func in lightModel.func_list:
            assert not hasattr(func, '_image_interp')

    def test_check_positive_flux_profile(self):
        ligthModel = LightModel(light_model_list=['GAUSSIAN'])
        kwargs_list = [{'amp': 0, 'sigma': 1}]
        bool = ligthModel.check_positive_flux_profile(kwargs_list)
        assert bool

        kwargs_list = [{'amp': -1, 'sigma': 1}]
        bool = ligthModel.check_positive_flux_profile(kwargs_list)
        assert not bool
Ejemplo n.º 4
0
class TestLightModel(object):
    """
    tests the source model routines
    """
    def setup(self):
        self.light_model_list = [
            'GAUSSIAN', 'MULTI_GAUSSIAN', 'SERSIC', 'SERSIC_ELLIPSE',
            'CORE_SERSIC', 'SHAPELETS', 'HERNQUIST', 'HERNQUIST_ELLIPSE',
            'PJAFFE', 'PJAFFE_ELLIPSE', 'UNIFORM', 'POWER_LAW', 'NIE',
            'INTERPOL', 'SHAPELETS_POLAR_EXP'
        ]
        phi_G, q = 0.5, 0.8
        e1, e2 = param_util.phi_q2_ellipticity(phi_G, q)
        self.kwargs = [
            {
                'amp': 1.,
                'sigma_x': 1,
                'sigma_y': 1.,
                'center_x': 0,
                'center_y': 0
            },  # 'GAUSSIAN'
            {
                'amp': [1., 2],
                'sigma': [1, 3],
                'center_x': 0,
                'center_y': 0
            },  # 'MULTI_GAUSSIAN'
            {
                'amp': 1,
                'R_sersic': 0.5,
                'n_sersic': 1,
                'center_x': 0,
                'center_y': 0
            },  # 'SERSIC'
            {
                'amp': 1,
                'R_sersic': 0.5,
                'n_sersic': 1,
                'e1': e1,
                'e2': e2,
                'center_x': 0,
                'center_y': 0
            },  # 'SERSIC_ELLIPSE'
            {
                'amp': 1,
                'R_sersic': 0.5,
                'Re': 0.1,
                'gamma': 2.,
                'n_sersic': 1,
                'e1': e1,
                'e2': e2,
                'center_x': 0,
                'center_y': 0
            },
            # 'CORE_SERSIC'
            {
                'amp': [1, 1, 1],
                'beta': 0.5,
                'n_max': 1,
                'center_x': 0,
                'center_y': 0
            },  # 'SHAPELETS'
            {
                'amp': 1,
                'Rs': 0.5,
                'center_x': 0,
                'center_y': 0
            },  # 'HERNQUIST'
            {
                'amp': 1,
                'Rs': 0.5,
                'center_x': 0,
                'center_y': 0,
                'e1': e1,
                'e2': e2
            },  # 'HERNQUIST_ELLIPSE'
            {
                'amp': 1,
                'Ra': 1,
                'Rs': 0.5,
                'center_x': 0,
                'center_y': 0
            },  # 'PJAFFE'
            {
                'amp': 1,
                'Ra': 1,
                'Rs': 0.5,
                'center_x': 0,
                'center_y': 0,
                'e1': e1,
                'e2': e2
            },  # 'PJAFFE_ELLIPSE'
            {
                'amp': 1
            },  # 'UNIFORM'
            {
                'amp': 1.,
                'gamma': 2.,
                'e1': e1,
                'e2': e2,
                'center_x': 0,
                'center_y': 0
            },  # 'POWER_LAW'
            {
                'amp': .001,
                'e1': 0,
                'e2': 1.,
                'center_x': 0,
                'center_y': 0,
                's_scale': 1.
            },  # 'NIE'
            {
                'image': np.zeros((10, 10)),
                'scale': 1,
                'phi_G': 0,
                'center_x': 0,
                'center_y': 0
            },
            {
                'amp': [1],
                'n_max': 0,
                'beta': 1,
                'center_x': 0,
                'center_y': 0
            }
        ]

        self.LightModel = LightModel(light_model_list=self.light_model_list)

    def test_init(self):
        model_list = [
            'CORE_SERSIC', 'SHAPELETS', 'SHAPELETS_POLAR',
            'SHAPELETS_POLAR_EXP', 'UNIFORM', 'CHAMELEON', 'DOUBLE_CHAMELEON',
            'TRIPLE_CHAMELEON'
        ]
        lightModel = LightModel(light_model_list=model_list)
        assert len(lightModel.profile_type_list) == len(model_list)

    def test_surface_brightness(self):
        output = self.LightModel.surface_brightness(x=1,
                                                    y=1,
                                                    kwargs_list=self.kwargs)
        npt.assert_almost_equal(output, 3.7065728131855824, decimal=6)

    def test_surface_brightness_array(self):
        output = self.LightModel.surface_brightness(x=[1],
                                                    y=[1],
                                                    kwargs_list=self.kwargs)
        npt.assert_almost_equal(output[0], 3.7065728131855824, decimal=6)

    def test_functions_split(self):
        output = self.LightModel.functions_split(x=1.,
                                                 y=1.,
                                                 kwargs_list=self.kwargs)
        npt.assert_almost_equal(output[0][0], 0.058549831524319168, decimal=6)

    def test_re_normalize_flux(self):
        kwargs_out = self.LightModel.re_normalize_flux(kwargs_list=self.kwargs,
                                                       norm_factor=2)
        assert kwargs_out[0]['amp'] == 2 * self.kwargs[0]['amp']

    def test_param_name_list(self):
        param_name_list = self.LightModel.param_name_list()
        assert len(self.light_model_list) == len(param_name_list)

    def test_num_param_linear(self):
        num = self.LightModel.num_param_linear(self.kwargs, list_return=False)
        assert num == 18

        num_list = self.LightModel.num_param_linear(self.kwargs,
                                                    list_return=True)
        assert num_list[0] == 1

    def test_update_linear(self):
        response, n = self.LightModel.functions_split(1, 1, self.kwargs)
        param = np.ones(n) * 2
        kwargs_out, i = self.LightModel.update_linear(param,
                                                      i=0,
                                                      kwargs_list=self.kwargs)
        assert i == n
        assert kwargs_out[0]['amp'] == 2

    def test_total_flux(self):
        light_model_list = [
            'SERSIC', 'SERSIC_ELLIPSE', 'INTERPOL', 'GAUSSIAN',
            'GAUSSIAN_ELLIPSE', 'MULTI_GAUSSIAN', 'MULTI_GAUSSIAN_ELLIPSE'
        ]
        kwargs_list = [
            {
                'amp': 1,
                'R_sersic': 0.5,
                'n_sersic': 1,
                'center_x': 0,
                'center_y': 0
            },  # 'SERSIC'
            {
                'amp': 1,
                'R_sersic': 0.5,
                'n_sersic': 1,
                'e1': 0.1,
                'e2': 0,
                'center_x': 0,
                'center_y': 0
            },  # 'SERSIC_ELLIPSE'
            {
                'image': np.ones((10, 10)),
                'scale': 1,
                'phi_G': 0,
                'center_x': 0,
                'center_y': 0
            },  # 'INTERPOL'
            {
                'amp': 2,
                'sigma_x': 2,
                'sigma_y': 1,
                'center_x': 0,
                'center_y': 0
            },  # 'GAUSSIAN'
            {
                'amp': 2,
                'sigma': 2,
                'e1': 0.1,
                'e2': 0,
                'center_x': 0,
                'center_y': 0
            },  # 'GAUSSIAN_ELLIPSE'
            {
                'amp': [1, 1],
                'sigma': [2, 1],
                'center_x': 0,
                'center_y': 0
            },  # 'MULTI_GAUSSIAN'
            {
                'amp': [1, 1],
                'sigma': [2, 1],
                'e1': 0.1,
                'e2': 0,
                'center_x': 0,
                'center_y': 0
            }  # 'MULTI_GAUSSIAN_ELLIPSE'
        ]
        lightModel = LightModel(light_model_list=light_model_list)
        total_flux_list = lightModel.total_flux(kwargs_list)
        assert total_flux_list[2] == 100
        assert total_flux_list[3] == 2
        assert total_flux_list[4] == 2
        assert total_flux_list[5] == 2
        assert total_flux_list[6] == 2

        total_flux_list = lightModel.total_flux(kwargs_list, norm=True)
        assert total_flux_list[2] == 100
        assert total_flux_list[3] == 1
        assert total_flux_list[4] == 1
        assert total_flux_list[5] == 2
        assert total_flux_list[6] == 2
Ejemplo n.º 5
0
class LensAnalysis(object):
    """
    class to compute flux ratio anomalies, inherited from standard MakeImage
    """
    def __init__(self, kwargs_model):
        self.LensLightModel = LightModel(
            kwargs_model.get('lens_light_model_list', []))
        self.SourceModel = LightModel(
            kwargs_model.get('source_light_model_list', []))
        self.LensModel = LensModel(
            lens_model_list=kwargs_model.get('lens_model_list', []),
            z_source=kwargs_model.get('z_source', None),
            redshift_list=kwargs_model.get('redshift_list', None),
            multi_plane=kwargs_model.get('multi_plane', False))
        self._lensModelExtensions = LensModelExtensions(self.LensModel)
        self.PointSource = PointSource(point_source_type_list=kwargs_model.get(
            'point_source_model_list', []))
        self.kwargs_model = kwargs_model
        self.NumLensModel = NumericLens(
            lens_model_list=kwargs_model.get('lens_model_list', []))

    def fermat_potential(self, kwargs_lens, kwargs_ps):
        ra_pos, dec_pos = self.PointSource.image_position(
            kwargs_ps, kwargs_lens)
        ra_pos = ra_pos[0]
        dec_pos = dec_pos[0]
        ra_source, dec_source = self.LensModel.ray_shooting(
            ra_pos, dec_pos, kwargs_lens)
        ra_source = np.mean(ra_source)
        dec_source = np.mean(dec_source)
        fermat_pot = self.LensModel.fermat_potential(ra_pos, dec_pos,
                                                     ra_source, dec_source,
                                                     kwargs_lens)
        return fermat_pot

    def ellipticity_lens_light(self,
                               kwargs_lens_light,
                               center_x=0,
                               center_y=0,
                               model_bool_list=None,
                               deltaPix=None,
                               numPix=None):
        """
        make sure that the window covers all the light, otherwise the moments may give to low answers.

        :param kwargs_lens_light:
        :param center_x:
        :param center_y:
        :param model_bool_list:
        :param deltaPix:
        :param numPix:
        :return:
        """
        if model_bool_list is None:
            model_bool_list = [True] * len(kwargs_lens_light)
        if numPix is None:
            numPix = 100
        if deltaPix is None:
            deltaPix = 0.05
        x_grid, y_grid = util.make_grid(numPix=numPix, deltapix=deltaPix)
        x_grid += center_x
        y_grid += center_y
        I_xy = self._lens_light_internal(x_grid,
                                         y_grid,
                                         kwargs_lens_light,
                                         model_bool_list=model_bool_list)
        e1, e2 = analysis_util.ellipticities(I_xy, x_grid, y_grid)
        return e1, e2

    def half_light_radius_lens(self,
                               kwargs_lens_light,
                               center_x=0,
                               center_y=0,
                               model_bool_list=None,
                               deltaPix=None,
                               numPix=None):
        """
        computes numerically the half-light-radius of the deflector light and the total photon flux

        :param kwargs_lens_light:
        :return:
        """
        if model_bool_list is None:
            model_bool_list = [True] * len(kwargs_lens_light)
        if numPix is None:
            numPix = 1000
        if deltaPix is None:
            deltaPix = 0.05
        x_grid, y_grid = util.make_grid(numPix=numPix, deltapix=deltaPix)
        x_grid += center_x
        y_grid += center_y
        lens_light = self._lens_light_internal(x_grid,
                                               y_grid,
                                               kwargs_lens_light,
                                               model_bool_list=model_bool_list)
        R_h = analysis_util.half_light_radius(lens_light, x_grid, y_grid,
                                              center_x, center_y)
        return R_h

    def half_light_radius_source(self,
                                 kwargs_source,
                                 center_x=0,
                                 center_y=0,
                                 deltaPix=None,
                                 numPix=None):
        """
        computes numerically the half-light-radius of the deflector light and the total photon flux

        :param kwargs_source:
        :return:
        """
        if numPix is None:
            numPix = 1000
        if deltaPix is None:
            deltaPix = 0.005
        x_grid, y_grid = util.make_grid(numPix=numPix, deltapix=deltaPix)
        x_grid += center_x
        y_grid += center_y
        source_light = self.SourceModel.surface_brightness(
            x_grid, y_grid, kwargs_source)
        R_h = analysis_util.half_light_radius(source_light,
                                              x_grid,
                                              y_grid,
                                              center_x=center_x,
                                              center_y=center_y)
        return R_h

    def _lens_light_internal(self,
                             x_grid,
                             y_grid,
                             kwargs_lens_light,
                             model_bool_list=None):
        """
        evaluates only part of the light profiles

        :param x_grid:
        :param y_grid:
        :param kwargs_lens_light:
        :return:
        """
        if model_bool_list is None:
            model_bool_list = [True] * len(kwargs_lens_light)
        lens_light = np.zeros_like(x_grid)
        for i, bool in enumerate(model_bool_list):
            if bool is True:
                lens_light_i = self.LensLightModel.surface_brightness(
                    x_grid, y_grid, kwargs_lens_light, k=i)
                lens_light += lens_light_i
        return lens_light

    def multi_gaussian_lens_light(self,
                                  kwargs_lens_light,
                                  model_bool_list=None,
                                  e1=0,
                                  e2=0,
                                  n_comp=20,
                                  deltaPix=None,
                                  numPix=None):
        """
        multi-gaussian decomposition of the lens light profile (in 1-dimension)

        :param kwargs_lens_light:
        :param n_comp:
        :return:
        """
        if 'center_x' in kwargs_lens_light[0]:
            center_x = kwargs_lens_light[0]['center_x']
            center_y = kwargs_lens_light[0]['center_y']
        else:
            center_x, center_y = 0, 0
        r_h = self.half_light_radius_lens(kwargs_lens_light,
                                          center_x=center_x,
                                          center_y=center_y,
                                          model_bool_list=model_bool_list,
                                          deltaPix=deltaPix,
                                          numPix=numPix)
        r_array = np.logspace(-3, 2, 200) * r_h * 2
        x_coords, y_coords = param_util.transform_e1e2(r_array,
                                                       np.zeros_like(r_array),
                                                       e1=-e1,
                                                       e2=-e2)
        x_coords += center_x
        y_coords += center_y
        #r_array = np.logspace(-2, 1, 50) * r_h
        flux_r = self._lens_light_internal(x_coords,
                                           y_coords,
                                           kwargs_lens_light,
                                           model_bool_list=model_bool_list)
        amplitudes, sigmas, norm = mge.mge_1d(r_array, flux_r, N=n_comp)
        return amplitudes, sigmas, center_x, center_y

    def multi_gaussian_lens(self,
                            kwargs_lens,
                            model_bool_list=None,
                            e1=0,
                            e2=0,
                            n_comp=20):
        """
        multi-gaussian lens model in convergence space

        :param kwargs_lens:
        :param n_comp:
        :return:
        """
        if 'center_x' in kwargs_lens[0]:
            center_x = kwargs_lens[0]['center_x']
            center_y = kwargs_lens[0]['center_y']
        else:
            raise ValueError('no keyword center_x defined!')
        theta_E = self._lensModelExtensions.effective_einstein_radius(
            kwargs_lens)
        r_array = np.logspace(-4, 2, 200) * theta_E
        x_coords, y_coords = param_util.transform_e1e2(r_array,
                                                       np.zeros_like(r_array),
                                                       e1=-e1,
                                                       e2=-e2)
        x_coords += center_x
        y_coords += center_y
        #r_array = np.logspace(-2, 1, 50) * theta_E
        if model_bool_list is None:
            model_bool_list = [True] * len(kwargs_lens)
        kappa_s = np.zeros_like(r_array)
        for i in range(len(kwargs_lens)):
            if model_bool_list[i] is True:
                kappa_s += self.LensModel.kappa(x_coords,
                                                y_coords,
                                                kwargs_lens,
                                                k=i)
        amplitudes, sigmas, norm = mge.mge_1d(r_array, kappa_s, N=n_comp)
        return amplitudes, sigmas, center_x, center_y

    def flux_components(self,
                        kwargs_light,
                        n_grid=400,
                        delta_grid=0.01,
                        deltaPix=0.05,
                        type="lens"):
        """
        computes the total flux in each component of the model

        :param kwargs_light:
        :param n_grid:
        :param delta_grid:
        :return:
        """
        flux_list = []
        R_h_list = []
        x_grid, y_grid = util.make_grid(numPix=n_grid, deltapix=delta_grid)
        kwargs_copy = copy.deepcopy(kwargs_light)
        for k, kwargs in enumerate(kwargs_light):
            if 'center_x' in kwargs_copy[k]:
                kwargs_copy[k]['center_x'] = 0
                kwargs_copy[k]['center_y'] = 0
            if type == 'lens':
                light = self.LensLightModel.surface_brightness(x_grid,
                                                               y_grid,
                                                               kwargs_copy,
                                                               k=k)
            elif type == 'source':
                light = self.SourceModel.surface_brightness(x_grid,
                                                            y_grid,
                                                            kwargs_copy,
                                                            k=k)
            else:
                raise ValueError("type %s not supported!" % type)
            flux = np.sum(light) * delta_grid**2 / deltaPix**2
            R_h = analysis_util.half_light_radius(light, x_grid, y_grid)
            flux_list.append(flux)
            R_h_list.append(R_h)
        return flux_list, R_h_list

    def error_map_source(self, kwargs_source, x_grid, y_grid, cov_param):
        """
        variance of the linear source reconstruction in the source plane coordinates,
        computed by the diagonal elements of the covariance matrix of the source reconstruction as a sum of the errors
        of the basis set.

        :param kwargs_source: keyword arguments of source model
        :param x_grid: x-axis of positions to compute error map
        :param y_grid: y-axis of positions to compute error map
        :param cov_param: covariance matrix of liner inversion parameters
        :return: diagonal covariance errors at the positions (x_grid, y_grid)
        """

        error_map = np.zeros_like(x_grid)
        basis_functions, n_source = self.SourceModel.functions_split(
            x_grid, y_grid, kwargs_source)
        basis_functions = np.array(basis_functions)

        if cov_param is not None:
            for i in range(len(error_map)):
                error_map[i] = basis_functions[:, i].T.dot(
                    cov_param[:n_source, :n_source]).dot(basis_functions[:, i])
        return error_map

    def light2mass_mge(self,
                       kwargs_lens_light,
                       model_bool_list=None,
                       elliptical=False,
                       numPix=100,
                       deltaPix=0.05):
        # estimate center
        if 'center_x' in kwargs_lens_light[0]:
            center_x, center_y = kwargs_lens_light[0][
                'center_x'], kwargs_lens_light[0]['center_y']
        else:
            center_x, center_y = 0, 0
        # estimate half-light radius
        r_h = self.half_light_radius_lens(kwargs_lens_light,
                                          center_x=center_x,
                                          center_y=center_y,
                                          model_bool_list=model_bool_list,
                                          numPix=numPix,
                                          deltaPix=deltaPix)
        # estimate ellipticity at half-light radius
        if elliptical is True:
            e1, e2 = self.ellipticity_lens_light(
                kwargs_lens_light,
                center_x=center_x,
                center_y=center_y,
                model_bool_list=model_bool_list,
                deltaPix=deltaPix * 2,
                numPix=numPix)
        else:
            e1, e2 = 0, 0
        # MGE around major axis
        amplitudes, sigmas, center_x, center_y = self.multi_gaussian_lens_light(
            kwargs_lens_light,
            model_bool_list=model_bool_list,
            e1=e1,
            e2=e2,
            n_comp=20)
        kwargs_mge = {
            'amp': amplitudes,
            'sigma': sigmas,
            'center_x': center_x,
            'center_y': center_y
        }
        if elliptical:
            kwargs_mge['e1'] = e1
            kwargs_mge['e2'] = e2
        # rotate axes and add ellipticity to model kwargs
        return kwargs_mge

    @staticmethod
    def light2mass_interpol(lens_light_model_list,
                            kwargs_lens_light,
                            numPix=100,
                            deltaPix=0.05,
                            subgrid_res=5,
                            center_x=0,
                            center_y=0):
        """
        takes a lens light model and turns it numerically in a lens model
        (with all lensmodel quantities computed on a grid). Then provides an interpolated grid for the quantities.

        :param kwargs_lens_light: lens light keyword argument list
        :param numPix: number of pixels per axis for the return interpolation
        :param deltaPix: interpolation/pixel size
        :param center_x: center of the grid
        :param center_y: center of the grid
        :param subgrid: subgrid for the numerical integrals
        :return:
        """
        # make sugrid
        x_grid_sub, y_grid_sub = util.make_grid(numPix=numPix * 5,
                                                deltapix=deltaPix,
                                                subgrid_res=subgrid_res)
        import lenstronomy.Util.mask as mask_util
        mask = mask_util.mask_sphere(x_grid_sub,
                                     y_grid_sub,
                                     center_x,
                                     center_y,
                                     r=1)
        x_grid, y_grid = util.make_grid(numPix=numPix, deltapix=deltaPix)
        # compute light on the subgrid
        lightModel = LightModel(light_model_list=lens_light_model_list)
        flux = lightModel.surface_brightness(x_grid_sub, y_grid_sub,
                                             kwargs_lens_light)
        flux_norm = np.sum(flux[mask == 1]) / np.sum(mask)
        flux /= flux_norm
        from lenstronomy.LensModel.numerical_profile_integrals import ConvergenceIntegrals
        integral = ConvergenceIntegrals()

        # compute lensing quantities with subgrid
        convergence_sub = flux
        f_x_sub, f_y_sub = integral.deflection_from_kappa(convergence_sub,
                                                          x_grid_sub,
                                                          y_grid_sub,
                                                          deltaPix=deltaPix /
                                                          float(subgrid_res))
        f_sub = integral.potential_from_kappa(convergence_sub,
                                              x_grid_sub,
                                              y_grid_sub,
                                              deltaPix=deltaPix /
                                              float(subgrid_res))
        # interpolation function on lensing quantities
        x_axes_sub, y_axes_sub = util.get_axes(x_grid_sub, y_grid_sub)
        from lenstronomy.LensModel.Profiles.interpol import Interpol_func
        interp_func = Interpol_func()
        interp_func.do_interp(x_axes_sub, y_axes_sub, f_sub, f_x_sub, f_y_sub)
        # compute lensing quantities on sparser grid
        x_axes, y_axes = util.get_axes(x_grid, y_grid)
        f_ = interp_func.function(x_grid, y_grid)
        f_x, f_y = interp_func.derivatives(x_grid, y_grid)
        # numerical differentials for second order differentials
        from lenstronomy.LensModel.numeric_lens_differentials import NumericLens
        lens_differential = NumericLens(lens_model_list=['INTERPOL'])
        kwargs = [{
            'grid_interp_x': x_axes_sub,
            'grid_interp_y': y_axes_sub,
            'f_': f_sub,
            'f_x': f_x_sub,
            'f_y': f_y_sub
        }]
        f_xx, f_xy, f_yx, f_yy = lens_differential.hessian(
            x_grid, y_grid, kwargs)
        kwargs_interpol = {
            'grid_interp_x': x_axes,
            'grid_interp_y': y_axes,
            'f_': util.array2image(f_),
            'f_x': util.array2image(f_x),
            'f_y': util.array2image(f_y),
            'f_xx': util.array2image(f_xx),
            'f_xy': util.array2image(f_xy),
            'f_yy': util.array2image(f_yy)
        }
        return kwargs_interpol

    def mass_fraction_within_radius(self,
                                    kwargs_lens,
                                    center_x,
                                    center_y,
                                    theta_E,
                                    numPix=100):
        """
        computes the mean convergence of all the different lens model components within a spherical aperture

        :param kwargs_lens: lens model keyword argument list
        :param center_x: center of the aperture
        :param center_y: center of the aperture
        :param theta_E: radius of aperture
        :return: list of average convergences for all the model components
        """
        x_grid, y_grid = util.make_grid(numPix=numPix,
                                        deltapix=2. * theta_E / numPix)
        x_grid += center_x
        y_grid += center_y
        mask = mask_util.mask_sphere(x_grid, y_grid, center_x, center_y,
                                     theta_E)
        kappa_list = []
        for i in range(len(kwargs_lens)):
            kappa = self.LensModel.kappa(x_grid, y_grid, kwargs_lens, k=i)
            kappa_mean = np.sum(kappa * mask) / np.sum(mask)
            kappa_list.append(kappa_mean)
        return kappa_list
Ejemplo n.º 6
0
class TestLightModel(object):
    """
    tests the source model routines
    """
    def setup(self):
        self.light_model_list = [
            'GAUSSIAN', 'MULTI_GAUSSIAN', 'SERSIC', 'SERSIC_ELLIPSE',
            'CORE_SERSIC', 'SHAPELETS', 'HERNQUIST', 'HERNQUIST_ELLIPSE',
            'PJAFFE', 'PJAFFE_ELLIPSE', 'UNIFORM', 'POWER_LAW', 'NIE'
        ]
        phi_G, q = 0.5, 0.8
        e1, e2 = param_util.phi_q2_ellipticity(phi_G, q)
        self.kwargs = [
            {
                'amp': 1.,
                'sigma_x': 1,
                'sigma_y': 1.,
                'center_x': 0,
                'center_y': 0
            },  # 'GAUSSIAN'
            {
                'amp': [1., 2],
                'sigma': [1, 3],
                'center_x': 0,
                'center_y': 0
            },  # 'MULTI_GAUSSIAN'
            {
                'amp': 1,
                'R_sersic': 0.5,
                'n_sersic': 1,
                'center_x': 0,
                'center_y': 0
            },  # 'SERSIC'
            {
                'amp': 1,
                'R_sersic': 0.5,
                'n_sersic': 1,
                'e1': e1,
                'e2': e2,
                'center_x': 0,
                'center_y': 0
            },  # 'SERSIC_ELLIPSE'
            {
                'amp': 1,
                'R_sersic': 0.5,
                'Re': 0.1,
                'gamma': 2.,
                'n_sersic': 1,
                'e1': e1,
                'e2': e2,
                'center_x': 0,
                'center_y': 0
            },
            # 'CORE_SERSIC'
            {
                'amp': [1, 1, 1],
                'beta': 0.5,
                'n_max': 1,
                'center_x': 0,
                'center_y': 0
            },  # 'SHAPELETS'
            {
                'amp': 1,
                'Rs': 0.5,
                'center_x': 0,
                'center_y': 0
            },  # 'HERNQUIST'
            {
                'amp': 1,
                'Rs': 0.5,
                'center_x': 0,
                'center_y': 0,
                'e1': e1,
                'e2': e2
            },  # 'HERNQUIST_ELLIPSE'
            {
                'amp': 1,
                'Ra': 1,
                'Rs': 0.5,
                'center_x': 0,
                'center_y': 0
            },  # 'PJAFFE'
            {
                'amp': 1,
                'Ra': 1,
                'Rs': 0.5,
                'center_x': 0,
                'center_y': 0,
                'e1': e1,
                'e2': e2
            },  # 'PJAFFE_ELLIPSE'
            {
                'amp': 1
            },  # 'UNIFORM'
            {
                'amp': 1.,
                'gamma': 2.,
                'e1': e1,
                'e2': e2,
                'center_x': 0,
                'center_y': 0
            },  # 'POWER_LAW'
            {
                'amp': .001,
                'e1': 0,
                'e2': 1.,
                'center_x': 0,
                'center_y': 0,
                's_scale': 1.
            },  # 'NIE'
        ]

        self.LightModel = LightModel(light_model_list=self.light_model_list)

    def test_init(self):
        model_list = [
            'CORE_SERSIC', 'SHAPELETS', 'UNIFORM', 'CHAMELEON',
            'DOUBLE_CHAMELEON'
        ]
        lightModel = LightModel(light_model_list=model_list)
        assert len(lightModel.profile_type_list) == len(model_list)

    def test_surface_brightness(self):
        output = self.LightModel.surface_brightness(x=1,
                                                    y=1,
                                                    kwargs_list=self.kwargs)
        npt.assert_almost_equal(output, 3.512593731652167, decimal=6)

    def test_surface_brightness_array(self):
        output = self.LightModel.surface_brightness(x=[1],
                                                    y=[1],
                                                    kwargs_list=self.kwargs)
        npt.assert_almost_equal(output[0], 3.512593731652167, decimal=6)

    def test_functions_split(self):
        output = self.LightModel.functions_split(x=1.,
                                                 y=1.,
                                                 kwargs_list=self.kwargs)
        npt.assert_almost_equal(output[0][0], 0.058549831524319168, decimal=6)

    def test_re_normalize_flux(self):
        kwargs_out = self.LightModel.re_normalize_flux(kwargs_list=self.kwargs,
                                                       norm_factor=2)
        assert kwargs_out[0]['amp'] == 2 * self.kwargs[0]['amp']

    def test_param_name_list(self):
        param_name_list = self.LightModel.param_name_list()
        assert len(self.light_model_list) == len(param_name_list)

    def test_update_linear(self):
        response, n = self.LightModel.functions_split(1, 1, self.kwargs)
        param = np.ones(n) * 2
        kwargs_out, i = self.LightModel.update_linear(param,
                                                      i=0,
                                                      kwargs_list=self.kwargs)
        assert i == n
        assert kwargs_out[0]['amp'] == 2
Ejemplo n.º 7
0
class LensAnalysis(object):
    """
    class to compute flux ratio anomalies, inherited from standard MakeImage
    """
    def __init__(self, kwargs_model):
        self.LensLightModel = LightModel(kwargs_model.get('lens_light_model_list', ['NONE']))
        self.SourceModel = LightModel(kwargs_model.get('source_light_model_list', ['NONE']))
        self.LensModel = LensModelExtensions(lens_model_list=kwargs_model['lens_model_list'])
        self.PointSource = PointSource(point_source_type_list=kwargs_model.get('point_source_model_list', ['NONE']))
        self.kwargs_model = kwargs_model
        self.NumLensModel = NumericLens(lens_model_list=kwargs_model['lens_model_list'])
        self.gaussian = Gaussian()

    def fermat_potential(self, kwargs_lens, kwargs_ps):
        ra_pos, dec_pos = self.PointSource.image_position(kwargs_ps, kwargs_lens)
        ra_pos = ra_pos[0]
        dec_pos = dec_pos[0]
        ra_source, dec_source = self.LensModel.ray_shooting(ra_pos, dec_pos, kwargs_lens)
        ra_source = np.mean(ra_source)
        dec_source = np.mean(dec_source)
        fermat_pot = self.LensModel.fermat_potential(ra_pos, dec_pos, ra_source, dec_source, kwargs_lens)
        return fermat_pot

    def half_light_radius_lens(self, kwargs_lens_light, deltaPix=None, numPix=None):
        """
        computes numerically the half-light-radius of the deflector light and the total photon flux

        :param kwargs_lens_light:
        :return:
        """
        if numPix is None:
            numPix = 1000
        if deltaPix is None:
            deltaPix = 0.05
        x_grid, y_grid = util.make_grid(numPix=numPix, deltapix=deltaPix)
        lens_light = self._lens_light_internal(x_grid, y_grid, kwargs_lens_light)
        R_h = analysis_util.half_light_radius(lens_light, x_grid, y_grid)
        return R_h

    def half_light_radius_source(self, kwargs_source, deltaPix=None, numPix=None):
        """
        computes numerically the half-light-radius of the deflector light and the total photon flux

        :param kwargs_lens_light:
        :return:
        """
        if numPix is None:
            numPix = 1000
        if deltaPix is None:
            deltaPix = 0.005
        x_grid, y_grid = util.make_grid(numPix=numPix, deltapix=deltaPix)
        source_light = self.SourceModel.surface_brightness(x_grid, y_grid, kwargs_source)
        R_h = analysis_util.half_light_radius(source_light, x_grid, y_grid, center_x=kwargs_source[0]['center_x'], center_y=kwargs_source[0]['center_y'])
        return R_h

    def _lens_light_internal(self, x_grid, y_grid, kwargs_lens_light):
        """

        :param x_grid:
        :param y_grid:
        :param kwargs_lens_light:
        :return:
        """
        kwargs_lens_light_copy = copy.deepcopy(kwargs_lens_light)
        lens_light_model_internal_bool = self.kwargs_model.get('light_model_deflector_bool', [True] * len(kwargs_lens_light))
        lens_light = np.zeros_like(x_grid)
        for i, bool in enumerate(lens_light_model_internal_bool):
            if bool is True:
                kwargs_lens_light_copy[i]['center_x'] = 0
                kwargs_lens_light_copy[i]['center_y'] = 0
                lens_light_i = self.LensLightModel.surface_brightness(x_grid, y_grid, kwargs_lens_light_copy, k=i)
                lens_light += lens_light_i
        return lens_light

    def multi_gaussian_lens_light(self, kwargs_lens_light, n_comp=20):
        """
        multi-gaussian decomposition of the lens light profile (in 1-dimension)

        :param kwargs_lens_light:
        :param n_comp:
        :return:
        """
        r_h = self.half_light_radius_lens(kwargs_lens_light)
        r_array = np.logspace(-3, 2, 200) * r_h * 2
        #r_array = np.logspace(-2, 1, 50) * r_h
        flux_r = self._lens_light_internal(r_array, np.zeros_like(r_array), kwargs_lens_light)
        amplitudes, sigmas, norm = mge.mge_1d(r_array, flux_r, N=n_comp)
        return amplitudes, sigmas

    def multi_gaussian_lens(self, kwargs_lens, n_comp=20):
        """
        multi-gaussian lens model in convergence space

        :param kwargs_lens:
        :param n_comp:
        :return:
        """
        kwargs_lens_copy = copy.deepcopy(kwargs_lens)
        if 'center_x' in kwargs_lens_copy[0]:
            center_x = kwargs_lens_copy[0]['center_x']
            center_y = kwargs_lens_copy[0]['center_y']
        else:
            raise ValueError('no keyword center_x defined!')
        theta_E = self.LensModel.effective_einstein_radius(kwargs_lens)
        r_array = np.logspace(-4, 2, 200) * theta_E
        #r_array = np.logspace(-2, 1, 50) * theta_E
        lens_model_internal_bool = self.kwargs_model.get('lens_model_internal_bool', [True] * len(kwargs_lens))
        kappa_s = np.zeros_like(r_array)
        for i in range(len(kwargs_lens_copy)):
            if lens_model_internal_bool[i]:
                if 'center_x' in kwargs_lens_copy[0]:
                    kwargs_lens_copy[i]['center_x'] -= center_x
                    kwargs_lens_copy[i]['center_y'] -= center_y
                kappa_s += self.LensModel.kappa(r_array, np.zeros_like(r_array), kwargs_lens_copy, k=i)
        amplitudes, sigmas, norm = mge.mge_1d(r_array, kappa_s, N=n_comp)
        return amplitudes, sigmas, center_x, center_y

    def flux_components(self, kwargs_light, n_grid=400, delta_grid=0.01, deltaPix=0.05, type="lens"):
        """
        computes the total flux in each component of the model

        :param kwargs_light:
        :param n_grid:
        :param delta_grid:
        :return:
        """
        flux_list = []
        R_h_list = []
        x_grid, y_grid = util.make_grid(numPix=n_grid, deltapix=delta_grid)
        kwargs_copy = copy.deepcopy(kwargs_light)
        for k, kwargs in enumerate(kwargs_light):
            if 'center_x' in kwargs_copy[k]:
                kwargs_copy[k]['center_x'] = 0
                kwargs_copy[k]['center_y'] = 0
            if type == 'lens':
                light = self.LensLightModel.surface_brightness(x_grid, y_grid, kwargs_copy, k=k)
            elif type == 'source':
                light = self.SourceModel.surface_brightness(x_grid, y_grid, kwargs_copy, k=k)
            else:
                raise ValueError("type %s not supported!" % type)
            flux = np.sum(light)*delta_grid**2/ deltaPix**2
            R_h = analysis_util.half_light_radius(light, x_grid, y_grid)
            flux_list.append(flux)
            R_h_list.append(R_h)
        return flux_list, R_h_list

    @staticmethod
    def buldge_disk_ratio(kwargs_buldge_disk):
        """
        computes the buldge-to-disk ratio of the

        :param kwargs_buldge_disk: kwargs of the buldge2disk function
        :return:
        """
        kwargs_bd = copy.deepcopy(kwargs_buldge_disk)
        kwargs_bd['center_x'] = 0
        kwargs_bd['center_y'] = 0
        deltaPix = 0.05
        numPix = 200
        x_grid, y_grid = util.make_grid(numPix, deltaPix)
        from lenstronomy.LightModel.Profiles.sersic import BuldgeDisk
        bd_class = BuldgeDisk()
        light_grid = bd_class.function(x_grid, y_grid, **kwargs_bd)
        light_tot = np.sum(light_grid)
        kwargs_bd['I0_d'] = 0
        light_grid = bd_class.function(x_grid, y_grid, **kwargs_bd)
        light_buldge = np.sum(light_grid)
        return light_tot, light_buldge

    def error_map_source(self, kwargs_source, x_grid, y_grid, cov_param):
        """
        variance of the linear source reconstruction in the source plane coordinates,
        computed by the diagonal elements of the covariance matrix of the source reconstruction as a sum of the errors
        of the basis set.

        :param kwargs_source: keyword arguments of source model
        :param x_grid: x-axis of positions to compute error map
        :param y_grid: y-axis of positions to compute error map
        :param cov_param: covariance matrix of liner inversion parameters
        :return: diagonal covariance errors at the positions (x_grid, y_grid)
        """

        error_map = np.zeros_like(x_grid)
        basis_functions, n_source = self.SourceModel.functions_split(x_grid, y_grid, kwargs_source)
        basis_functions = np.array(basis_functions)

        if cov_param is not None:
            for i in range(len(error_map)):
                error_map[i] = basis_functions[:, i].T.dot(cov_param[:n_source, :n_source]).dot(basis_functions[:, i])
        return error_map
Ejemplo n.º 8
0
 def test_raise(self):
     with self.assertRaises(ValueError):
         # try to set decomposition scale to higher than maximal value
         starlets = SLIT_Starlets(force_no_pysap=True)
         # define a test image with gaussian components
         num_pix = 50
         x, y = util.make_grid(num_pix, 1)
         # build a non-trivial positive image from sum of gaussians
         gaussian = Gaussian()
         gaussian1 = gaussian.function(x,
                                       y,
                                       amp=100,
                                       sigma=1,
                                       center_x=-7,
                                       center_y=-7)
         gaussian2 = gaussian.function(x,
                                       y,
                                       amp=500,
                                       sigma=3,
                                       center_x=-3,
                                       center_y=-3)
         gaussian3 = gaussian.function(x,
                                       y,
                                       amp=2000,
                                       sigma=5,
                                       center_x=+5,
                                       center_y=+5)
         test_image = util.array2image(gaussian1 + gaussian2 + gaussian3)
         n_scales = 100
         _ = starlets.decomposition_2d(test_image, n_scales)
     with self.assertRaises(ValueError):
         # try to set decomposition scale to negative value
         starlets = SLIT_Starlets(force_no_pysap=True)
         # define a test image with gaussian components
         num_pix = 50
         x, y = util.make_grid(num_pix, 1)
         # build a non-trivial positive image from sum of gaussians
         gaussian = Gaussian()
         gaussian1 = gaussian.function(x,
                                       y,
                                       amp=100,
                                       sigma=1,
                                       center_x=-7,
                                       center_y=-7)
         gaussian2 = gaussian.function(x,
                                       y,
                                       amp=500,
                                       sigma=3,
                                       center_x=-3,
                                       center_y=-3)
         gaussian3 = gaussian.function(x,
                                       y,
                                       amp=2000,
                                       sigma=5,
                                       center_x=+5,
                                       center_y=+5)
         test_image = util.array2image(gaussian1 + gaussian2 + gaussian3)
         n_scales = -1
         _ = starlets.decomposition_2d(test_image, n_scales)
     with self.assertRaises(ValueError):
         # function_split is not supported/defined for pixel-based profiles
         light_model = LightModel(['SLIT_STARLETS'])
         num_pix = 20
         x, y = util.make_grid(num_pix, 1)
         kwargs_list = [{
             'amp': np.ones((3, num_pix, num_pix)),
             'n_scales': 3,
             'n_pixels': 20**2,
             'center_x': 0,
             'center_y': 0,
             'scale': 1
         }]
         _ = light_model.functions_split(x, y, kwargs_list)
     with self.assertRaises(ValueError):
         # provided a wrong shape for starlet coefficients
         starlet_class = SLIT_Starlets()
         num_pix = 20
         x, y = util.make_grid(num_pix, 1)
         coeffs_wrong = np.ones((3, num_pix**2))
         kwargs_list = {
             'amp': coeffs_wrong,
             'n_scales': 3,
             'n_pixels': 20**2,
             'center_x': 0,
             'center_y': 0,
             'scale': 1
         }
         _ = starlet_class.function(x, y, **kwargs_list)
         image_wrong = np.ones((1, num_pix, num_pix))
         _ = starlet_class.decomposition(image_wrong, 3)
     with self.assertRaises(ValueError):
         # provided a wrong shape for image to be decomposed
         starlet_class = SLIT_Starlets()
         num_pix = 20
         image_wrong = np.ones((2, num_pix, num_pix))
         _ = starlet_class.decomposition(image_wrong, 3)