numba-utils 0.1.0__tar.gz

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 (56) hide show
  1. numba_utils-0.1.0/LICENSE +21 -0
  2. numba_utils-0.1.0/PKG-INFO +191 -0
  3. numba_utils-0.1.0/README.md +152 -0
  4. numba_utils-0.1.0/numba_utils/__init__.py +137 -0
  5. numba_utils-0.1.0/numba_utils/_config.py +92 -0
  6. numba_utils-0.1.0/numba_utils/algorithms/__init__.py +26 -0
  7. numba_utils-0.1.0/numba_utils/algorithms/_select.py +123 -0
  8. numba_utils-0.1.0/numba_utils/algorithms/_sort.py +166 -0
  9. numba_utils-0.1.0/numba_utils/algorithms/_topk.py +87 -0
  10. numba_utils-0.1.0/numba_utils/arrays/__init__.py +21 -0
  11. numba_utils-0.1.0/numba_utils/arrays/_hist.py +56 -0
  12. numba_utils-0.1.0/numba_utils/arrays/_rolling.py +50 -0
  13. numba_utils-0.1.0/numba_utils/arrays/_search.py +64 -0
  14. numba_utils-0.1.0/numba_utils/arrays/_transform.py +89 -0
  15. numba_utils-0.1.0/numba_utils/arrays/_unique.py +34 -0
  16. numba_utils-0.1.0/numba_utils/collections/__init__.py +28 -0
  17. numba_utils-0.1.0/numba_utils/collections/_bitset.py +57 -0
  18. numba_utils-0.1.0/numba_utils/collections/_heap.py +72 -0
  19. numba_utils-0.1.0/numba_utils/collections/_sparse.py +105 -0
  20. numba_utils-0.1.0/numba_utils/collections/_stack_queue.py +123 -0
  21. numba_utils-0.1.0/numba_utils/collections/_typed.py +58 -0
  22. numba_utils-0.1.0/numba_utils/decorators/__init__.py +19 -0
  23. numba_utils-0.1.0/numba_utils/decorators/_wrappers.py +118 -0
  24. numba_utils-0.1.0/numba_utils/diagnostics/__init__.py +13 -0
  25. numba_utils-0.1.0/numba_utils/diagnostics/_inspect.py +190 -0
  26. numba_utils-0.1.0/numba_utils/parallel/__init__.py +31 -0
  27. numba_utils-0.1.0/numba_utils/parallel/_histogram.py +59 -0
  28. numba_utils-0.1.0/numba_utils/parallel/_reduce.py +86 -0
  29. numba_utils-0.1.0/numba_utils/parallel/_scan.py +65 -0
  30. numba_utils-0.1.0/numba_utils/parallel/_topk.py +86 -0
  31. numba_utils-0.1.0/numba_utils/profiling/__init__.py +21 -0
  32. numba_utils-0.1.0/numba_utils/profiling/_compare.py +118 -0
  33. numba_utils-0.1.0/numba_utils/profiling/_timer.py +144 -0
  34. numba_utils-0.1.0/numba_utils/random/__init__.py +27 -0
  35. numba_utils-0.1.0/numba_utils/random/_rng.py +59 -0
  36. numba_utils-0.1.0/numba_utils/random/_sampling.py +142 -0
  37. numba_utils-0.1.0/numba_utils/testing/__init__.py +24 -0
  38. numba_utils-0.1.0/numba_utils/testing/_asserts.py +93 -0
  39. numba_utils-0.1.0/numba_utils/testing/_generators.py +63 -0
  40. numba_utils-0.1.0/numba_utils.egg-info/PKG-INFO +191 -0
  41. numba_utils-0.1.0/numba_utils.egg-info/SOURCES.txt +54 -0
  42. numba_utils-0.1.0/numba_utils.egg-info/dependency_links.txt +1 -0
  43. numba_utils-0.1.0/numba_utils.egg-info/requires.txt +10 -0
  44. numba_utils-0.1.0/numba_utils.egg-info/top_level.txt +1 -0
  45. numba_utils-0.1.0/pyproject.toml +69 -0
  46. numba_utils-0.1.0/setup.cfg +4 -0
  47. numba_utils-0.1.0/tests/test_algorithms.py +206 -0
  48. numba_utils-0.1.0/tests/test_arrays.py +187 -0
  49. numba_utils-0.1.0/tests/test_collections.py +285 -0
  50. numba_utils-0.1.0/tests/test_config.py +75 -0
  51. numba_utils-0.1.0/tests/test_decorators.py +125 -0
  52. numba_utils-0.1.0/tests/test_diagnostics.py +100 -0
  53. numba_utils-0.1.0/tests/test_parallel.py +138 -0
  54. numba_utils-0.1.0/tests/test_profiling.py +156 -0
  55. numba_utils-0.1.0/tests/test_random.py +174 -0
  56. numba_utils-0.1.0/tests/test_testing.py +118 -0
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 Nicolás Seijas
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
@@ -0,0 +1,191 @@
1
+ Metadata-Version: 2.4
2
+ Name: numba-utils
3
+ Version: 0.1.0
4
+ Summary: Battle-tested building blocks for production Numba workloads.
5
+ Author-email: Nicolás Seijas <nicoseijas@gmail.com>
6
+ License: MIT
7
+ Project-URL: Homepage, https://github.com/nicoseijas/numba-utils
8
+ Project-URL: Repository, https://github.com/nicoseijas/numba-utils
9
+ Project-URL: Documentation, https://nicoseijas.github.io/numba-utils/
10
+ Project-URL: Changelog, https://github.com/nicoseijas/numba-utils/blob/main/CHANGELOG.md
11
+ Project-URL: Issues, https://github.com/nicoseijas/numba-utils/issues
12
+ Keywords: numba,njit,jit,high-performance,numerical-computing,hpc,parallel,benchmarking,data-structures
13
+ Classifier: Development Status :: 4 - Beta
14
+ Classifier: Intended Audience :: Developers
15
+ Classifier: Intended Audience :: Science/Research
16
+ Classifier: License :: OSI Approved :: MIT License
17
+ Classifier: Operating System :: OS Independent
18
+ Classifier: Programming Language :: Python :: 3
19
+ Classifier: Programming Language :: Python :: 3.10
20
+ Classifier: Programming Language :: Python :: 3.11
21
+ Classifier: Programming Language :: Python :: 3.12
22
+ Classifier: Programming Language :: Python :: 3.13
23
+ Classifier: Programming Language :: Python :: Implementation :: CPython
24
+ Classifier: Topic :: Scientific/Engineering
25
+ Classifier: Topic :: Software Development :: Libraries
26
+ Classifier: Typing :: Typed
27
+ Requires-Python: >=3.10
28
+ Description-Content-Type: text/markdown
29
+ License-File: LICENSE
30
+ Requires-Dist: numba
31
+ Requires-Dist: numpy
32
+ Provides-Extra: dev
33
+ Requires-Dist: pytest; extra == "dev"
34
+ Requires-Dist: build; extra == "dev"
35
+ Requires-Dist: twine; extra == "dev"
36
+ Provides-Extra: docs
37
+ Requires-Dist: mkdocs-material>=9.5; extra == "docs"
38
+ Dynamic: license-file
39
+
40
+ # numba-utils
41
+
42
+ **Battle-tested building blocks for production
43
+ [Numba](https://numba.pydata.org/) workloads.** Built for production
44
+ numerical software with Numba.
45
+
46
+ ✓ Zero dependencies beyond NumPy + Numba &nbsp;·&nbsp; ✓ Callable inside
47
+ `@njit` &nbsp;·&nbsp; ✓ Honest benchmarks &nbsp;·&nbsp; ✓ Diagnostics
48
+ &nbsp;·&nbsp; ✓ CI &nbsp;·&nbsp; ✓ MIT
49
+
50
+ ```
51
+ Numba
52
+
53
+
54
+ numba-utils
55
+ ┌───────────────┼───────────────┐
56
+ Arrays Collections Parallel
57
+ Algorithms Random Profiling
58
+ Decorators Testing Diagnostics
59
+ ```
60
+
61
+ ```python
62
+ from numba import njit
63
+ from numba_utils import topk
64
+
65
+ @njit
66
+ def winners(scores):
67
+ return topk(scores, 10) # O(n), no full sort — runs in nopython mode
68
+ ```
69
+
70
+ ```python
71
+ from numba import njit
72
+ from numba_utils import PriorityQueue, SparseSet
73
+
74
+ @njit
75
+ def simulate(n_events):
76
+ events = PriorityQueue(n_events) # constructed in nopython mode
77
+ active = SparseSet(100_000) # O(1) add/discard/contains/clear
78
+ ...
79
+ ```
80
+
81
+ ```python
82
+ from numba_utils import compare
83
+
84
+ compare(numpy_impl, njit_impl, args=(values,))
85
+ # 31x on a fused kernel — JIT compilation excluded automatically
86
+ ```
87
+
88
+ And the part that almost no library ships — diagnostics for compiled
89
+ code:
90
+
91
+ ```python
92
+ >>> from numba_utils import diagnostics
93
+ >>> diagnostics.check(fn)
94
+ ⚠ cache=True may crash when loaded across processes (farms, network FS)
95
+ → NUMBA_UTILS_CACHE=0 or configure(cache=False)
96
+ ⚠ fastmath=True relaxes IEEE 754 — not for exact/reproducible results
97
+ ```
98
+
99
+ ## Why this exists
100
+
101
+ After enough numerical projects — long-running Monte Carlo engines,
102
+ solvers, simulation farms — you realize you've rewritten the same binary
103
+ search, the same typed collections, the same sampling algorithms and the
104
+ same benchmarking helpers again. And debugged the same Numba production
105
+ surprises again.
106
+
107
+ numba-utils ships more than code. It ships the production knowledge
108
+ that usually stays trapped inside numerical projects — as kernels with
109
+ the pitfalls engineered around, as diagnostics, and as
110
+ [documentation](https://github.com/nicoseijas/numba-utils/tree/main/docs).
111
+ It does not compete with Numba: it builds on top of it.
112
+
113
+ ## Why not...
114
+
115
+ - **heapq / `collections`?** They can't be called from nopython mode.
116
+ The containers here are jitclasses usable inside `@njit`.
117
+ - **NumPy?** Many helpers are built to run *inside* compiled kernels,
118
+ where NumPy calls can't reach. Where NumPy is faster (bandwidth-bound
119
+ sweeps, its SIMD sort),
120
+ [BENCHMARKS.md](https://github.com/nicoseijas/numba-utils/blob/main/BENCHMARKS.md)
121
+ says so.
122
+ - **SciPy?** A heavy dependency that isn't njit-callable; this stays at
123
+ NumPy + Numba and works in the compiled path.
124
+ - **Numba itself?** Numba is a compiler. numba-utils is a standard
125
+ library on top of it.
126
+
127
+ ## Design principles
128
+
129
+ 1. **Performance First** — nothing ships without a benchmarked justification.
130
+ 2. **No Hidden Magic** — thin, readable layers over Numba; nothing rewrites your code.
131
+ 3. **Numba Compatible** — everything callable from your own `@njit` code, no hacks.
132
+ 4. **Minimal APIs** — `topk(arr, 10)`, not twenty keyword parameters.
133
+ 5. **Benchmark Honesty** — losses are published next to the wins.
134
+
135
+ The identity behind these:
136
+ [docs/philosophy.md](https://github.com/nicoseijas/numba-utils/blob/main/docs/philosophy.md).
137
+
138
+ ## Modules
139
+
140
+ **Core** — decorators, arrays, algorithms ·
141
+ **Performance** — parallel (complete operations, not prange wrappers),
142
+ profiling (JIT excluded by default), diagnostics ·
143
+ **Data structures** — collections, random ·
144
+ **Developer tools** — testing, config
145
+
146
+ Full API:
147
+ [docs/modules.md](https://github.com/nicoseijas/numba-utils/blob/main/docs/modules.md)
148
+ · Runnable code:
149
+ [examples/](https://github.com/nicoseijas/numba-utils/tree/main/examples)
150
+
151
+ ## Benchmark honesty
152
+
153
+ Every algorithm states whether it is **faster**, **similar but more
154
+ ergonomic**, or **slower but solving a problem unavailable elsewhere**.
155
+ [BENCHMARKS.md](https://github.com/nicoseijas/numba-utils/blob/main/BENCHMARKS.md)
156
+ contains losing rows on purpose: they tell you when NOT to use a
157
+ function. Backed in-repo by reproducible
158
+ [benchmarks/](https://github.com/nicoseijas/numba-utils/tree/main/benchmarks),
159
+ 200+ reference-validated tests
160
+ ([why there's no coverage badge](https://github.com/nicoseijas/numba-utils/blob/main/docs/testing.md)),
161
+ and CI running all of it. Trade-off records:
162
+ [docs/design/](https://github.com/nicoseijas/numba-utils/tree/main/docs/design).
163
+
164
+ ## Used in
165
+
166
+ Patterns extracted from real workloads: Monte Carlo equity engines,
167
+ game-theory solvers (CFR), quantitative research, scientific
168
+ simulations, optimization loops.
169
+
170
+ ## Status
171
+
172
+ Phase 1 (see
173
+ [ROADMAP.md](https://github.com/nicoseijas/numba-utils/blob/main/ROADMAP.md)):
174
+
175
+ - [x] decorators, profiling, diagnostics, config
176
+ - [x] arrays, algorithms, random, collections
177
+ - [x] parallel patterns, testing helpers
178
+ - [ ] dtype-generic collections, `stable_argsort`, `lexsort`
179
+ - [ ] PyPI release
180
+
181
+ ## Development
182
+
183
+ ```
184
+ python -m venv .venv
185
+ .venv/Scripts/pip install -e .[dev]
186
+ .venv/Scripts/python -m pytest
187
+ ```
188
+
189
+ Contributions follow
190
+ [GUIDELINES.md](https://github.com/nicoseijas/numba-utils/blob/main/GUIDELINES.md)
191
+ — benchmarks are mandatory, honesty is policy.
@@ -0,0 +1,152 @@
1
+ # numba-utils
2
+
3
+ **Battle-tested building blocks for production
4
+ [Numba](https://numba.pydata.org/) workloads.** Built for production
5
+ numerical software with Numba.
6
+
7
+ ✓ Zero dependencies beyond NumPy + Numba &nbsp;·&nbsp; ✓ Callable inside
8
+ `@njit` &nbsp;·&nbsp; ✓ Honest benchmarks &nbsp;·&nbsp; ✓ Diagnostics
9
+ &nbsp;·&nbsp; ✓ CI &nbsp;·&nbsp; ✓ MIT
10
+
11
+ ```
12
+ Numba
13
+
14
+
15
+ numba-utils
16
+ ┌───────────────┼───────────────┐
17
+ Arrays Collections Parallel
18
+ Algorithms Random Profiling
19
+ Decorators Testing Diagnostics
20
+ ```
21
+
22
+ ```python
23
+ from numba import njit
24
+ from numba_utils import topk
25
+
26
+ @njit
27
+ def winners(scores):
28
+ return topk(scores, 10) # O(n), no full sort — runs in nopython mode
29
+ ```
30
+
31
+ ```python
32
+ from numba import njit
33
+ from numba_utils import PriorityQueue, SparseSet
34
+
35
+ @njit
36
+ def simulate(n_events):
37
+ events = PriorityQueue(n_events) # constructed in nopython mode
38
+ active = SparseSet(100_000) # O(1) add/discard/contains/clear
39
+ ...
40
+ ```
41
+
42
+ ```python
43
+ from numba_utils import compare
44
+
45
+ compare(numpy_impl, njit_impl, args=(values,))
46
+ # 31x on a fused kernel — JIT compilation excluded automatically
47
+ ```
48
+
49
+ And the part that almost no library ships — diagnostics for compiled
50
+ code:
51
+
52
+ ```python
53
+ >>> from numba_utils import diagnostics
54
+ >>> diagnostics.check(fn)
55
+ ⚠ cache=True may crash when loaded across processes (farms, network FS)
56
+ → NUMBA_UTILS_CACHE=0 or configure(cache=False)
57
+ ⚠ fastmath=True relaxes IEEE 754 — not for exact/reproducible results
58
+ ```
59
+
60
+ ## Why this exists
61
+
62
+ After enough numerical projects — long-running Monte Carlo engines,
63
+ solvers, simulation farms — you realize you've rewritten the same binary
64
+ search, the same typed collections, the same sampling algorithms and the
65
+ same benchmarking helpers again. And debugged the same Numba production
66
+ surprises again.
67
+
68
+ numba-utils ships more than code. It ships the production knowledge
69
+ that usually stays trapped inside numerical projects — as kernels with
70
+ the pitfalls engineered around, as diagnostics, and as
71
+ [documentation](https://github.com/nicoseijas/numba-utils/tree/main/docs).
72
+ It does not compete with Numba: it builds on top of it.
73
+
74
+ ## Why not...
75
+
76
+ - **heapq / `collections`?** They can't be called from nopython mode.
77
+ The containers here are jitclasses usable inside `@njit`.
78
+ - **NumPy?** Many helpers are built to run *inside* compiled kernels,
79
+ where NumPy calls can't reach. Where NumPy is faster (bandwidth-bound
80
+ sweeps, its SIMD sort),
81
+ [BENCHMARKS.md](https://github.com/nicoseijas/numba-utils/blob/main/BENCHMARKS.md)
82
+ says so.
83
+ - **SciPy?** A heavy dependency that isn't njit-callable; this stays at
84
+ NumPy + Numba and works in the compiled path.
85
+ - **Numba itself?** Numba is a compiler. numba-utils is a standard
86
+ library on top of it.
87
+
88
+ ## Design principles
89
+
90
+ 1. **Performance First** — nothing ships without a benchmarked justification.
91
+ 2. **No Hidden Magic** — thin, readable layers over Numba; nothing rewrites your code.
92
+ 3. **Numba Compatible** — everything callable from your own `@njit` code, no hacks.
93
+ 4. **Minimal APIs** — `topk(arr, 10)`, not twenty keyword parameters.
94
+ 5. **Benchmark Honesty** — losses are published next to the wins.
95
+
96
+ The identity behind these:
97
+ [docs/philosophy.md](https://github.com/nicoseijas/numba-utils/blob/main/docs/philosophy.md).
98
+
99
+ ## Modules
100
+
101
+ **Core** — decorators, arrays, algorithms ·
102
+ **Performance** — parallel (complete operations, not prange wrappers),
103
+ profiling (JIT excluded by default), diagnostics ·
104
+ **Data structures** — collections, random ·
105
+ **Developer tools** — testing, config
106
+
107
+ Full API:
108
+ [docs/modules.md](https://github.com/nicoseijas/numba-utils/blob/main/docs/modules.md)
109
+ · Runnable code:
110
+ [examples/](https://github.com/nicoseijas/numba-utils/tree/main/examples)
111
+
112
+ ## Benchmark honesty
113
+
114
+ Every algorithm states whether it is **faster**, **similar but more
115
+ ergonomic**, or **slower but solving a problem unavailable elsewhere**.
116
+ [BENCHMARKS.md](https://github.com/nicoseijas/numba-utils/blob/main/BENCHMARKS.md)
117
+ contains losing rows on purpose: they tell you when NOT to use a
118
+ function. Backed in-repo by reproducible
119
+ [benchmarks/](https://github.com/nicoseijas/numba-utils/tree/main/benchmarks),
120
+ 200+ reference-validated tests
121
+ ([why there's no coverage badge](https://github.com/nicoseijas/numba-utils/blob/main/docs/testing.md)),
122
+ and CI running all of it. Trade-off records:
123
+ [docs/design/](https://github.com/nicoseijas/numba-utils/tree/main/docs/design).
124
+
125
+ ## Used in
126
+
127
+ Patterns extracted from real workloads: Monte Carlo equity engines,
128
+ game-theory solvers (CFR), quantitative research, scientific
129
+ simulations, optimization loops.
130
+
131
+ ## Status
132
+
133
+ Phase 1 (see
134
+ [ROADMAP.md](https://github.com/nicoseijas/numba-utils/blob/main/ROADMAP.md)):
135
+
136
+ - [x] decorators, profiling, diagnostics, config
137
+ - [x] arrays, algorithms, random, collections
138
+ - [x] parallel patterns, testing helpers
139
+ - [ ] dtype-generic collections, `stable_argsort`, `lexsort`
140
+ - [ ] PyPI release
141
+
142
+ ## Development
143
+
144
+ ```
145
+ python -m venv .venv
146
+ .venv/Scripts/pip install -e .[dev]
147
+ .venv/Scripts/python -m pytest
148
+ ```
149
+
150
+ Contributions follow
151
+ [GUIDELINES.md](https://github.com/nicoseijas/numba-utils/blob/main/GUIDELINES.md)
152
+ — benchmarks are mandatory, honesty is policy.
@@ -0,0 +1,137 @@
1
+ """numba-utils: high-performance building blocks for Numba."""
2
+
3
+ from numba_utils import diagnostics, testing
4
+ from numba_utils._config import config, configure
5
+ from numba_utils.algorithms import (
6
+ argmax2,
7
+ counting_sort,
8
+ fast_argpartition,
9
+ insertion_sort,
10
+ nth_element,
11
+ partial_sort,
12
+ quickselect,
13
+ radix_sort,
14
+ topk,
15
+ )
16
+ from numba_utils.arrays import (
17
+ bincount,
18
+ binary_search,
19
+ cumulative_sum,
20
+ fast_clip,
21
+ histogram,
22
+ lower_bound,
23
+ normalize,
24
+ rolling_mean,
25
+ rolling_sum,
26
+ unique_sorted,
27
+ upper_bound,
28
+ )
29
+ from numba_utils.collections import (
30
+ BitSet,
31
+ FixedQueue,
32
+ ObjectPool,
33
+ PriorityQueue,
34
+ RingBuffer,
35
+ SparseSet,
36
+ Stack,
37
+ counter,
38
+ typed_defaultdict,
39
+ )
40
+ from numba_utils.decorators import (
41
+ boundscheck,
42
+ cached_njit,
43
+ njit_fast,
44
+ njit_parallel,
45
+ )
46
+ from numba_utils.parallel import (
47
+ parallel_histogram,
48
+ parallel_prefix_sum,
49
+ parallel_reduce,
50
+ parallel_sum,
51
+ parallel_topk,
52
+ )
53
+ from numba_utils.profiling import (
54
+ BenchmarkResult,
55
+ ComparisonResult,
56
+ TimingStats,
57
+ benchmark,
58
+ compare,
59
+ compile_stats,
60
+ compile_time,
61
+ warmup,
62
+ )
63
+ from numba_utils.random import (
64
+ alias_draw,
65
+ alias_sample,
66
+ alias_setup,
67
+ choice,
68
+ permutation,
69
+ reservoir_sampling,
70
+ seed,
71
+ shuffle,
72
+ weighted_sampling,
73
+ )
74
+
75
+ __version__ = "0.1.0"
76
+
77
+ __all__ = [
78
+ "BenchmarkResult",
79
+ "BitSet",
80
+ "ComparisonResult",
81
+ "FixedQueue",
82
+ "ObjectPool",
83
+ "PriorityQueue",
84
+ "RingBuffer",
85
+ "SparseSet",
86
+ "Stack",
87
+ "TimingStats",
88
+ "alias_draw",
89
+ "alias_sample",
90
+ "alias_setup",
91
+ "argmax2",
92
+ "benchmark",
93
+ "bincount",
94
+ "binary_search",
95
+ "boundscheck",
96
+ "cached_njit",
97
+ "choice",
98
+ "compare",
99
+ "compile_stats",
100
+ "compile_time",
101
+ "config",
102
+ "configure",
103
+ "counter",
104
+ "counting_sort",
105
+ "cumulative_sum",
106
+ "diagnostics",
107
+ "fast_argpartition",
108
+ "fast_clip",
109
+ "histogram",
110
+ "insertion_sort",
111
+ "lower_bound",
112
+ "njit_fast",
113
+ "njit_parallel",
114
+ "normalize",
115
+ "nth_element",
116
+ "parallel_histogram",
117
+ "parallel_prefix_sum",
118
+ "parallel_reduce",
119
+ "parallel_sum",
120
+ "parallel_topk",
121
+ "partial_sort",
122
+ "permutation",
123
+ "quickselect",
124
+ "radix_sort",
125
+ "reservoir_sampling",
126
+ "rolling_mean",
127
+ "rolling_sum",
128
+ "seed",
129
+ "shuffle",
130
+ "testing",
131
+ "topk",
132
+ "typed_defaultdict",
133
+ "unique_sorted",
134
+ "upper_bound",
135
+ "warmup",
136
+ "weighted_sampling",
137
+ ]
@@ -0,0 +1,92 @@
1
+ """Global configuration: code-level overrides with environment fallbacks.
2
+
3
+ Two levels, resolved per option at decoration time:
4
+
5
+ 1. Code: ``configure(cache=False)`` or ``config.cache = False``.
6
+ 2. Environment: ``NUMBA_UTILS_CACHE=0`` (checked only when the code level
7
+ is unset).
8
+
9
+ A set option (``True``/``False``) is a GLOBAL override: it wins over
10
+ decorator defaults and per-call keyword arguments alike. That is the
11
+ point — overrides exist for environment-level policy, like disabling the
12
+ on-disk cache on machines where it is unsafe (see docs/numba-cache.md).
13
+ ``None`` means "no override": decorator defaults and per-call arguments
14
+ apply unchanged.
15
+
16
+ Overrides affect only functions decorated AFTER the change — configure
17
+ before defining your jitted functions.
18
+ """
19
+
20
+ from __future__ import annotations
21
+
22
+ import os
23
+
24
+ _TRUTHY = frozenset({"1", "true", "yes", "on"})
25
+ _FALSY = frozenset({"0", "false", "no", "off"})
26
+
27
+ OPTION_ENV_VARS = {
28
+ "cache": "NUMBA_UTILS_CACHE",
29
+ "fastmath": "NUMBA_UTILS_FASTMATH",
30
+ "parallel": "NUMBA_UTILS_PARALLEL",
31
+ "nogil": "NUMBA_UTILS_NOGIL",
32
+ }
33
+
34
+
35
+ class GlobalConfig:
36
+ """Tri-state global overrides for every numba-utils decorator.
37
+
38
+ Attributes ``cache``, ``fastmath``, ``parallel``, ``nogil`` are each
39
+ ``None`` (no override), ``True`` or ``False`` (forced globally).
40
+ """
41
+
42
+ __slots__ = ("cache", "fastmath", "parallel", "nogil")
43
+
44
+ def __init__(self) -> None:
45
+ self.reset()
46
+
47
+ def reset(self) -> None:
48
+ """Clear all code-level overrides. Environment fallbacks remain."""
49
+ for name in OPTION_ENV_VARS:
50
+ setattr(self, name, None)
51
+
52
+ def resolve(self, name: str) -> bool | None:
53
+ """Effective override for ``name``: code level, else environment,
54
+ else ``None``. Unrecognized environment values count as unset."""
55
+ value = getattr(self, name)
56
+ if value is not None:
57
+ return bool(value)
58
+ raw = os.environ.get(OPTION_ENV_VARS[name], "").strip().lower()
59
+ if raw in _TRUTHY:
60
+ return True
61
+ if raw in _FALSY:
62
+ return False
63
+ return None
64
+
65
+
66
+ config = GlobalConfig()
67
+
68
+
69
+ def configure(**options: bool | None) -> None:
70
+ """Set global decorator overrides in code.
71
+
72
+ ::
73
+
74
+ import numba_utils as nu
75
+ nu.configure(cache=False, fastmath=True)
76
+
77
+ Valid options: ``cache``, ``fastmath``, ``parallel``, ``nogil``.
78
+ Pass ``None`` to clear a single override; ``config.reset()`` clears
79
+ all. Raises ``ValueError`` on unknown names (fail fast, no typos
80
+ silently ignored).
81
+ """
82
+ for name, value in options.items():
83
+ if name not in OPTION_ENV_VARS:
84
+ valid = ", ".join(sorted(OPTION_ENV_VARS))
85
+ raise ValueError(
86
+ f"configure: unknown option {name!r}; valid options: {valid}"
87
+ )
88
+ if value is not None and not isinstance(value, bool):
89
+ raise ValueError(
90
+ f"configure: option {name!r} must be True, False or None"
91
+ )
92
+ setattr(config, name, value)
@@ -0,0 +1,26 @@
1
+ """Selection and sorting algorithms specialized for Numba."""
2
+
3
+ from numba_utils.algorithms._select import (
4
+ fast_argpartition,
5
+ nth_element,
6
+ quickselect,
7
+ )
8
+ from numba_utils.algorithms._sort import (
9
+ counting_sort,
10
+ insertion_sort,
11
+ partial_sort,
12
+ radix_sort,
13
+ )
14
+ from numba_utils.algorithms._topk import argmax2, topk
15
+
16
+ __all__ = [
17
+ "argmax2",
18
+ "counting_sort",
19
+ "fast_argpartition",
20
+ "insertion_sort",
21
+ "nth_element",
22
+ "partial_sort",
23
+ "quickselect",
24
+ "radix_sort",
25
+ "topk",
26
+ ]