Source code for irfpy.vels.bible.energy

''' The energy table for VEX/ELS.

The simplest way of getting energy table is using :func:`get_table_128` and :func:`get_table_32`.
They return a numpy array with element of (*nstep*, 16), where *nstep* is the number of energy step
(128 and 32 respectively).

>>> etbl128 = get_table_128()
>>> print(etbl128.shape)
(128, 16)

>>> etbl32 = get_table_32()
>>> print(etbl32.shape)
(32, 16)

'''
import numpy as np

from . import kfactor

[docs]def tm2ref_l(tm): ''' Function converting TM raw value to reference voltage (low). See equation (3) in :ref:`vexelsbible`. ''' return tm * (21.8 / 4095.)
[docs]def tm2ref_h(tm): ''' Function converting TM raw value to reference voltage (low). See equation (3) in :ref:`vexelsbible`. ''' return tm * (2777. / 4095.)
[docs]def tm2ref(tm): ''' Convert TM raw value to reference voltage. To accompany both low and high power supply, a trick is used: For negative tm, low power supply is used and for positive tm, high power supply is used. Thus, simple logic is used like:: if tm < 0: return tm2ref_low(-tm) else: return tm2ref_high(tm) See also :func:`tm2ref_l` and :func:`tm2ref_h`. >>> tm2ref(-100) == tm2ref_l(100) True >>> tm2ref(100) == tm2ref_h(100) True ''' if tm < 0: return tm2ref_l(-tm) else: return tm2ref_h(tm)
[docs]class EnergyTable: ''' Base class of energy table. This class is an implementation of section 7 of :ref:`vexelsbible`. .. note:: There is a little bit difference in the table and the calculated value. However the difference is very small, so I do not think it matters our science. This class is considered as a base class for each implemented ELS energy table. To make the child class, following method should be implemented. * self.tmidx(self) * self.nstep(self) ''' def __init__(self): self.kfact = kfactor.kfactors() # 16 element array self.n = self.nstep() self.tm = self.tmidx() # self.n tm array self.hv = np.array([tm2ref(tm) for tm in self.tm])
[docs] def energy(self, estep, anode, fill_flyback=np.nan): ''' Return the energy for the specified energy step and anode. ''' e = self.kfact[anode] * self.hv[estep] if e == 0: e = fill_flyback return e
[docs] def energy_table(self, fill_flyback=np.nan): ''' Return the energy table. :keyword fill_flyback: Value to fill the flyback energy step. :returns: The energy table. :rtype: ``np.array`` with ``nstep`` x16 elements. ''' etbl = np.zeros([self.n, 16]) for ie in range(self.n): for id in range(16): etbl[ie, id] = self.energy(ie, id, fill_flyback=fill_flyback) return etbl
[docs] def nstep(self): ''' Return the number of the energy step. ''' raise NotImplementedError("The function nstep() should be overrided.")
[docs] def tmidx(self): ''' Return a ``nstep`` element nparray of TM value. Negative for low power suppy is employed to use :func:`tm2ref`. ''' raise NotImplementedError("The function tmidx() should be overrided.")
[docs]class EnergyTable128(EnergyTable): ''' Energy table class for 128 energy step mode. This class is an implementation of section 7 of :ref:`vexelsbible`. Flyback energy step looks step-0. .. todo:: Check the flyback energy step. A simple usage is >>> tbl = EnergyTable128() >>> print("%.3f" % tbl.energy(15, 5)) 3.158 >>> print("%.3f" % tbl.energy(100, 10)) 3299.235 >>> print(tbl.energy(0, 5)) nan ''' def __init__(self): EnergyTable.__init__(self)
[docs] def nstep(self): ''' Return the number of the energy step. ''' return 128
[docs] def tmidx(self): ''' Return a 128 element nparray of TM value. Negative for low power suppy is employed to use :func:`tm2ref`. ''' return np.array([0, -16, -18, -19, -21, -23, -25, -27, -29, -32, -35, -38, -41, -45, -49, -53, -57, -62, -68, -74, -80, -87, -95, -103, -112, -121, -132, -143, -155, -169, -183, -199, -216, -235, -255, -277, -301, -327, -355, -385, -419, -455, -494, -536, -582, -632, -687, -746, -810, -880, -955, -1037, -1127, -1223, -1329, -1443, -1567, -1702, -1848, -2007, -2179, -2366, -2570, -2791, -3031, -3291, -3574, -3881, 31, 34, 37, 40, 43, 47, 51, 56, 61, 66, 72, 78, 84, 92, 100, 108, 118, 128, 139, 151, 164, 178, 193, 210, 228, 248, 269, 292, 317, 345, 374, 407, 442, 480, 521, 566, 614, 667, 724, 787, 854, 928, 1008, 1094, 1188, 1291, 1402, 1522, 1653, 1795, 1949, 2117, 2299, 2496, 2711, 2944, 3197, 3472, 3770, 4095])
[docs]class EnergyTable32(EnergyTable): ''' Energy table class for 32 energy step mode. See :class:`EnergyTable128` for details. >>> tbl = EnergyTable32() >>> print(tbl.energy_table().shape) (32, 16) >>> print('%.2f' % tbl.energy(0, 5)) nan >>> print('%.2f' % tbl.energy(10, 15)) 22.40 ''' def __init__(self): EnergyTable.__init__(self)
[docs] def nstep(self): return 32
[docs] def tmidx(self): ''' Return a TM reference values for 32 step mode ''' return -np.array([0, 151, 168, 188, 209, 234, 261, 291, 325, 363, 406, 453, 505, 564, 630, 703, 785, 877, 979, 1092, 1220, 1362, 1520, 1697, 1895, 2115, 2361, 2636, 2943, 3286, 3668, 4095])
[docs]def get_table_128(fill_flyback=np.nan): ''' Get the energy table for 128 energy step mode. :keyword fill_flyback: Value to fill the flyback energy step. >>> tbl = get_table_128() >>> print(tbl.shape) (128, 16) >>> print('%.3f' % tbl[66, 6]) # Return the energy of anode 6, energy step 66. 215.189 ''' return EnergyTable128().energy_table(fill_flyback=fill_flyback)
[docs]def get_table_32(fill_flyback=np.nan): ''' Get the energy table for 128 energy step mode. :keyword fill_flyback: Value to fill the flyback energy step. >>> tbl = get_table_32() >>> print(tbl.shape) (32, 16) >>> print('%.3f' % tbl[26, 7]) # Return the energy of anode 6, energy step 66. 143.248 ''' return EnergyTable32().energy_table(fill_flyback=fill_flyback)
import unittest,doctest
[docs]def doctests(): return unittest.TestSuite(( doctest.DocTestSuite(), ))
if __name__=='__main__': unittest.main(defaultTest='doctests')