def __init__(self, transform_type, n, ell_min, ell_max, theta_min, theta_max, lower=1.0, upper=-2.0): # We use a fixed ell grid in log space and will interpolate/extrapolate our inputs onto this # grid. We typically use a maximum ell very much higher than the range we have physical values # for. The exact values there do not matter, but they must be not have a sharp cut-off to avoid # oscillations at small angle. self.ell_min = ell_min self.ell_max = ell_max ell = np.logspace(np.log10(ell_min), np.log10(ell_max), n) self.ell = ell dlogr = np.log(ell[1]) - np.log(ell[0]) # pyfftlog has several options about how the theta and ell values used are chosen. # This option tells it to pick them to minimize ringing. kropt = 1 # The parameters of the Hankel transform depend on the type. # They are defined in a dict at the top of the file self.q, self.mu = _TRANSFORM_PARAMETERS[transform_type] # Prepare the Hankel transform. self.kr, self.xsave = pyfftlog.fhti( n, self.mu, dlogr, q=self.q, kropt=kropt) # We always to the inverse transform, from Fourier->Real. self.direction = -1 # Some more fixed values. self.theta_min = theta_min self.theta_max = theta_max self.lower = lower self.upper = upper # work out the effective theta values. nc = 0.5 * (n + 1) log_ellmin = np.log(ell_min) log_ellmax = np.log(ell_max) log_ellmid = 0.5 * (log_ellmin + log_ellmax) ell_mid = np.exp(log_ellmid) r_mid = self.kr / ell_mid # radians x = np.arange(n) # And the effective angles of the output self.theta_rad = np.exp((x - nc) * dlogr) * r_mid # radians theta_arcmin = np.degrees(self.theta_rad) * 60.0 # arcmin self.range = (theta_arcmin > self.theta_min) & ( theta_arcmin < self.theta_max) self.theta_arcmin = theta_arcmin[self.range]
def fftlogbessel(func,npts,mini,maxi,tdir=1,dim=2): ''' Bessel function transform. Uses pyfftlog Args: func, function from R1->R1 npts, int, number of points to evaluate the bessel function transform mini,float, minimum log_10 value for input (i) maxi,float, maximum log_10 value for output (i) tdir,int, direction of the transform (forward or backward) dim,int, 2d or 3d transform Returns: oaxis, npts numpy array, fourier-space axis. ao, npts numpy array, log-fft'd function function values ''' assert dim==2 or dim ==3 assert tdir==1 or tdir==-1 if tdir==1: onormal=1. elif tdir==-1: onormal=2.*PI if dim==3: mu=.5 else: mu=0. logic=(mini+maxi)/2. nc=(npts+1)/2. dlogi=(maxi-mini)*1./npts dlni=dlogi*np.log(10.) iaxis=10.**(logic+(np.arange(1,npts+1)-nc)*dlogi) kr,xsave=pyfftlog.fhti(npts, mu, dlni, 0, 1., 1) logoc=np.log10(kr)-logic oaxis=10.**(logoc+(np.arange(1,npts+1)-nc)*dlogi) ai=func(iaxis)*iaxis if dim==3: ai*=2.*iaxis*np.sqrt(PI/2./iaxis) #print ai ao=2.*PI*pyfftlog.fht(ai.copy(),xsave,tdir=1)/onormal**2. if dim==3: ao/=oaxis**.5 ao=ao/oaxis #print ao return oaxis,ao
def hankel_transform(n, kr, q, mu, dlnr, Ar): """executing Hankel transformation Args: n (int): binning number of fftlog kr (float): Product of k_c and r_c where 'c' indicate the center of scale array, r and k. q (flaot): bias index for fftlog. mu (float): mu of Bessel function. dlnr (float): bin width in logarithmic Ar (ndarray): array of input function Returns: Ak (ndarray): Hankel-transformed array. """ _kr, xsave = pyfftlog.fhti(n, mu, dlnr, q, kr, 0) Ak = pyfftlog.fht(Ar.copy(), xsave, 1) # execute fftlog return Ak
dlnr = dlogr*np.log(10.0) # ### Calculate input function: $r^{\mu+1}\exp\left(-\frac{r^2}{2}\right)$ # In[4]: r = 10**(logrc + (np.arange(1, n+1) - nc)*dlogr) ar = r**(mu + 1)*np.exp(-r**2/2.0) # ### Initialize FFTLog transform - note fhti resets `kr` # In[5]: kr, xsave = pyfftlog.fhti(n, mu, dlnr, q, kr, kropt) print('pyfftlog.fhti: new kr = ', kr) # ### Call `pyfftlog.fht` (or `pyfftlog.fhtl`) # In[6]: logkc = np.log10(kr) - logrc print('Central point in k-space at log10(k_c) = ', logkc) # rk = r_c/k_c rk = 10**(logrc - logkc) # Transform #ak = pyfftlog.fftl(ar.copy(), xsave, rk, tdir)
# ls = np.linspace(np.log(lmin), np.log(lmax), nl) # dlnr = ls[1]-ls[0] # ls = np.exp(ls) data = open("data/hankel/pow2D.dat", "r") lines = data.readlines() data.close() refs = [float(val) for val in lines] refs = np.array(refs) thsarcmin = np.array(get.get_theta_CFHT()) # tharcmin = np.array(tharcmin) thsdeg = thsarcmin/60 nth = thsarcmin.size # Send numpy arrays kr, xsave = ht.fhti(refs.size, 0, dlnr, 0, 1, 0) xip = ht.fht(refs, xsave) print(xip) print(xip.size) # xim = ht.fht(refs, tharcmin) plt.figure(1).set_size_inches((8, 8), forward=False) # plt.plot(thsarcmin, [abs(xip[i]*2*np.pi - refs1[i])/refs1[i] for i in range(nth)]) plt.plot(refs) plt.plot(xip) plt.title("Variation of $\\xi_+$ changing modes number, lref={0}" .format(ref)) plt.xlabel("$\\theta$ (arcmin)") plt.ylabel("$(\\xi_+-\\xi_m)/ \\xi_m$")