lisaanalysistools 1.1.20__cp39-cp39-macosx_15_0_arm64.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- lisaanalysistools/git_version.py +7 -0
- lisaanalysistools-1.1.20.dist-info/METADATA +281 -0
- lisaanalysistools-1.1.20.dist-info/RECORD +48 -0
- lisaanalysistools-1.1.20.dist-info/WHEEL +5 -0
- lisaanalysistools-1.1.20.dist-info/licenses/LICENSE +201 -0
- lisatools/.dylibs/libgcc_s.1.1.dylib +0 -0
- lisatools/.dylibs/libstdc++.6.dylib +0 -0
- lisatools/__init__.py +90 -0
- lisatools/_version.py +34 -0
- lisatools/analysiscontainer.py +474 -0
- lisatools/cutils/Detector.cu +307 -0
- lisatools/cutils/Detector.hpp +84 -0
- lisatools/cutils/__init__.py +129 -0
- lisatools/cutils/global.hpp +28 -0
- lisatools/cutils/pycppdetector.pyx +256 -0
- lisatools/datacontainer.py +312 -0
- lisatools/detector.py +867 -0
- lisatools/diagnostic.py +990 -0
- lisatools/git_version.py.in +7 -0
- lisatools/orbit_files/equalarmlength-orbits-best-fit-to-esa.h5 +0 -0
- lisatools/orbit_files/equalarmlength-orbits.h5 +0 -0
- lisatools/orbit_files/esa-trailing-orbits.h5 +0 -0
- lisatools/sampling/__init__.py +0 -0
- lisatools/sampling/likelihood.py +882 -0
- lisatools/sampling/moves/__init__.py +0 -0
- lisatools/sampling/moves/skymodehop.py +110 -0
- lisatools/sampling/prior.py +646 -0
- lisatools/sampling/stopping.py +320 -0
- lisatools/sampling/utility.py +411 -0
- lisatools/sensitivity.py +1554 -0
- lisatools/sources/__init__.py +6 -0
- lisatools/sources/bbh/__init__.py +1 -0
- lisatools/sources/bbh/waveform.py +106 -0
- lisatools/sources/defaultresponse.py +37 -0
- lisatools/sources/emri/__init__.py +1 -0
- lisatools/sources/emri/waveform.py +79 -0
- lisatools/sources/gb/__init__.py +1 -0
- lisatools/sources/gb/waveform.py +69 -0
- lisatools/sources/utils.py +459 -0
- lisatools/sources/waveformbase.py +41 -0
- lisatools/stochastic.py +327 -0
- lisatools/utils/__init__.py +0 -0
- lisatools/utils/constants.py +54 -0
- lisatools/utils/exceptions.py +95 -0
- lisatools/utils/parallelbase.py +11 -0
- lisatools/utils/utility.py +122 -0
- lisatools_backend_cpu/git_version.py +7 -0
- lisatools_backend_cpu/pycppdetector.cpython-39-darwin.so +0 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
from .waveform import BBHSNRWaveform
|
|
@@ -0,0 +1,106 @@
|
|
|
1
|
+
import numpy as np
|
|
2
|
+
from typing import Optional, Any, Tuple
|
|
3
|
+
from copy import deepcopy
|
|
4
|
+
|
|
5
|
+
# imports
|
|
6
|
+
from fastlisaresponse import ResponseWrapper
|
|
7
|
+
from bbhx.waveformbuild import BBHWaveformFD
|
|
8
|
+
from ...utils.constants import *
|
|
9
|
+
|
|
10
|
+
from ..waveformbase import SNRWaveform
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
class BBHSNRWaveform(SNRWaveform):
|
|
14
|
+
"""Wrapper class for straightforward BBH SNR calculations.
|
|
15
|
+
|
|
16
|
+
Calculates it for A and E channels in TDI2.
|
|
17
|
+
|
|
18
|
+
Args:
|
|
19
|
+
bbh_waveform_kwargs: ``amp_phase_kwargs`` for :class:`BBHWaveformFD`.
|
|
20
|
+
response_kwargs: ``response_kwargs`` for :class:`BBHWaveformFD`.
|
|
21
|
+
|
|
22
|
+
"""
|
|
23
|
+
|
|
24
|
+
def __init__(
|
|
25
|
+
self,
|
|
26
|
+
bbh_waveform_kwargs: Optional[dict] = {"run_phenomd": False},
|
|
27
|
+
response_kwargs: Optional[dict] = {"TDItag": "AET", "tdi2": True},
|
|
28
|
+
) -> None:
|
|
29
|
+
|
|
30
|
+
if "TDItag" not in response_kwargs:
|
|
31
|
+
response_kwargs["TDItag"] = "AET"
|
|
32
|
+
|
|
33
|
+
if "tdi2" not in response_kwargs:
|
|
34
|
+
response_kwargs["tdi2"] = True
|
|
35
|
+
|
|
36
|
+
# wave generating class
|
|
37
|
+
self.wave_gen = BBHWaveformFD(
|
|
38
|
+
amp_phase_kwargs=bbh_waveform_kwargs,
|
|
39
|
+
response_kwargs=response_kwargs,
|
|
40
|
+
)
|
|
41
|
+
|
|
42
|
+
@property
|
|
43
|
+
def f_arr(self) -> np.ndarray:
|
|
44
|
+
"""Frequency array."""
|
|
45
|
+
return self._f_arr
|
|
46
|
+
|
|
47
|
+
@f_arr.setter
|
|
48
|
+
def f_arr(self, f_arr: np.ndarray) -> None:
|
|
49
|
+
"""Set frequency array."""
|
|
50
|
+
self._f_arr = f_arr
|
|
51
|
+
|
|
52
|
+
def __call__(
|
|
53
|
+
self,
|
|
54
|
+
*params: Any,
|
|
55
|
+
return_array: Optional[bool] = False,
|
|
56
|
+
mf_min: Optional[float] = 1e-4,
|
|
57
|
+
mf_max: Optional[float] = 0.6,
|
|
58
|
+
freqs: Optional[np.ndarray] = None,
|
|
59
|
+
**kwargs: Any
|
|
60
|
+
) -> Tuple[np.ndarray, np.ndarray, np.ndarray] | np.ndarray:
|
|
61
|
+
"""Generate waveforms for SNR calculations.
|
|
62
|
+
|
|
63
|
+
Args:
|
|
64
|
+
*params: Parameters for the ``__call__`` function
|
|
65
|
+
for :class:`BBHWaveformFD`.
|
|
66
|
+
return_array: If ``True``, return ``array([A, E, T]).
|
|
67
|
+
If ``False``, return (A, E, T).
|
|
68
|
+
mf_min: Minimum dimensionless frequency to evaluate.
|
|
69
|
+
mf_max: Maximum dimensionless frequency to evaluate.
|
|
70
|
+
freqs: If ``None``, then default will be ``np.logspace(mf_min / M, mf_max / M, 1024)``.
|
|
71
|
+
Otherwise, it will calulate frequencies based on this exact array.
|
|
72
|
+
**kwargs: ``kwargs`` for the ``__call__`` function
|
|
73
|
+
for :class:`BBHWaveformFD`.
|
|
74
|
+
|
|
75
|
+
Returns:
|
|
76
|
+
Output waveform.
|
|
77
|
+
|
|
78
|
+
"""
|
|
79
|
+
|
|
80
|
+
# determine frequency array (sparse, log-spaced)
|
|
81
|
+
m1 = params[0]
|
|
82
|
+
m2 = params[1]
|
|
83
|
+
|
|
84
|
+
if freqs is None:
|
|
85
|
+
min_f = mf_min / (MTSUN_SI * (m1 + m2))
|
|
86
|
+
max_f = mf_max / (MTSUN_SI * (m1 + m2))
|
|
87
|
+
self.f_arr = np.logspace(np.log10(min_f), np.log10(max_f), 1024)
|
|
88
|
+
|
|
89
|
+
else:
|
|
90
|
+
assert isinstance(freqs, np.ndarray)
|
|
91
|
+
self.f_arr = freqs
|
|
92
|
+
|
|
93
|
+
# generate waveform with proper settings
|
|
94
|
+
AET = self.wave_gen(
|
|
95
|
+
*params,
|
|
96
|
+
direct=True,
|
|
97
|
+
combine=True,
|
|
98
|
+
freqs=self.f_arr,
|
|
99
|
+
**kwargs,
|
|
100
|
+
)[0]
|
|
101
|
+
|
|
102
|
+
# prepare output
|
|
103
|
+
if return_array:
|
|
104
|
+
return AET
|
|
105
|
+
else:
|
|
106
|
+
return (AET[0], AET[1], AET[2])
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
from dataclasses import dataclass
|
|
2
|
+
|
|
3
|
+
from ..detector import EqualArmlengthOrbits, Orbits
|
|
4
|
+
|
|
5
|
+
|
|
6
|
+
@dataclass
|
|
7
|
+
class DefaultResponseKwargs:
|
|
8
|
+
"""Default response kwargs
|
|
9
|
+
|
|
10
|
+
Default response kwargs for
|
|
11
|
+
|
|
12
|
+
``t0=30000.0``
|
|
13
|
+
``order=25``
|
|
14
|
+
``tdi="1st generation"``
|
|
15
|
+
``tdi_chan="AET"``
|
|
16
|
+
``orbits=EqualArmlengthOrbits()``
|
|
17
|
+
|
|
18
|
+
"""
|
|
19
|
+
# `fastlisaresponse.ResponseWrapper <https://mikekatz04.github.io/lisa-on-gpu/user/main.html#response-function-wrapper>`_.
|
|
20
|
+
|
|
21
|
+
|
|
22
|
+
t0 = 30000.0
|
|
23
|
+
order = 25
|
|
24
|
+
tdi = "1st generation"
|
|
25
|
+
tdi_chan = "AET"
|
|
26
|
+
orbits = EqualArmlengthOrbits()
|
|
27
|
+
|
|
28
|
+
@classmethod
|
|
29
|
+
def get_dict(cls) -> dict:
|
|
30
|
+
"""Return default dictionary"""
|
|
31
|
+
return dict(
|
|
32
|
+
t0=cls.t0,
|
|
33
|
+
order=cls.order,
|
|
34
|
+
tdi=cls.tdi,
|
|
35
|
+
tdi_chan=cls.tdi_chan,
|
|
36
|
+
orbits=cls.orbits,
|
|
37
|
+
)
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
from .waveform import EMRITDIWaveform
|
|
@@ -0,0 +1,79 @@
|
|
|
1
|
+
from __future__ import annotations
|
|
2
|
+
from lisatools.detector import EqualArmlengthOrbits
|
|
3
|
+
import numpy as np
|
|
4
|
+
from typing import Optional, Any
|
|
5
|
+
from copy import deepcopy
|
|
6
|
+
|
|
7
|
+
from few.waveform import GenerateEMRIWaveform
|
|
8
|
+
|
|
9
|
+
# imports
|
|
10
|
+
from ..waveformbase import AETTDIWaveform
|
|
11
|
+
from fastlisaresponse import ResponseWrapper
|
|
12
|
+
from ...detector import EqualArmlengthOrbits
|
|
13
|
+
|
|
14
|
+
default_response_kwargs = dict(
|
|
15
|
+
t0=30000.0,
|
|
16
|
+
order=25,
|
|
17
|
+
tdi="1st generation",
|
|
18
|
+
tdi_chan="AET",
|
|
19
|
+
orbits=EqualArmlengthOrbits(),
|
|
20
|
+
)
|
|
21
|
+
|
|
22
|
+
|
|
23
|
+
class EMRITDIWaveform(AETTDIWaveform):
|
|
24
|
+
"""Generate EMRI waveforms with the TDI LISA Response.
|
|
25
|
+
|
|
26
|
+
Args:
|
|
27
|
+
T: Observation time in years.
|
|
28
|
+
dt: Time cadence in seconds.
|
|
29
|
+
emri_waveform_args: Arguments for :class:`GenerateEMRIWaveforms`.
|
|
30
|
+
emri_waveform_kwargs: Keyword arguments for :class:`GenerateEMRIWaveforms`.
|
|
31
|
+
response_kwargs: Keyword arguments for :class:`ResponseWrapper`.
|
|
32
|
+
|
|
33
|
+
"""
|
|
34
|
+
|
|
35
|
+
def __init__(
|
|
36
|
+
self,
|
|
37
|
+
T: Optional[float] = 1.0,
|
|
38
|
+
dt: Optional[float] = 10.0,
|
|
39
|
+
emri_waveform_args: Optional[tuple] = ("FastKerrEccentricEquatorialFlux",),
|
|
40
|
+
emri_waveform_kwargs: Optional[dict] = {},
|
|
41
|
+
response_kwargs: Optional[dict] = default_response_kwargs,
|
|
42
|
+
):
|
|
43
|
+
# sky parameters in GenerateEMRIWaveform
|
|
44
|
+
index_lambda = 8
|
|
45
|
+
index_beta = 7
|
|
46
|
+
|
|
47
|
+
for key in default_response_kwargs:
|
|
48
|
+
response_kwargs[key] = response_kwargs.get(
|
|
49
|
+
key, default_response_kwargs[key]
|
|
50
|
+
)
|
|
51
|
+
gen_wave = GenerateEMRIWaveform(
|
|
52
|
+
*emri_waveform_args,
|
|
53
|
+
sum_kwargs=dict(pad_output=True),
|
|
54
|
+
**emri_waveform_kwargs,
|
|
55
|
+
)
|
|
56
|
+
|
|
57
|
+
response_kwargs_in = deepcopy(response_kwargs)
|
|
58
|
+
# parameters
|
|
59
|
+
self.response = ResponseWrapper(
|
|
60
|
+
gen_wave,
|
|
61
|
+
T,
|
|
62
|
+
dt,
|
|
63
|
+
index_lambda,
|
|
64
|
+
index_beta,
|
|
65
|
+
flip_hx=True, # set to True if waveform is h+ - ihx
|
|
66
|
+
remove_sky_coords=False,
|
|
67
|
+
is_ecliptic_latitude=False,
|
|
68
|
+
remove_garbage=True, # removes the beginning of the signal that has bad information
|
|
69
|
+
**response_kwargs_in,
|
|
70
|
+
)
|
|
71
|
+
|
|
72
|
+
@property
|
|
73
|
+
def dt(self) -> float:
|
|
74
|
+
"""timestep"""
|
|
75
|
+
return self.response.dt
|
|
76
|
+
|
|
77
|
+
def __call__(self, *args: Any, **kwargs: Any) -> Any:
|
|
78
|
+
__doc__ = ResponseWrapper.__call__.__doc__
|
|
79
|
+
return self.response(*args, **kwargs)
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
from .waveform import GBAETWaveform
|
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
from __future__ import annotations
|
|
2
|
+
|
|
3
|
+
import numpy as np
|
|
4
|
+
from typing import Optional, Any, Tuple
|
|
5
|
+
from copy import deepcopy
|
|
6
|
+
|
|
7
|
+
from few.waveform import GenerateEMRIWaveform
|
|
8
|
+
|
|
9
|
+
# imports
|
|
10
|
+
from fastlisaresponse import ResponseWrapper
|
|
11
|
+
from lisatools.detector import EqualArmlengthOrbits
|
|
12
|
+
from ..waveformbase import AETTDIWaveform
|
|
13
|
+
|
|
14
|
+
from gbgpu.gbgpu import GBGPU
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
class GBAETWaveform(AETTDIWaveform):
|
|
18
|
+
"""Stock AET waveform for Galactic Binaries.
|
|
19
|
+
|
|
20
|
+
Args:
|
|
21
|
+
*args: Arguments for :class:`GBGPU`.
|
|
22
|
+
**kwargs: Arguments for :class:`GBGPU`.
|
|
23
|
+
|
|
24
|
+
"""
|
|
25
|
+
|
|
26
|
+
def __init__(self, *args: Any, **kwargs: Any) -> None:
|
|
27
|
+
# wave generating class
|
|
28
|
+
self.wave_gen = GBGPU(*args, **kwargs)
|
|
29
|
+
|
|
30
|
+
@property
|
|
31
|
+
def f_arr(self) -> np.ndarray:
|
|
32
|
+
"""Frequency array."""
|
|
33
|
+
return self._f_arr
|
|
34
|
+
|
|
35
|
+
@f_arr.setter
|
|
36
|
+
def f_arr(self, f_arr: np.ndarray) -> None:
|
|
37
|
+
"""Set the frequency array."""
|
|
38
|
+
self._f_arr = f_arr
|
|
39
|
+
|
|
40
|
+
def __call__(
|
|
41
|
+
self, *params: Any, return_array: Optional[bool] = False, **kwargs: Any
|
|
42
|
+
) -> Tuple[np.ndarray, np.ndarray, np.ndarray] | np.ndarray:
|
|
43
|
+
"""Generate waveform.
|
|
44
|
+
|
|
45
|
+
Args:
|
|
46
|
+
*params: Parameters going into :meth:`GBGPU.run_wave`.
|
|
47
|
+
return_array: If ``True``, return ``array([A, E, T]).
|
|
48
|
+
If ``False``, return (A, E, T).
|
|
49
|
+
**kwargs: Keyword arguments going into :meth:`GBGPU.run_wave`.
|
|
50
|
+
|
|
51
|
+
Returns:
|
|
52
|
+
Output waveform.
|
|
53
|
+
|
|
54
|
+
"""
|
|
55
|
+
self.wave_gen.run_wave(
|
|
56
|
+
*params,
|
|
57
|
+
**kwargs,
|
|
58
|
+
)
|
|
59
|
+
|
|
60
|
+
# prepare outputs
|
|
61
|
+
self.f_arr = self.wave_gen.freqs[0]
|
|
62
|
+
A = self.wave_gen.A[0]
|
|
63
|
+
E = self.wave_gen.E[0]
|
|
64
|
+
T = self.wave_gen.X[0]
|
|
65
|
+
|
|
66
|
+
if return_array:
|
|
67
|
+
return np.array([A, E, T])
|
|
68
|
+
else:
|
|
69
|
+
return (A, E, T)
|