nova-clone 0.1.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.
Files changed (53) hide show
  1. nova_clone/__init__.py +1 -0
  2. nova_clone/algorithm/__init__.py +2 -0
  3. nova_clone/algorithm/_build_intbc_graph.py +135 -0
  4. nova_clone/algorithm/_call_clones_from_coresets.py +235 -0
  5. nova_clone/algorithm/_clone_call_ops.py +258 -0
  6. nova_clone/algorithm/_clone_calling_algorithm.py +1571 -0
  7. nova_clone/algorithm/_compute_cellbc_vs_coreset_overlap_matrix.py +143 -0
  8. nova_clone/algorithm/_compute_coreset_co_assignment_matrix.py +170 -0
  9. nova_clone/algorithm/_find_maximal_coresets.py +428 -0
  10. nova_clone/algorithm/_keep_reliable_edges.py +202 -0
  11. nova_clone/algorithm/_make_coresets_disjoint.py +114 -0
  12. nova_clone/algorithm/_prune_coresets.py +164 -0
  13. nova_clone/algorithm/_prune_custom_intbcs.py +150 -0
  14. nova_clone/algorithm/_prune_likely_homoplastic_intbcs.py +162 -0
  15. nova_clone/algorithm/_prune_likely_sequencing_errors.py +201 -0
  16. nova_clone/algorithm/_prune_low_cellbc_count_intbcs.py +154 -0
  17. nova_clone/algorithm/_prune_low_umi_count_intbcs.py +152 -0
  18. nova_clone/algorithm/_types.py +150 -0
  19. nova_clone/algorithm/_utils.py +53 -0
  20. nova_clone/algorithm/cassiopeia/__init__.py +1 -0
  21. nova_clone/algorithm/cassiopeia/_call_lineage_groups.py +270 -0
  22. nova_clone/caching/__init__.py +24 -0
  23. nova_clone/caching/_cached.py +175 -0
  24. nova_clone/caching/_cached_computation.py +369 -0
  25. nova_clone/caching/_cached_parallel_computation.py +428 -0
  26. nova_clone/caching/_common.py +200 -0
  27. nova_clone/data/__init__.py +1 -0
  28. nova_clone/qc/__init__.py +179 -0
  29. nova_clone/qc/_clone_intbc_sets.py +234 -0
  30. nova_clone/qc/_compare_clone_calls.py +218 -0
  31. nova_clone/qc/_data_retention.py +175 -0
  32. nova_clone/qc/_homoplasy.py +81 -0
  33. nova_clone/qc/_inter_clonal_kinship.py +60 -0
  34. nova_clone/qc/_intra_clonal_kinship.py +172 -0
  35. nova_clone/qc/_multiplet_rate.py +158 -0
  36. nova_clone/qc/_number_of_clones.py +153 -0
  37. nova_clone/qc/_pre_qc.py +485 -0
  38. nova_clone/simulation/HDBSCAN_method_adjusted.py +68 -0
  39. nova_clone/simulation/__init__.py +0 -0
  40. nova_clone/simulation/_caching.py +40 -0
  41. nova_clone/simulation/benchmarking.py +1221 -0
  42. nova_clone/simulation/clone_to_sequences.py +408 -0
  43. nova_clone/simulation/creating_tree.py +416 -0
  44. nova_clone/simulation/evaluation.py +344 -0
  45. nova_clone/simulation/jaccard_hierarchical_by_intBC.py +78 -0
  46. nova_clone/simulation/plot_benchmark_lines.py +226 -0
  47. nova_clone/simulation/slice_benchmark.py +640 -0
  48. nova_clone/simulation/slice_benchmark_clone_calling.py +68 -0
  49. nova_clone-0.1.0.dist-info/METADATA +298 -0
  50. nova_clone-0.1.0.dist-info/RECORD +53 -0
  51. nova_clone-0.1.0.dist-info/WHEEL +5 -0
  52. nova_clone-0.1.0.dist-info/licenses/LICENSE +28 -0
  53. nova_clone-0.1.0.dist-info/top_level.txt +1 -0
