| math_utils.py | math_utils.py | |||
|---|---|---|---|---|
| # -*- coding: utf-8 -*- | # -*- coding: utf-8 -*- | |||
| import numpy as np | import numpy as np | |||
| import math | import math | |||
| from scipy import special | ||||
| # Mandatory TAU = 6.283185307179586... | # Mandatory TAU = 6.283185307179586... | |||
| math.tau = 2 * math.pi | math.tau = 2 * math.pi | |||
| def merge_where_nan(target, filler): | def merge_where_nan(target, filler): | |||
| """ | """ | |||
| Procedurally mutates target by replacing its nan values by values from filler. | Procedurally mutates target by replacing its nan values by values from filler. | |||
| This is a very simple polyfill for numpy.copyto (for numpy < 1.7). | This is a very simple polyfill for numpy.copyto (for numpy < 1.7). | |||
| """ | """ | |||
| try: | #try: | |||
| # np.copyto(target, filler, where=np.isnan(target)) | ||||
| #except AttributeError: | ||||
| # isnan = np.isnan(target) | ||||
| # target[isnan] = filler[isnan] | ||||
| if target.size == filler.size: | ||||
| np.copyto(target, filler, where=np.isnan(target)) | np.copyto(target, filler, where=np.isnan(target)) | |||
| except AttributeError: | else: | |||
| isnan = np.isnan(target) | try: | |||
| target[isnan] = filler[isnan] | for k in target.names: | |||
| if k in filler.names: | ||||
| target[k] = np.where(np.isnan(target[k]), filler[k], ta | ||||
| rget[k]) | ||||
| except ValueError: | ||||
| raise ValueError(" merge failed ") | ||||
| def safe_exp(x): | def safe_exp(x): | |||
| """ | """ | |||
| Should not throw during Underflows (and return 0) and Overflows (and re turn inf). | Should not throw during Underflows (and return 0) and Overflows (and re turn inf). | |||
| This code is a hack, and may be cause of future bugs. | This code is a hack, and may be cause of future bugs. | |||
| Oddly enough, it passes a few basic tests in `math_utils_test.py`. | Oddly enough, it passes a few basic tests in `math_utils_test.py`. | |||
| """ | """ | |||
| try: | try: | |||
| a = math.exp(x) | a = math.exp(x) | |||
| except OverflowError: | except OverflowError: | |||
| skipping to change at line 99 | skipping to change at line 109 | |||
| median = np.median(data) | median = np.median(data) | |||
| sigma = np.std(data) | sigma = np.std(data) | |||
| return median, sigma, iteration | return median, sigma, iteration | |||
| def flux_gaussian(radius, rhwhm): | def flux_gaussian(radius, rhwhm): | |||
| """ | """ | |||
| Disk Gaussian profile with Gaussian thickness | Disk Gaussian profile with Gaussian thickness | |||
| """ | """ | |||
| energy = np.exp(-radius ** 2 / 2. / (2. * rhwhm / 2.35) ** 2) #* np | #energy = np.exp(-radius ** 2 / 2. / (2. * rhwhm / 2.35) ** 2) #* n | |||
| .exp(-nz ** 2 / 2. / hz ** 2) | p.exp(-nz ** 2 / 2. / hz ** 2) | |||
| return energy #DizkModel.flux_sersic(radius, size, 0.5) | return flux_sersic(radius, rhwhm, 0.5) | |||
| def flux_sersic(radius, size, index): | def flux_sersic(radius, size, index, normalize=False): | |||
| """ | """ | |||
| Sersic profile with Gaussian thickness | Sersic profile with Gaussian thickness | |||
| See http://en.wikipedia.org/wiki/Sersic_profile | See http://en.wikipedia.org/wiki/Sersic_profile | |||
| """ | """ | |||
| beta = 1.9992 * index - 0.3271 | beta = 1.9992 * index - 0.3271 | |||
| energy = np.exp(-beta * (radius / size) ** (1. / index)) | energy = np.exp(-beta * ((radius / size) ** (1. / index) -1) ) | |||
| if normalize: | ||||
| #Graham Driver 2005 | ||||
| Norm = size**2 * 2 * np.pi * index * np.exp(beta) / beta**(2*in | ||||
| dex) | ||||
| energy = energy / Norm | ||||
| #energy = np.exp(-beta * (radius / size) ** (1. / index)) * np.exp( -nz ** 2 / 2. / hz ** 2) | #energy = np.exp(-beta * (radius / size) ** (1. / index)) * np.exp( -nz ** 2 / 2. / hz ** 2) | |||
| #energy = np.exp(-beta * (radius / size) ** (1. / index)) * np.exp( -np.sqrt(nz ** 2) / hz ) #exponential z-profile | #energy = np.exp(-beta * (radius / size) ** (1. / index)) * np.exp( -np.sqrt(nz ** 2) / hz ) #exponential z-profile | |||
| #energy = np.exp(-beta * (radius / size) ** (1. / index)) * np.cosh (-nz / hz )**(-2.) #sech^2 z-profile | #energy = np.exp(-beta * (radius / size) ** (1. / index)) * np.cosh (-nz / hz )**(-2.) #sech^2 z-profile | |||
| return energy | return energy | |||
| def flux_exponential(radius, size): | def flux_exponential(radius, size): | |||
| """ | """ | |||
| Disk exponential profile with Gaussian thickness | Disk exponential profile with Gaussian thickness | |||
| This is merely a Sérsic profile with index = 1 | This is merely a Sérsic profile with index = 1 | |||
| """ | """ | |||
| return flux_sersic(radius, size, 1.) | return flux_sersic(radius, size, 1.) | |||
| def flux_de_vaucouleurs(radius, size): | def flux_de_vaucouleurs(radius, size): | |||
| """ | """ | |||
| De Vaucouleurs profile with Gaussian thickness | De Vaucouleurs profile with Gaussian thickness | |||
| See http://en.wikipedia.org/wiki/De_Vaucouleurs%27_law | See http://en.wikipedia.org/wiki/De_Vaucouleurs%27_law | |||
| This is merely a Sérsic profile with index = 4 | This is merely a Sérsic profile with index = 4 | |||
| """ | """ | |||
| return flux_sersic(radius, size, 4.) | return flux_sersic(radius, size, 4.) | |||
| def Phi_ppf(q, loc=0, scale=1.): | ||||
| """ | ||||
| normal ppf | ||||
| :param q: | ||||
| :param loc: | ||||
| :param scale: | ||||
| :return: | ||||
| """ | ||||
| #https://stackoverflow.com/questions/38754423/drawing-gaussian-random-v | ||||
| ariables-using-scipy-erfinv | ||||
| return loc+2**0.5*scale*special.erfinv(2*q-1) | ||||
| End of changes. 7 change blocks. | ||||
| 9 lines changed or deleted | 26 lines changed or added | |||
This html diff was produced by rfcdiff 1.41. The latest version is available from http://tools.ietf.org/tools/rfcdiff/ | ||||