phylogenie 2.1.4__py3-none-any.whl → 2.1.6__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.
- phylogenie/generators/alisim.py +3 -5
- phylogenie/generators/factories.py +9 -0
- phylogenie/generators/trees.py +8 -8
- phylogenie/treesimulator/events/core.py +7 -7
- phylogenie/treesimulator/gillespie.py +13 -8
- {phylogenie-2.1.4.dist-info → phylogenie-2.1.6.dist-info}/METADATA +1 -1
- {phylogenie-2.1.4.dist-info → phylogenie-2.1.6.dist-info}/RECORD +10 -10
- {phylogenie-2.1.4.dist-info → phylogenie-2.1.6.dist-info}/LICENSE.txt +0 -0
- {phylogenie-2.1.4.dist-info → phylogenie-2.1.6.dist-info}/WHEEL +0 -0
- {phylogenie-2.1.4.dist-info → phylogenie-2.1.6.dist-info}/entry_points.txt +0 -0
phylogenie/generators/alisim.py
CHANGED
|
@@ -6,7 +6,7 @@ from typing import Any, Literal
|
|
|
6
6
|
from numpy.random import Generator, default_rng
|
|
7
7
|
|
|
8
8
|
from phylogenie.generators.dataset import DatasetGenerator, DataType
|
|
9
|
-
from phylogenie.generators.factories import data
|
|
9
|
+
from phylogenie.generators.factories import data, string
|
|
10
10
|
from phylogenie.generators.trees import TreeDatasetGeneratorConfig
|
|
11
11
|
from phylogenie.io import dump_newick
|
|
12
12
|
|
|
@@ -19,7 +19,7 @@ class AliSimDatasetGenerator(DatasetGenerator):
|
|
|
19
19
|
trees: TreeDatasetGeneratorConfig
|
|
20
20
|
keep_trees: bool = False
|
|
21
21
|
iqtree_path: str = "iqtree2"
|
|
22
|
-
args: dict[str,
|
|
22
|
+
args: dict[str, Any]
|
|
23
23
|
|
|
24
24
|
def _generate_one_from_tree(
|
|
25
25
|
self, filename: str, tree_file: str, rng: Generator, data: dict[str, Any]
|
|
@@ -35,9 +35,7 @@ class AliSimDatasetGenerator(DatasetGenerator):
|
|
|
35
35
|
]
|
|
36
36
|
|
|
37
37
|
for key, value in self.args.items():
|
|
38
|
-
command.extend(
|
|
39
|
-
[key, value.format(**data) if isinstance(value, str) else str(value)]
|
|
40
|
-
)
|
|
38
|
+
command.extend([key, string(value, data)])
|
|
41
39
|
|
|
42
40
|
command.extend(["-af", "fasta"])
|
|
43
41
|
subprocess.run(command, check=True, stdout=subprocess.DEVNULL)
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import re
|
|
1
2
|
from typing import Any
|
|
2
3
|
|
|
3
4
|
import numpy as np
|
|
@@ -53,6 +54,14 @@ def scalar(x: cfg.Scalar, data: dict[str, Any]) -> pgt.Scalar:
|
|
|
53
54
|
return x
|
|
54
55
|
|
|
55
56
|
|
|
57
|
+
def string(s: Any, data: dict[str, Any]) -> str:
|
|
58
|
+
if not isinstance(s, str):
|
|
59
|
+
return str(s)
|
|
60
|
+
return re.sub(
|
|
61
|
+
r"\{([^{}]+)\}", lambda match: str(_eval_expression(match.group(1), data)), s
|
|
62
|
+
) # Match content inside curly braces
|
|
63
|
+
|
|
64
|
+
|
|
56
65
|
def many_scalars(x: cfg.ManyScalars, data: dict[str, Any]) -> pgt.ManyScalars:
|
|
57
66
|
if isinstance(x, str):
|
|
58
67
|
e = _eval_expression(x, data)
|
phylogenie/generators/trees.py
CHANGED
|
@@ -46,7 +46,7 @@ class ParameterizationType(str, Enum):
|
|
|
46
46
|
class TreeDatasetGenerator(DatasetGenerator):
|
|
47
47
|
data_type: Literal[DataType.TREES] = DataType.TREES
|
|
48
48
|
min_tips: cfg.Integer = 1
|
|
49
|
-
max_tips: cfg.Integer =
|
|
49
|
+
max_tips: cfg.Integer | None = None
|
|
50
50
|
max_time: cfg.Scalar = np.inf
|
|
51
51
|
init_state: str | None = None
|
|
52
52
|
sampling_probability_at_present: cfg.Scalar = 0.0
|
|
@@ -64,7 +64,7 @@ class TreeDatasetGenerator(DatasetGenerator):
|
|
|
64
64
|
return simulate_tree(
|
|
65
65
|
events=self._get_events(data),
|
|
66
66
|
min_tips=integer(self.min_tips, data),
|
|
67
|
-
max_tips=integer(self.max_tips, data),
|
|
67
|
+
max_tips=None if self.max_tips is None else integer(self.max_tips, data),
|
|
68
68
|
max_time=scalar(self.max_time, data),
|
|
69
69
|
init_state=init_state,
|
|
70
70
|
sampling_probability_at_present=scalar(
|
|
@@ -98,8 +98,8 @@ class CanonicalTreeDatasetGenerator(TreeDatasetGenerator):
|
|
|
98
98
|
ParameterizationType.CANONICAL
|
|
99
99
|
)
|
|
100
100
|
states: list[str]
|
|
101
|
-
sampling_rates: cfg.SkylineVector
|
|
102
|
-
remove_after_sampling: bool
|
|
101
|
+
sampling_rates: cfg.SkylineVector = 0
|
|
102
|
+
remove_after_sampling: bool = False
|
|
103
103
|
birth_rates: cfg.SkylineVector = 0
|
|
104
104
|
death_rates: cfg.SkylineVector = 0
|
|
105
105
|
migration_rates: cfg.SkylineMatrix = None
|
|
@@ -122,7 +122,7 @@ class CanonicalTreeDatasetGenerator(TreeDatasetGenerator):
|
|
|
122
122
|
class FBDTreeDatasetGenerator(TreeDatasetGenerator):
|
|
123
123
|
parameterization: Literal[ParameterizationType.FBD] = ParameterizationType.FBD
|
|
124
124
|
states: list[str]
|
|
125
|
-
sampling_proportions: cfg.SkylineVector
|
|
125
|
+
sampling_proportions: cfg.SkylineVector = 0
|
|
126
126
|
diversification: cfg.SkylineVector = 0
|
|
127
127
|
turnover: cfg.SkylineVector = 0
|
|
128
128
|
migration_rates: cfg.SkylineMatrix = None
|
|
@@ -218,7 +218,7 @@ class BDTreeDatasetGenerator(TreeDatasetGeneratorForEpidemiology):
|
|
|
218
218
|
parameterization: Literal[ParameterizationType.BD] = ParameterizationType.BD
|
|
219
219
|
reproduction_number: cfg.SkylineParameter
|
|
220
220
|
infectious_period: cfg.SkylineParameter
|
|
221
|
-
sampling_proportion: cfg.SkylineParameter
|
|
221
|
+
sampling_proportion: cfg.SkylineParameter
|
|
222
222
|
|
|
223
223
|
def _get_base_events(self, data: dict[str, Any]) -> list[Event]:
|
|
224
224
|
return get_BD_events(
|
|
@@ -233,7 +233,7 @@ class BDEITreeDatasetGenerator(TreeDatasetGeneratorForEpidemiology):
|
|
|
233
233
|
reproduction_number: cfg.SkylineParameter
|
|
234
234
|
infectious_period: cfg.SkylineParameter
|
|
235
235
|
incubation_period: cfg.SkylineParameter
|
|
236
|
-
sampling_proportion: cfg.SkylineParameter
|
|
236
|
+
sampling_proportion: cfg.SkylineParameter
|
|
237
237
|
|
|
238
238
|
def _get_base_events(self, data: dict[str, Any]) -> list[Event]:
|
|
239
239
|
return get_BDEI_events(
|
|
@@ -250,7 +250,7 @@ class BDSSTreeDatasetGenerator(TreeDatasetGeneratorForEpidemiology):
|
|
|
250
250
|
infectious_period: cfg.SkylineParameter
|
|
251
251
|
superspreading_ratio: cfg.SkylineParameter
|
|
252
252
|
superspreaders_proportion: cfg.SkylineParameter
|
|
253
|
-
sampling_proportion: cfg.SkylineParameter
|
|
253
|
+
sampling_proportion: cfg.SkylineParameter
|
|
254
254
|
|
|
255
255
|
def _get_base_events(self, data: dict[str, Any]) -> list[Event]:
|
|
256
256
|
return get_BDSS_events(
|
|
@@ -64,8 +64,8 @@ class Sampling(Event):
|
|
|
64
64
|
|
|
65
65
|
def get_canonical_events(
|
|
66
66
|
states: list[str],
|
|
67
|
-
sampling_rates: SkylineVectorCoercible,
|
|
68
|
-
remove_after_sampling: bool,
|
|
67
|
+
sampling_rates: SkylineVectorCoercible = 0,
|
|
68
|
+
remove_after_sampling: bool = False,
|
|
69
69
|
birth_rates: SkylineVectorCoercible = 0,
|
|
70
70
|
death_rates: SkylineVectorCoercible = 0,
|
|
71
71
|
migration_rates: SkylineMatrixCoercible | None = None,
|
|
@@ -100,7 +100,7 @@ def get_canonical_events(
|
|
|
100
100
|
|
|
101
101
|
def get_FBD_events(
|
|
102
102
|
states: list[str],
|
|
103
|
-
sampling_proportions: SkylineVectorCoercible =
|
|
103
|
+
sampling_proportions: SkylineVectorCoercible = 0,
|
|
104
104
|
diversification: SkylineVectorCoercible = 0,
|
|
105
105
|
turnover: SkylineVectorCoercible = 0,
|
|
106
106
|
migration_rates: SkylineMatrixCoercible | None = None,
|
|
@@ -134,7 +134,7 @@ def get_FBD_events(
|
|
|
134
134
|
|
|
135
135
|
def get_epidemiological_events(
|
|
136
136
|
states: list[str],
|
|
137
|
-
sampling_proportions: SkylineVectorCoercible
|
|
137
|
+
sampling_proportions: SkylineVectorCoercible,
|
|
138
138
|
reproduction_numbers: SkylineVectorCoercible = 0,
|
|
139
139
|
become_uninfectious_rates: SkylineVectorCoercible = 0,
|
|
140
140
|
migration_rates: SkylineMatrixCoercible | None = None,
|
|
@@ -172,7 +172,7 @@ def get_epidemiological_events(
|
|
|
172
172
|
def get_BD_events(
|
|
173
173
|
reproduction_number: SkylineParameterLike,
|
|
174
174
|
infectious_period: SkylineParameterLike,
|
|
175
|
-
sampling_proportion: SkylineParameterLike
|
|
175
|
+
sampling_proportion: SkylineParameterLike,
|
|
176
176
|
) -> list[Event]:
|
|
177
177
|
return get_epidemiological_events(
|
|
178
178
|
states=[INFECTIOUS_STATE],
|
|
@@ -186,7 +186,7 @@ def get_BDEI_events(
|
|
|
186
186
|
reproduction_number: SkylineParameterLike,
|
|
187
187
|
infectious_period: SkylineParameterLike,
|
|
188
188
|
incubation_period: SkylineParameterLike,
|
|
189
|
-
sampling_proportion: SkylineParameterLike
|
|
189
|
+
sampling_proportion: SkylineParameterLike,
|
|
190
190
|
) -> list[Event]:
|
|
191
191
|
return get_epidemiological_events(
|
|
192
192
|
states=[EXPOSED_STATE, INFECTIOUS_STATE],
|
|
@@ -202,7 +202,7 @@ def get_BDSS_events(
|
|
|
202
202
|
infectious_period: SkylineParameterLike,
|
|
203
203
|
superspreading_ratio: SkylineParameterLike,
|
|
204
204
|
superspreaders_proportion: SkylineParameterLike,
|
|
205
|
-
sampling_proportion: SkylineParameterLike
|
|
205
|
+
sampling_proportion: SkylineParameterLike,
|
|
206
206
|
) -> list[Event]:
|
|
207
207
|
f_SS = superspreaders_proportion
|
|
208
208
|
r_SS = superspreading_ratio
|
|
@@ -11,20 +11,18 @@ from phylogenie.io import dump_newick
|
|
|
11
11
|
from phylogenie.tree import Tree
|
|
12
12
|
from phylogenie.treesimulator.model import Event, Model
|
|
13
13
|
|
|
14
|
-
MAX_TIPS = 2**32
|
|
15
|
-
|
|
16
14
|
|
|
17
15
|
def simulate_tree(
|
|
18
16
|
events: Sequence[Event],
|
|
19
17
|
min_tips: int = 1,
|
|
20
|
-
max_tips: int =
|
|
18
|
+
max_tips: int | None = None,
|
|
21
19
|
max_time: float = np.inf,
|
|
22
20
|
init_state: str | None = None,
|
|
23
21
|
sampling_probability_at_present: float = 0.0,
|
|
24
22
|
seed: int | None = None,
|
|
25
23
|
timeout: float = np.inf,
|
|
26
24
|
) -> Tree:
|
|
27
|
-
if max_time == np.inf and max_tips
|
|
25
|
+
if max_time == np.inf and max_tips is None:
|
|
28
26
|
raise ValueError("Either max_time or max_tips must be specified.")
|
|
29
27
|
|
|
30
28
|
if max_time == np.inf and sampling_probability_at_present:
|
|
@@ -49,7 +47,11 @@ def simulate_tree(
|
|
|
49
47
|
current_time = 0.0
|
|
50
48
|
change_times = sorted(set(t for e in events for t in e.rate.change_times))
|
|
51
49
|
next_change_time = change_times.pop(0) if change_times else np.inf
|
|
52
|
-
|
|
50
|
+
if max_time == np.inf:
|
|
51
|
+
assert max_tips is not None
|
|
52
|
+
target_n_tips = rng.integers(min_tips, max_tips + 1)
|
|
53
|
+
else:
|
|
54
|
+
target_n_tips = None
|
|
53
55
|
|
|
54
56
|
while current_time < max_time:
|
|
55
57
|
if time.perf_counter() - start_clock > timeout:
|
|
@@ -66,7 +68,8 @@ def simulate_tree(
|
|
|
66
68
|
|
|
67
69
|
if (
|
|
68
70
|
not any(rates)
|
|
69
|
-
or
|
|
71
|
+
or max_tips is not None
|
|
72
|
+
and model.n_sampled > max_tips
|
|
70
73
|
or target_n_tips is not None
|
|
71
74
|
and model.n_sampled >= target_n_tips
|
|
72
75
|
):
|
|
@@ -89,7 +92,9 @@ def simulate_tree(
|
|
|
89
92
|
if rng.random() < sampling_probability_at_present:
|
|
90
93
|
model.sample(individual, current_time, True)
|
|
91
94
|
|
|
92
|
-
if min_tips <= model.n_sampled
|
|
95
|
+
if min_tips <= model.n_sampled and (
|
|
96
|
+
max_tips is None or model.n_sampled <= max_tips
|
|
97
|
+
):
|
|
93
98
|
return model.get_sampled_tree()
|
|
94
99
|
|
|
95
100
|
|
|
@@ -125,7 +130,7 @@ def generate_trees(
|
|
|
125
130
|
|
|
126
131
|
if os.path.exists(output_dir):
|
|
127
132
|
raise FileExistsError(f"Output directory {output_dir} already exists")
|
|
128
|
-
os.
|
|
133
|
+
os.makedirs(output_dir)
|
|
129
134
|
|
|
130
135
|
rng = default_rng(seed)
|
|
131
136
|
jobs = joblib.Parallel(n_jobs=n_jobs, return_as="generator_unordered")(
|
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
phylogenie/__init__.py,sha256=T2mRLsYtoLlWt8GlxrrUnfXJ9XVioq7hTvVq3uJpwQI,2215
|
|
2
2
|
phylogenie/generators/__init__.py,sha256=zsOxy28-9j9alOQLIgrOAFfmM58NNHO_NEtW-KXQXAY,888
|
|
3
|
-
phylogenie/generators/alisim.py,sha256=
|
|
3
|
+
phylogenie/generators/alisim.py,sha256=6IQEn8zNoVSLdHLRT1HBnrv1wfZzYaT-38SQNXE_MU4,2702
|
|
4
4
|
phylogenie/generators/configs.py,sha256=AiiFS6rpH9BPwDKCkT4SVrRzfLFFrwRCJM4CRj0Srdk,1072
|
|
5
5
|
phylogenie/generators/dataset.py,sha256=loVKC_1G7gzkPDN9W3GF-Rj9od8AeOJgIC0aJJa-4KA,2110
|
|
6
|
-
phylogenie/generators/factories.py,sha256=
|
|
7
|
-
phylogenie/generators/trees.py,sha256=
|
|
6
|
+
phylogenie/generators/factories.py,sha256=OKCNg9jwF2KahZCJKTdJVxhLTeLNBDMOqJs7XSVXTqY,7881
|
|
7
|
+
phylogenie/generators/trees.py,sha256=KEDvyrfMjUPWwyp1xnhWpatNnjmDLPhSSQl6Msx19Ms,10508
|
|
8
8
|
phylogenie/generators/typeguards.py,sha256=yj4VkhOaUXJ2OrY-6zhOeY9C4yKIQxjZtk2d-vIxttQ,828
|
|
9
9
|
phylogenie/io.py,sha256=y7nQIvLgCvqELsXFKfm1GgKJO_saoQ-7zQpE3Kvajzc,3509
|
|
10
10
|
phylogenie/main.py,sha256=vtvSpQxBNlYABoFQ25czl-l3fIr4QRo3svWVd-jcArw,1170
|
|
@@ -18,15 +18,15 @@ phylogenie/tree.py,sha256=KTx3m_tJPdeBqA5i0SA3dwCIobxsFcJwZFunMfDmVBY,2791
|
|
|
18
18
|
phylogenie/treesimulator/__init__.py,sha256=XG_xwETKWgDmCihqNUFCcMHtFg4WvZu5qbqWn9Dndt8,879
|
|
19
19
|
phylogenie/treesimulator/events/__init__.py,sha256=UGfvXOVJ_ZAkk_8sBPihjmxciiaEnXZEPFIY53sttWI,940
|
|
20
20
|
phylogenie/treesimulator/events/contact_tracing.py,sha256=_nJ85yhgGkeruQgMHvGpDYoyhheBf8M4LgZWiWdi5dY,4801
|
|
21
|
-
phylogenie/treesimulator/events/core.py,sha256=
|
|
21
|
+
phylogenie/treesimulator/events/core.py,sha256=RF7oHzAjkU675PnczaVc66d9gNrHBL-IhmVHtcy7MKE,7949
|
|
22
22
|
phylogenie/treesimulator/events/mutations.py,sha256=xkXUIppbLIWZqKwVf-hi7d-_pS42TG2EPVfJA_grxBg,3443
|
|
23
|
-
phylogenie/treesimulator/gillespie.py,sha256=
|
|
23
|
+
phylogenie/treesimulator/gillespie.py,sha256=EfEbuMBQSk9izamBPaQ9rNKA4NvtrI3XVm891G2iMeM,5014
|
|
24
24
|
phylogenie/treesimulator/model.py,sha256=0Im6cFTlpMlJrSP4pTTKtvLT9qrQWV8MSTesAsBxT8g,5422
|
|
25
25
|
phylogenie/typeguards.py,sha256=JtqmbEWJZBRHbWgCvcl6nrWm3VcBfzRbklbTBYHItn0,1325
|
|
26
26
|
phylogenie/typings.py,sha256=GknvAFXyiaWeeYJ8Lk5d6E2VHT-xW6ONEojYbtJYiB8,476
|
|
27
27
|
phylogenie/utils.py,sha256=pCg9ob0RpLUHwM49x4knKxL4FNPr3-EU_6zMXsvxtAg,370
|
|
28
|
-
phylogenie-2.1.
|
|
29
|
-
phylogenie-2.1.
|
|
30
|
-
phylogenie-2.1.
|
|
31
|
-
phylogenie-2.1.
|
|
32
|
-
phylogenie-2.1.
|
|
28
|
+
phylogenie-2.1.6.dist-info/LICENSE.txt,sha256=NUrDqElK-eD3I0WqC004CJsy6cs0JgsAoebDv_42-pw,1071
|
|
29
|
+
phylogenie-2.1.6.dist-info/METADATA,sha256=dkSGsLeSFma9nDy-6J_gAHlOEs2NxjUeJvo4Ey4x5WM,5375
|
|
30
|
+
phylogenie-2.1.6.dist-info/WHEEL,sha256=sP946D7jFCHeNz5Iq4fL4Lu-PrWrFsgfLXbbkciIZwg,88
|
|
31
|
+
phylogenie-2.1.6.dist-info/entry_points.txt,sha256=Rt6_usN0FkBX1ZfiqCirjMN9FKOgFLG8rydcQ8kugeE,51
|
|
32
|
+
phylogenie-2.1.6.dist-info/RECORD,,
|
|
File without changes
|
|
File without changes
|
|
File without changes
|