Electron Distributions¶
- eDist(double[::1] gamma, double ne, list params, unicode edist)¶
Common function for built-in electron distributions
- Parameters
gamma (np.ndarray) – 1-D gamma array (C contiguous)
ne (float) – Number of electrons
params (list of floats) –
- Electron distributions parameters varies based on edist
”thermal” : theta_E
”kappa” : kappa, kappa_width
”powerlaw” : p, g_min, g_max
”bknpowerlaw” : p1, p2, g_break, g_min, g_max
”powerlawexpcutoff” : p, g_min, g_max
”bknpowerlawexpcutoff” : p1, p2, g_break, g_min, g_max
edist (str) – see params
- Returns
dN/dgamma
- Return type
np.ndarray
How to add new electron distributions¶
Unfortunately, we are not able to provide a convenient way to add new electron distributions in python as electron distributions are tightly integrated in C utilities at lower level. But, C interface is modular and it is possible to add new distributions on the source code.
Our powerlaw implementation at C level is given below:
// cfuncs/edist.c
//...
// params : p, gamma_min, gamma_max
double powerlaw(double gamma, void *params){
double *p = (double*) params;
return pow(gamma, -p[0]);
}
//...
double powerlaw_norm(void* params){
double *p = (double*) params;
return (P_THRESH > fabs(p[0] - 1)) ? (log(p[2])-log(p[1])) : (pow(p[1], -p[0]+1)-pow(p[2], -p[0]+1))/(p[0]-1);
}
//...
// cfuncs/edist.h
//...
// params : p, gamma_min, gamma_max
double powerlaw(double gamma, void *params);
//...
double powerlaw_norm(void *params);
//...
Then, the distribution needs to be registered with a name tag in Cython interface. This makes the distribution available to the rest of the code with the given name tag.
# flaremodel/utils/cfuncs.pyx
# ...
cdef extern from "edist.h":
double powerlaw (double, void*) # <--
double powerlawexpcutoff (double, void*)
double thermal (double, void*)
double kappa (double, void*)
double bknpowerlaw (double, void*)
double bknpowerlawexpcutoff (double, void*)
double powerlaw_norm (void*) # <--
double thermal_norm (void*)
double kappa_norm (void*)
double bknpowerlaw_norm (void*)
int c_eDist "eDist" (...)
# ...
cdef _set_source_params(Source *source_t, str edist):
cdef double *params = source_t.params
if edist == "powerlaw": # <--
source_t.gamma_min = params[1]
source_t.gamma_max = params[2]
source_t.d_func = &powerlaw
source_t.n_func = &powerlaw_norm
elif edist == "thermal":
source_t.d_func = &thermal
source_t.n_func = &thermal_norm
elif edist == "kappa":
source_t.d_func = &kappa
source_t.n_func = &kappa_norm
elif edist == "bknpowerlaw":
source_t.gamma_min = params[3]
source_t.gamma_max = params[4]
source_t.d_func = &bknpowerlaw
source_t.n_func = &bknpowerlaw_norm
elif edist == "powerlawexpcutoff":
source_t.gamma_min = params[1]
source_t.gamma_max = params[2]*10
source_t.d_func = &powerlawexpcutoff
source_t.n_func = &powerlaw_norm
elif edist == "bknpowerlawexpcutoff":
source_t.gamma_min = params[3]
source_t.gamma_max = params[4]*10
source_t.d_func = &bknpowerlawexpcutoff
source_t.n_func = &bknpowerlaw_norm
else:
raise ValueError("%s not implemented" % edist)
# ...