예제 #1
0
def GaussianFilter(per=None, times=None, std=None, Npix=None):
    '''
	call jp.Gaussian.GaussianFilter()

	return: [gaussianfilter, std]
		Unit for std: pixel
		When use this std, x must pixel: np.arange(...)

		gaussianfilter.size = (per-1) * times + 1

	gf1, s1 = GaussianFilter(per, times)
	gf2, s2 = GaussianFilter(None, None, s1, gf1.size)
	gf3 = GaussianValue(np.arange(gf1.size), gf1.size/2, s1)
		gf1==gf2==gf3,  s1==s2

	NOTE THAT must be GaussianFilter.sum()==1
		can NOT be other value

	(1) per, times
		Use per, times to generate gaussian filter
		then use Npix to reshape
	(2) sigma, Npix
		Use sigma, npix to generate gaussian filter
	'''
    from jizhipy.Math import Gaussian
    import numpy as np
    if (per is not None or times is not None):
        gaussianfilter, std = _GaussianFilter(per, times)
    else:
        x = np.arange(Npix)
        x = x - x.mean()
        gaussianfilter = Gaussian.GaussianValue(x, 0, std)
    return [gaussianfilter, std]
예제 #2
0
 def func(x, p):
     return Gaussian.GaussianValue1(x, 0, p[0])
예제 #3
0
 def func(x, p):
     return Gaussian.GaussianValue(x, p[0], p[1])
예제 #4
0
    def Bins(self, array, nbins, weight=None, wmax2a=None, nsigma=None):
        '''
		nbins:
			(1) ==list/ndarray with .size==3
				** nbins, bmin, bmax = bins
				nbins: number of bins
				bmin, bmax: min and max of bins, NOT use the whole bin
			(2) ==int_number:
				** Then use weight and wmax2a
				Give the total number of the bins, in this case, x.size=bins+1, xc.size=bins

		nsigma:
			float | None
			When generate the bins, won't use the whole range of array, set nsigma, will use |array| <= nsigma*array.std()

		weight:
			** Use this only when bins==int_number
			'G?', 'K?' | None | ndarray with size=bins
			(1) ==None: each bin has the same weight => uniform bins
			(2) ==ndarray: give weights to each bins
			(3) =='G?': 
					'?' should be an value, for example, 'G1', 'G2.3', 'G5.4', 'G12', use Gaussian weight, and obtain it from np.linspace(-?, +?, bins)
			    =='K?': 
					'?' should be an value, for example, 'K1', 'K2.3', 'K5.4', 'K12', use modified Bessel functions of the second kind, and obtain it from np.linspace(-?, +?, bins)

		wmax2a:
			Use it when weight is not None
			float | None
			(1) ==float: weight.max() corresponds to which bin, the bin which value wmax2a is in
		'''
        import numpy as np
        from jizhipy.Basic import IsType
        from jizhipy.Array import Invalid, Asarray
        from jizhipy.Math import Gaussian
        #---------------------------------------------
        array = Asarray(array)
        if (nsigma is not None):
            mean, sigma = array.mean(), array.std()
            array = array[(mean - nsigma * sigma <= array) *
                          (array <= mean + nsigma * sigma)]
        amin, amax = array.min(), array.max()
        #---------------------------------------------
        if (Asarray(nbins).size == 3): nbins, bmin, bmax = nbins
        else: bmin, bmax = amin, amax
        #---------------------------------------------
        # First uniform bins
        bins = np.linspace(bmin, bmax, nbins + 1)
        bstep = bins[1] - bins[0]
        #---------------------------------------------
        # weight
        if (weight is not None):
            if (IsType.isstr(weight)):
                w, v = str(weight[0]).lower(), abs(float(weight[1:]))
                if (v == 0): v = 1
                x = np.linspace(-v, v, nbins)
                if (w == 'k'):
                    import scipy.special as spsp
                    weight = spsp.k0(abs(x))
                    weight = Invalid(weight)
                    weight.data[weight.mask] = 2 * weight.max()
                else:  # Gaussian
                    weight = Gaussian.GaussianValue1(x, 0, 0.4)
            #--------------------
            # wmax2a
            if (wmax2a is not None):
                nmax = int(round(np.where(weight == weight.max())[0].mean()))
                nb = abs(bins - wmax2a)
                nb = np.where(nb == nb.min())[0][0]
                for i in range(bins.size - 1):
                    if (bins[i] <= wmax2a < bins[i + 1]):
                        nb = i
                        break
                d = abs(nmax - nb)
                if (nmax < nb): weight = np.append(weight[-d:], weight[:-d])
                elif (nmax > nb): weight = np.append(weight[d:], weight[:d])
            #--------------------
            weight = weight[:nbins]
            if (weight.size < nbins):
                weight = np.concatenate([weight] +
                                        (nbins - weight.size) * [weight[-1:]])
            weight = weight.max() - weight + weight.min()
            weight /= weight.sum()
            weight = weight.cumsum()
            #--------------------
            c = bins[0] + (bmax - bmin) * weight
            bins[1:-1] = c[:-1]
            #--------------------
            bins = list(bins)
            n = 1
            while (n < len(bins)):
                if (bins[n] - bins[n - 1] < bstep / 20.):
                    bins = bins[:n] + bins[n + 1:]
                else:
                    n += 1
            bins = Asarray(bins)
        #---------------------------------------------
        return bins
