tiwave 0.0.0__py3-none-any.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.
- tiwave/__init__.py +0 -0
- tiwave/constants.py +22 -0
- tiwave/utils.py +164 -0
- tiwave/waveforms/IMRPhenomD.py +1352 -0
- tiwave/waveforms/IMRPhenomXAS.py +2628 -0
- tiwave/waveforms/IMRPhenomXHM.py +7495 -0
- tiwave/waveforms/IMRPhenomXPHM.py +1522 -0
- tiwave/waveforms/__init__.py +12 -0
- tiwave/waveforms/base_waveform.py +131 -0
- tiwave/waveforms/common.py +340 -0
- tiwave/waveforms/data/QNMData_a.txt +1003 -0
- tiwave/waveforms/data/QNMData_fdamp.txt +1003 -0
- tiwave/waveforms/data/QNMData_fring.txt +1003 -0
- tiwave-0.0.0.dist-info/METADATA +132 -0
- tiwave-0.0.0.dist-info/RECORD +18 -0
- tiwave-0.0.0.dist-info/WHEEL +5 -0
- tiwave-0.0.0.dist-info/licenses/LICENSE +674 -0
- tiwave-0.0.0.dist-info/top_level.txt +1 -0
tiwave/__init__.py
ADDED
|
File without changes
|
tiwave/constants.py
ADDED
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
"""
|
|
2
|
+
Useful constants, copied from lalsuite
|
|
3
|
+
"""
|
|
4
|
+
|
|
5
|
+
# Nominal solar mass, kg
|
|
6
|
+
# MSUN_SI = GMSUN_SI / G_SI
|
|
7
|
+
MSUN_SI = 1.988409870698050731911960804878414216e30
|
|
8
|
+
|
|
9
|
+
# Geometrized nominal solar mass, m
|
|
10
|
+
# MRSUN_SI = GMSUN_SI / (C_SI * C_SI)
|
|
11
|
+
MRSUN_SI = 1.476625038050124729627979840144936351e3
|
|
12
|
+
|
|
13
|
+
# Geometrized nominal solar mass, s
|
|
14
|
+
# MTSUN_SI = GMSUN_SI / (C_SI * C_SI * C_SI)
|
|
15
|
+
MTSUN_SI = 4.925490947641266978197229498498379006e-6
|
|
16
|
+
|
|
17
|
+
# Parsec, m
|
|
18
|
+
PC_SI = 3.085677581491367e16
|
|
19
|
+
|
|
20
|
+
# Math constants
|
|
21
|
+
PI = 3.141592653589793
|
|
22
|
+
EULER_GAMMA = 0.5772156649015329
|
tiwave/utils.py
ADDED
|
@@ -0,0 +1,164 @@
|
|
|
1
|
+
import copy
|
|
2
|
+
|
|
3
|
+
import taichi as ti
|
|
4
|
+
import taichi.math as tm
|
|
5
|
+
import numpy as np
|
|
6
|
+
from numpy.typing import NDArray
|
|
7
|
+
|
|
8
|
+
from .constants import *
|
|
9
|
+
|
|
10
|
+
|
|
11
|
+
ti_complex = ti.types.vector(2, float)
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
def sub_struct_from(parent):
|
|
15
|
+
"""
|
|
16
|
+
Since inheritance is not supported in ti.dataclass currently, we use this func as
|
|
17
|
+
a decorator to copy members and bind methods of existing dataclass to current dataclass.
|
|
18
|
+
Only supporting inheritance of just one generation.
|
|
19
|
+
TODO:
|
|
20
|
+
- a usage example
|
|
21
|
+
- staticmethod
|
|
22
|
+
"""
|
|
23
|
+
# parent_members = copy.deepcopy(parent.members)
|
|
24
|
+
# parent_methods = copy.deepcopy(parent.methods)
|
|
25
|
+
# values of the dict point to address of taichi type object or func, using shallow copy is fine
|
|
26
|
+
parent_members = copy.copy(parent.members)
|
|
27
|
+
parent_methods = copy.copy(parent.methods)
|
|
28
|
+
|
|
29
|
+
def sub_struct(cls):
|
|
30
|
+
[parent_members.pop(key) for key in getattr(cls, "removed_members", [])]
|
|
31
|
+
fields = parent_members
|
|
32
|
+
fields.update(getattr(cls, "__annotations__", {}))
|
|
33
|
+
|
|
34
|
+
substruct_methods = {
|
|
35
|
+
attr: getattr(cls, attr)
|
|
36
|
+
for attr in dir(cls)
|
|
37
|
+
if callable(getattr(cls, attr)) and not attr.startswith("__")
|
|
38
|
+
}
|
|
39
|
+
conflict_methods = [k for k in substruct_methods if k in parent_methods]
|
|
40
|
+
# TODO: can have problem if the parent of parent has already had the method with same name
|
|
41
|
+
for k in conflict_methods:
|
|
42
|
+
parent_methods[f"_parent_{k}"] = parent_methods[k]
|
|
43
|
+
parent_methods.update(substruct_methods)
|
|
44
|
+
fields["__struct_methods"] = parent_methods
|
|
45
|
+
|
|
46
|
+
return ti.types.struct(**fields)
|
|
47
|
+
|
|
48
|
+
return sub_struct
|
|
49
|
+
|
|
50
|
+
|
|
51
|
+
# def complex_ti_field_to_np_array(
|
|
52
|
+
# input_field: ti.MatrixField,
|
|
53
|
+
# ) -> NDArray:
|
|
54
|
+
# np_array = input_field.to_numpy()
|
|
55
|
+
# return np_array[:, 0] + 1j * np_array[:, 1]
|
|
56
|
+
|
|
57
|
+
|
|
58
|
+
# def complex_np_array_to_ti_field(
|
|
59
|
+
# input_array: NDArray, field_container: ti.MatrixField
|
|
60
|
+
# ) -> None:
|
|
61
|
+
# field_container.from_numpy(np.vstack([input_array.real, input_array.imag]).T)
|
|
62
|
+
# return None
|
|
63
|
+
|
|
64
|
+
|
|
65
|
+
@ti.dataclass
|
|
66
|
+
class UsefulPowers:
|
|
67
|
+
third: float
|
|
68
|
+
two_thirds: float
|
|
69
|
+
one: float
|
|
70
|
+
four_thirds: float
|
|
71
|
+
five_thirds: float
|
|
72
|
+
two: float
|
|
73
|
+
seven_thirds: float
|
|
74
|
+
eight_thirds: float
|
|
75
|
+
three: float
|
|
76
|
+
four: float
|
|
77
|
+
fourth: float
|
|
78
|
+
three_fourths: float
|
|
79
|
+
seven_sixths: float
|
|
80
|
+
log: float
|
|
81
|
+
|
|
82
|
+
@ti.pyfunc
|
|
83
|
+
def update(self, number: float):
|
|
84
|
+
self.third = number ** (1 / 3)
|
|
85
|
+
self.two_thirds = self.third * self.third
|
|
86
|
+
self.one = number
|
|
87
|
+
self.four_thirds = number * self.third
|
|
88
|
+
self.five_thirds = number * self.two_thirds
|
|
89
|
+
self.two = number * number
|
|
90
|
+
self.seven_thirds = self.two * self.third
|
|
91
|
+
self.eight_thirds = self.two * self.two_thirds
|
|
92
|
+
self.three = self.two * number
|
|
93
|
+
self.four = self.three * number
|
|
94
|
+
self.fourth = number ** (1 / 4)
|
|
95
|
+
self.three_fourths = self.fourth**3
|
|
96
|
+
self.seven_sixths = ti.sqrt(self.seven_thirds)
|
|
97
|
+
self.log = ti.log(number)
|
|
98
|
+
|
|
99
|
+
|
|
100
|
+
@ti.func
|
|
101
|
+
def gauss_elimination(Ab: ti.template()) -> ti.template():
|
|
102
|
+
"""
|
|
103
|
+
Solving a system of linear equations Ax=b using Gauss elimination. Note the loop
|
|
104
|
+
unrolling is used here, do not use this function to solve systems with large dimension.
|
|
105
|
+
|
|
106
|
+
Parameters
|
|
107
|
+
==========
|
|
108
|
+
Ab:
|
|
109
|
+
The matrix containing the coefficinet matrix and numbers for the right hand side,
|
|
110
|
+
having the dimension of (n, n+1).
|
|
111
|
+
|
|
112
|
+
Returns
|
|
113
|
+
=======
|
|
114
|
+
x:
|
|
115
|
+
The solution of the system.
|
|
116
|
+
"""
|
|
117
|
+
for i in ti.static(range(Ab.n)):
|
|
118
|
+
for j in ti.static(range(i + 1, Ab.n)):
|
|
119
|
+
scale = Ab[j, i] / Ab[i, i]
|
|
120
|
+
Ab[j, i] = 0.0
|
|
121
|
+
for k in ti.static(range(i + 1, Ab.m)):
|
|
122
|
+
Ab[j, k] -= Ab[i, k] * scale
|
|
123
|
+
# Back substitution
|
|
124
|
+
x = ti.Vector.zero(float, Ab.n)
|
|
125
|
+
for i in ti.static(range(Ab.n - 1, -1, -1)):
|
|
126
|
+
x[i] = Ab[i, Ab.m - 1]
|
|
127
|
+
for k in ti.static(range(i + 1, Ab.n)):
|
|
128
|
+
x[i] -= Ab[i, k] * x[k]
|
|
129
|
+
x[i] = x[i] / Ab[i, i]
|
|
130
|
+
return x
|
|
131
|
+
|
|
132
|
+
|
|
133
|
+
# def initialize_waveform_container_from_frequencies_array(
|
|
134
|
+
# frequencies, return_form="polarization", include_tf=True
|
|
135
|
+
# ):
|
|
136
|
+
# """
|
|
137
|
+
# Parparing waveform_container of ti.field from frequencies of np.array
|
|
138
|
+
|
|
139
|
+
# Parameters:
|
|
140
|
+
# ===========
|
|
141
|
+
# frequencies: np.array
|
|
142
|
+
|
|
143
|
+
# Returns:
|
|
144
|
+
# ========
|
|
145
|
+
# frequency_field: ti.field
|
|
146
|
+
# waveform_container: ti.Struct.field({'plus': ti_complex, 'cross': ti_complex, 'tf': float})
|
|
147
|
+
# """
|
|
148
|
+
# ret_content = {}
|
|
149
|
+
# if return_form == "polarizations":
|
|
150
|
+
# ret_content.update({"plus": ti_complex, "cross": ti_complex})
|
|
151
|
+
# elif return_form == "amplitude_phase":
|
|
152
|
+
# ret_content.update({"amplitude": float, "phase": float})
|
|
153
|
+
# if include_tf:
|
|
154
|
+
# ret_content.update({"tf": float})
|
|
155
|
+
# waveform_field = ti.Struct.field(ret_content)
|
|
156
|
+
|
|
157
|
+
# data_length = len(frequencies)
|
|
158
|
+
# ti.root.dense(ti.i, data_length).place(waveform_field)
|
|
159
|
+
# waveform_container = waveform_field
|
|
160
|
+
|
|
161
|
+
# frequency_field = ti.field(dtype=float, shape=(data_length,))
|
|
162
|
+
# frequency_field.from_numpy(frequencies)
|
|
163
|
+
|
|
164
|
+
# return frequency_field, waveform_container
|