@@ -0,0 +1,143 @@
1
+ """
2
+ Module for computing the overlap (intersection) between intBC sets (of cellBCs)
3
+ and coresets.
4
+
5
+ The main function exposed by this module is `compute_cellbc_vs_coreset_overlap_matrix`.
6
+ """
7
+
8
+ import logging
9
+ import sys
10
+ import time
11
+ from typing import *
12
+
13
+ from multiset import Multiset
14
+ import numpy as np
15
+ import tqdm
16
+
17
+ from ._types import *
18
+ from ._utils import _cell_intbc_sets_from_intbc_tables
19
+
20
+
21
+ def _init_logger():
22
+ logger = logging.getLogger(__name__)
23
+ logger.setLevel(logging.INFO)
24
+ fmt_str = "[%(asctime)s] - %(name)s - %(levelname)s - %(message)s"
25
+ formatter = logging.Formatter(fmt_str)
26
+
27
+ consoleHandler = logging.StreamHandler(sys.stdout)
28
+ consoleHandler.setFormatter(formatter)
29
+ logger.addHandler(consoleHandler)
30
+
31
+
32
+ _init_logger()
33
+
34
+
35
+ class ComputeCellBCvsCoresetOverlapMatrixReturnType(NamedTuple):
36
+ """
37
+ Object returned by the `compute_cellbc_vs_coreset_overlap_matrix` function.
38
+
39
+ Attributes:
40
+ cellbc_vs_coreset_overlap_matrix: Of size #cellBC x #coresets, the
41
+ size of the intersection between the intBC set of each cellBC and
42
+ each coreset.
43
+ total_time: Total time taken.
44
+ """
45
+
46
+ cellbc_vs_coreset_overlap_matrix: pd.DataFrame
47
+ total_time: float
48
+
49
+
50
+ def compute_cellbc_vs_coreset_overlap_matrix(
51
+ cellbc_intbc_sets: Dict[IntBCType, Set[IntBCType]],
52
+ coresets: List[Coreset[IntBCType]],
53
+ ) -> ComputeCellBCvsCoresetOverlapMatrixReturnType:
54
+ """
55
+ Pandas dataframe of cell vs coreset.
56
+
57
+ Entry (i, j) contains the overlap of cell i's intBC set with coreset j.
58
+ """
59
+ st = time.time()
60
+ logger = logging.getLogger(__name__)
61
+ logger.info("Going to compute_cellbc_vs_coreset_overlap_matrix ...")
62
+ cells = sorted(cellbc_intbc_sets.keys())
63
+ res_array = np.zeros(shape=(len(cells), len(coresets)))
64
+
65
+ for cell_idx, cell in tqdm.tqdm(list(enumerate(cells))):
66
+ cell_intbc_set = cellbc_intbc_sets[cell]
67
+ for coreset_idx, coreset in enumerate(coresets):
68
+ overlap = len([intbc for intbc in coreset if intbc in cell_intbc_set]) # Handles multiset coresets (for single-intBC support)
69
+ res_array[cell_idx, coreset_idx] = overlap
70
+
71
+ cellbc_vs_coreset_overlap_matrix = pd.DataFrame(
72
+ res_array,
73
+ index=cells,
74
+ columns=list(range(len(coresets))),
75
+ )
76
+ total_time = time.time() - st
77
+ res = ComputeCellBCvsCoresetOverlapMatrixReturnType(
78
+ cellbc_vs_coreset_overlap_matrix=cellbc_vs_coreset_overlap_matrix,
79
+ total_time=total_time,
80
+ )
81
+ logger.info(
82
+ f"Done with compute_cellbc_vs_coreset_overlap_matrix! Total time: {total_time}"
83
+ )
84
+ return res
85
+
86
+
87
+ def test_compute_cell_vs_coreset_overlap_matrix():
88
+ cellbc_intbc_sets = {
89
+ "cell_1": {"1", "2", "3"},
90
+ "cell_2": {"4", "5", "6"},
91
+ "cell_3": {"1", "2", "3", "4", "5", "6"},
92
+ "cell_4": {"1", "2", "4"},
93
+ }
94
+ coresets = [
95
+ {"1", "2", "3"},
96
+ {"4", "5", "6"},
97
+ ]
98
+ mat = compute_cellbc_vs_coreset_overlap_matrix(
99
+ cellbc_intbc_sets=cellbc_intbc_sets,
100
+ coresets=coresets,
101
+ ).cellbc_vs_coreset_overlap_matrix
102
+ np.testing.assert_equal(
103
+ mat,
104
+ np.array(
105
+ [
106
+ [3, 0],
107
+ [0, 3],
108
+ [3, 3],
109
+ [2, 1],
110
+ ]
111
+ ),
112
+ )
113
+
114
+
115
+ def test_compute_cell_vs_coreset_overlap_matrix_with_multisets():
116
+ cellbc_intbc_sets = {
117
+ "cell_1": {"1", "2"},
118
+ "cell_2": {"1", "3"},
119
+ "cell_3": {"1", "2", "3"},
120
+ "cell_4": {"1", "2", "4"},
121
+ "cell_5": {"4"},
122
+ }
123
+ coresets = [
124
+ {"1", "2"},
125
+ {"1", "3"},
126
+ Multiset(["4"]) + Multiset(["4"]),
127
+ ]
128
+ mat = compute_cellbc_vs_coreset_overlap_matrix(
129
+ cellbc_intbc_sets=cellbc_intbc_sets,
130
+ coresets=coresets,
131
+ ).cellbc_vs_coreset_overlap_matrix
132
+ np.testing.assert_equal(
133
+ mat,
134
+ np.array(
135
+ [
136
+ [2, 1, 0],
137
+ [1, 2, 0],
138
+ [2, 2, 0],
139
+ [2, 1, 2],
140
+ [0, 0, 2],
141
+ ]
142
+ ),
143
+ )
@@ -0,0 +1,170 @@
1
+ """
2
+ Module for computing the number of cellBCs assigned to two coresets.
3
+
4
+ The main function exposed by this module is `compute_coreset_co_assignment_matrix`.
5
+ """
6
+
7
+ import logging
8
+ import sys
9
+ import time
10
+ from typing import *
11
+ from multiset import Multiset
12
+
13
+ import numpy as np
14
+ import tqdm
15
+
16
+ from ._types import *
17
+
18
+
19
+ def _init_logger():
20
+ logger = logging.getLogger(__name__)
21
+ logger.setLevel(logging.INFO)
22
+ fmt_str = "[%(asctime)s] - %(name)s - %(levelname)s - %(message)s"
23
+ formatter = logging.Formatter(fmt_str)
24
+
25
+ consoleHandler = logging.StreamHandler(sys.stdout)
26
+ consoleHandler.setFormatter(formatter)
27
+ logger.addHandler(consoleHandler)
28
+
29
+
30
+ _init_logger()
31
+
32
+
33
+ class ComputeCoresetCoAssignmentMatrixReturnType(NamedTuple):
34
+ """
35
+ Object returned by the `compute_coreset_co_assignment_matrix` function.
36
+
37
+ Attributes:
38
+ coreset_co_assignment_matrix: #coresets x #coresets, a numpy array
39
+ containing the number of cellBCs mapping to those two coresets.
40
+ (In particular, the diagonal contains the number of cellBC mapping
41
+ to that coerset).
42
+ total_time: Total time taken.
43
+ """
44
+
45
+ coreset_co_assignment_matrix: pd.DataFrame
46
+ total_time: float
47
+
48
+
49
+ def compute_coreset_co_assignment_matrix(
50
+ cellbc_intbc_sets: Dict[CellBCType, Set[IntBCType]],
51
+ coresets: List[Coreset[IntBCType]],
52
+ min_overlap_for_assigning_cellbc: int,
53
+ ) -> ComputeCoresetCoAssignmentMatrixReturnType:
54
+ """
55
+ Map cells to coresets to build the coreset co-assignment matrix.
56
+
57
+ The coreset co-assignment matrix M contains the statistics:
58
+ M_{i,j} = #(cell assigned to coresets i and j)
59
+ """
60
+ st = time.time()
61
+ logger = logging.getLogger(__name__)
62
+ logger.info("Going to compute_coreset_co_assignment_matrix ...")
63
+ num_coresets = len(coresets)
64
+ res = np.zeros(shape=(num_coresets, num_coresets))
65
+ for cell, cell_intbc_set in tqdm.tqdm(cellbc_intbc_sets.items()):
66
+ coresets_assigned = []
67
+ for coreset_idx, coreset in enumerate(coresets):
68
+ overlap = len([intbc for intbc in coreset if intbc in cell_intbc_set]) # Handles multiset coresets
69
+ if overlap >= min_overlap_for_assigning_cellbc:
70
+ coresets_assigned.append(coreset_idx)
71
+ for coreset_idx_1 in coresets_assigned:
72
+ for coreset_idx_2 in coresets_assigned:
73
+ if coreset_idx_1 < coreset_idx_2:
74
+ res[coreset_idx_1, coreset_idx_2] += 1
75
+ res[coreset_idx_2, coreset_idx_1] += 1
76
+ elif coreset_idx_1 == coreset_idx_2:
77
+ res[coreset_idx_1, coreset_idx_2] += 1
78
+ total_time = time.time() - st
79
+ res = ComputeCoresetCoAssignmentMatrixReturnType(
80
+ coreset_co_assignment_matrix=res,
81
+ total_time=total_time,
82
+ )
83
+ logger.info(
84
+ f"Done with compute_coreset_co_assignment_matrix! Total time: {total_time}"
85
+ )
86
+ return res
87
+
88
+
89
+ def test_compute_coreset_co_assignment_matrix():
90
+ cellbc_intbc_sets = {
91
+ "cell_1": {"1", "2", "3"},
92
+ "cell_2": {"4", "5", "6"},
93
+ "cell_3": {"1", "2", "3", "4", "5", "6"},
94
+ "cell_4": {"1", "2", "4"},
95
+ }
96
+ coresets = [
97
+ {"1", "2", "3"},
98
+ {"4", "5", "6"},
99
+ ]
100
+ mat = compute_coreset_co_assignment_matrix(
101
+ cellbc_intbc_sets=cellbc_intbc_sets,
102
+ coresets=coresets,
103
+ min_overlap_for_assigning_cellbc=3,
104
+ ).coreset_co_assignment_matrix
105
+ np.testing.assert_equal(
106
+ mat,
107
+ np.array(
108
+ [
109
+ [2, 1],
110
+ [1, 2],
111
+ ]
112
+ ),
113
+ )
114
+ mat = compute_coreset_co_assignment_matrix(
115
+ cellbc_intbc_sets=cellbc_intbc_sets,
116
+ coresets=coresets,
117
+ min_overlap_for_assigning_cellbc=2,
118
+ ).coreset_co_assignment_matrix
119
+ np.testing.assert_equal(
120
+ mat,
121
+ np.array(
122
+ [
123
+ [3, 1],
124
+ [1, 2],
125
+ ]
126
+ ),
127
+ )
128
+ mat = compute_coreset_co_assignment_matrix(
129
+ cellbc_intbc_sets=cellbc_intbc_sets,
130
+ coresets=coresets,
131
+ min_overlap_for_assigning_cellbc=1,
132
+ ).coreset_co_assignment_matrix
133
+ np.testing.assert_equal(
134
+ mat,
135
+ np.array(
136
+ [
137
+ [3, 2],
138
+ [2, 3],
139
+ ]
140
+ ),
141
+ )
142
+
143
+
144
+ def test_compute_coreset_co_assignment_matrix_multisets():
145
+ cellbc_intbc_sets = {
146
+ "cell_1": {"1", "2"},
147
+ "cell_2": {"1", "3"},
148
+ "cell_3": {"1", "2", "3"},
149
+ "cell_4": {"1", "2", "4"},
150
+ }
151
+ coresets = [
152
+ {"1", "2"},
153
+ {"1", "3"},
154
+ Multiset(["4"]) + Multiset(["4"]),
155
+ ]
156
+ mat = compute_coreset_co_assignment_matrix(
157
+ cellbc_intbc_sets=cellbc_intbc_sets,
158
+ coresets=coresets,
159
+ min_overlap_for_assigning_cellbc=2,
160
+ ).coreset_co_assignment_matrix
161
+ np.testing.assert_equal(
162
+ mat,
163
+ np.array(
164
+ [
165
+ [3, 1, 1],
166
+ [1, 2, 0],
167
+ [1, 0, 1],
168
+ ]
169
+ ),
170
+ )