예제 #5
0
def K2Jy(T, freq, Dx=None, Dy=None, fwhmx=None, fwhmy=None):
    '''
	Convert brightness temperature T(K) to flux density S(Jy)

	Tb = S*1e-26 * wavelength**2 / 2 / kB / solid_angle
	S = Tb * 2*bB * 1e26 * solid_angle / wavelength**2

	T, freq, Dx, Dy, fwhmx, fwhmy:
		Can be any shape, but must can broadcast

	freq:
		None | MHz
		(1) None: solid_angle = 1.133 * fwhm**2
		(2) in MHz: solid_angle = GaussianSolidAngle()

	fwhmx, fwhmy:
		in rad

	(1) Jy2K(S, None, D)
	(2) Jy2K(S, freq, D)
	(3) Jy2K(S, freq, Dx, Dy)
	(4) Jy2K(S, freq, fwhm)
	(4) Jy2K(S, freq, fwhmx, fwhmy)
	'''
    import numpy as np
    from jizhipy.Math import Gaussian
    from jizhipy.Basic import Raise
    from jizhipy.Array import Asarray
    T, freq, Dx, Dy, fwhmx, fwhmy = Asarray2(T, True), Asarray2(
        freq, True), Asarray2(Dx, True), Asarray2(Dy, True), Asarray2(
            fwhmx, True), Asarray2(fwhmy, True)
    kB = 1.3806e-23
    const = T * 2 * kB * 1e26
    if (freq is None and Dx is not None):
        if (Dy is not None and Dy != Dx):
            Raise(
                Exception,
                'Wrong parameters: Jy2K( S, None, Dx, Dy ). When use Dx and Dy, freq can NOT be None'
            )
        S = const / Dx**2 * (1.133 * 1.029**2)
        return S
    #--------------------------------------------------

    if (Dx is not None):
        fwhmx = 1.029 * 300 / freq / Dx
        if (Dy is not None): fwhmy = 1.029 * 300 / freq / Dy
        else: fwhmy = fwhmx

    elif (Dy is not None):
        fwhmy = 1.029 * 300 / freq / Dy
        fwhmx = fwhmy

    elif (fwhmx is not None):
        if (fwhmy is not None): fwhmy = Num(fwhmy, float)
        else: fwhmy = fwhmx

    elif (fwhmy is not None): fwhmx = fwhmy
    else: Raise(Exception, 'Dx=Dy=fwhmx=fwhmy = None')
    #--------------------------------------------------
    solid_angle = Gaussian.GaussianSolidAngle(fwhmx, fwhmy)
    #--------------------------------------------------
    S = const / (300. / freq)**2 * solid_angle
    return S
예제 #6
0
def Jy2K(S, freq, Dx=None, Dy=None, fwhmx=None, fwhmy=None, **kwargs):
    '''
	Convert flux density S(Jy) to brightness temperature T(K) with Gaussian Beam with FWHM resolution

	Tb = S*1e-26 / 2 / kB * wavelength**2 / solid_angle
	Tb = S*1e-26 / 2 / kB / (1.133*1.029**2) * Dx**2 

	sigma = fwhm / (8ln2)**0.5
	sigma \approx lambda/D /ksd, ksd=1.962~2.286, Reza=2

	S, freq, Dx, Dy, fwhmx, fwhmy:
		Can be any shape, but must can broadcast

	freq:
		None | MHz
		(1) None: solid_angle = 1.133 * fwhm**2
		(2) in MHz: solid_angle = GaussianSolidAngle()

	fwhmx, fwhmy:
		in rad

	(1) Jy2K(S, None, D)
	(2) Jy2K(S, freq, D)
	(3) Jy2K(S, freq, Dx, Dy)
	(4) Jy2K(S, freq, fwhm)
	(4) Jy2K(S, freq, fwhmx, fwhmy)
	'''
    import numpy as np
    from jizhipy.Math import Gaussian
    from jizhipy.Basic import Raise
    from jizhipy.Array import Asarray
    if ('fwhm' in kwargs.keys()): fwhmx = kwargs['fwhm']
    S, freq, Dx, Dy, fwhmx, fwhmy = Asarray2(S, True), Asarray2(
        freq, True), Asarray2(Dx, True), Asarray2(Dy, True), Asarray2(
            fwhmx, True), Asarray2(fwhmy, True)
    kB = 1.3806e-23
    const = S * 1e-26 / 2 / kB
    if (freq is None and Dx is not None):
        if (Dy is not None and Dy != Dx):
            Raise(
                Exception,
                'Wrong parameters: Jy2K( S, None, Dx, Dy ). When use Dx and Dy, freq can NOT be None'
            )
        Tb = const * Dx**2 / (1.133 * 1.029**2)
        return Tb
    #--------------------------------------------------

    if (Dx is not None):
        fwhmx = 1.029 * 300 / freq / Dx
        if (Dy is not None): fwhmy = 1.029 * 300 / freq / Dy
        else: fwhmy = fwhmx

    elif (Dy is not None):
        fwhmy = 1.029 * 300 / freq / Dy
        fwhmx = fwhmy

    elif (fwhmx is not None):
        if (fwhmy is not None): fwhmy = Num(fwhmy, float)
        else: fwhmy = fwhmx

    elif (fwhmy is not None): fwhmx = fwhmy
    else: Raise(Exception, 'Dx=Dy=fwhmx=fwhmy=None')
    #--------------------------------------------------
    case = 2
    if (case == 1):
        solid_angle = Gaussian.GaussianSolidAngle(fwhmx, fwhmy)
    elif (case == 2):
        solid_angle = 1.133 * fwhmx * fwhmy
    #--------------------------------------------------
    Tb = const * (300. / freq)**2 / solid_angle
    return Tb