mapFolding 0.3.7__py3-none-any.whl → 0.3.9__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 (47) hide show
  1. mapFolding/__init__.py +38 -0
  2. mapFolding/basecamp.py +55 -0
  3. mapFolding/beDRY.py +364 -0
  4. mapFolding/oeis.py +329 -0
  5. mapFolding/someAssemblyRequired/makeJob.py +62 -0
  6. mapFolding/someAssemblyRequired/synthesizeModuleJAX.py +29 -0
  7. someAssemblyRequired/synthesizeModuleJob.py → mapFolding/someAssemblyRequired/synthesizeModuleJobNumba.py +81 -27
  8. mapFolding/someAssemblyRequired/synthesizeModulesNumba.py +506 -0
  9. mapFolding/syntheticModules/__init__.py +3 -0
  10. syntheticModules/Initialize.py → mapFolding/syntheticModules/numba_countInitialize.py +5 -4
  11. syntheticModules/Parallel.py → mapFolding/syntheticModules/numba_countParallel.py +10 -5
  12. syntheticModules/Sequential.py → mapFolding/syntheticModules/numba_countSequential.py +5 -4
  13. mapFolding/syntheticModules/numba_doTheNeedful.py +33 -0
  14. mapFolding/theDao.py +214 -0
  15. mapFolding/theSSOT.py +269 -0
  16. mapFolding-0.3.9.dist-info/LICENSE +407 -0
  17. {mapFolding-0.3.7.dist-info → mapFolding-0.3.9.dist-info}/METADATA +9 -5
  18. mapFolding-0.3.9.dist-info/RECORD +40 -0
  19. mapFolding-0.3.9.dist-info/top_level.txt +2 -0
  20. tests/__init__.py +1 -0
  21. tests/conftest.py +224 -0
  22. tests/conftest_tmpRegistry.py +62 -0
  23. tests/conftest_uniformTests.py +53 -0
  24. tests/test_oeis.py +200 -0
  25. tests/test_other.py +258 -0
  26. tests/test_tasks.py +44 -0
  27. tests/test_types.py +5 -0
  28. benchmarks/benchmarking.py +0 -67
  29. citations/updateCitation.py +0 -238
  30. mapFolding-0.3.7.dist-info/RECORD +0 -25
  31. mapFolding-0.3.7.dist-info/top_level.txt +0 -5
  32. someAssemblyRequired/makeJob.py +0 -34
  33. someAssemblyRequired/synthesizeModules.py +0 -216
  34. syntheticModules/__init__.py +0 -4
  35. {reference → mapFolding/reference}/flattened.py +0 -0
  36. {reference → mapFolding/reference}/hunterNumba.py +0 -0
  37. {reference → mapFolding/reference}/irvineJavaPort.py +0 -0
  38. {reference → mapFolding/reference}/jax.py +0 -0
  39. {reference → mapFolding/reference}/lunnan.py +0 -0
  40. {reference → mapFolding/reference}/lunnanNumpy.py +0 -0
  41. {reference → mapFolding/reference}/lunnanWhile.py +0 -0
  42. {reference → mapFolding/reference}/rotatedEntryPoint.py +0 -0
  43. {reference → mapFolding/reference}/total_countPlus1vsPlusN.py +0 -0
  44. {someAssemblyRequired → mapFolding/someAssemblyRequired}/__init__.py +0 -0
  45. {someAssemblyRequired → mapFolding/someAssemblyRequired}/getLLVMforNoReason.py +0 -0
  46. {mapFolding-0.3.7.dist-info → mapFolding-0.3.9.dist-info}/WHEEL +0 -0
  47. {mapFolding-0.3.7.dist-info → mapFolding-0.3.9.dist-info}/entry_points.txt +0 -0
mapFolding/theDao.py ADDED
@@ -0,0 +1,214 @@
1
+ from mapFolding import indexMy, indexTrack
2
+ from numpy import integer
3
+ from numpy.typing import NDArray
4
+ from typing import Any, Tuple
5
+ import numba
6
+ import numpy
7
+
8
+ def activeGapIncrement(my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]) -> None:
9
+ my[indexMy.gap1ndex.value] += 1
10
+
11
+ def activeLeafGreaterThan0Condition(my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]) -> Any:
12
+ return my[indexMy.leaf1ndex.value]
13
+
14
+ def activeLeafGreaterThanLeavesTotalCondition(foldGroups: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]], my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]) -> Any:
15
+ return my[indexMy.leaf1ndex.value] > foldGroups[-1]
16
+
17
+ def activeLeafIsTheFirstLeafCondition(my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]) -> Any:
18
+ return my[indexMy.leaf1ndex.value] <= 1
19
+
20
+ def allDimensionsAreUnconstrained(my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]) -> Any:
21
+ return not my[indexMy.dimensionsUnconstrained.value]
22
+
23
+ def backtrack(my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]], track: numpy.ndarray[Tuple[int, int], numpy.dtype[integer[Any]]]) -> None:
24
+ my[indexMy.leaf1ndex.value] -= 1
25
+ track[indexTrack.leafBelow.value, track[indexTrack.leafAbove.value, my[indexMy.leaf1ndex.value]]] = track[indexTrack.leafBelow.value, my[indexMy.leaf1ndex.value]]
26
+ track[indexTrack.leafAbove.value, track[indexTrack.leafBelow.value, my[indexMy.leaf1ndex.value]]] = track[indexTrack.leafAbove.value, my[indexMy.leaf1ndex.value]]
27
+
28
+ def backtrackCondition(my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]], track: numpy.ndarray[Tuple[int, int], numpy.dtype[integer[Any]]]) -> Any:
29
+ return my[indexMy.leaf1ndex.value] and my[indexMy.gap1ndex.value] == track[indexTrack.gapRangeStart.value, my[indexMy.leaf1ndex.value] - 1]
30
+
31
+ def gap1ndexCeilingIncrement(my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]) -> None:
32
+ my[indexMy.gap1ndexCeiling.value] += 1
33
+
34
+ def countGaps(gapsWhere: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]], my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]], track: numpy.ndarray[Tuple[int, int], numpy.dtype[integer[Any]]]) -> None:
35
+ gapsWhere[my[indexMy.gap1ndexCeiling.value]] = my[indexMy.leafConnectee.value]
36
+ if track[indexTrack.countDimensionsGapped.value, my[indexMy.leafConnectee.value]] == 0:
37
+ gap1ndexCeilingIncrement(my=my)
38
+ track[indexTrack.countDimensionsGapped.value, my[indexMy.leafConnectee.value]] += 1
39
+
40
+ def dimension1ndexIncrement(my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]) -> None:
41
+ my[indexMy.indexDimension.value] += 1
42
+
43
+ def dimensionsUnconstrainedCondition(connectionGraph: numpy.ndarray[Tuple[int, int, int], numpy.dtype[integer[Any]]], my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]) -> Any:
44
+ return connectionGraph[my[indexMy.indexDimension.value], my[indexMy.leaf1ndex.value], my[indexMy.leaf1ndex.value]] == my[indexMy.leaf1ndex.value]
45
+
46
+ def dimensionsUnconstrainedDecrement(my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]) -> None:
47
+ my[indexMy.dimensionsUnconstrained.value] -= 1
48
+
49
+ def filterCommonGaps(gapsWhere: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]], my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]], track: numpy.ndarray[Tuple[int, int], numpy.dtype[integer[Any]]]) -> None:
50
+ gapsWhere[my[indexMy.gap1ndex.value]] = gapsWhere[my[indexMy.indexMiniGap.value]]
51
+ if track[indexTrack.countDimensionsGapped.value, gapsWhere[my[indexMy.indexMiniGap.value]]] == my[indexMy.dimensionsUnconstrained.value]:
52
+ activeGapIncrement(my=my)
53
+ track[indexTrack.countDimensionsGapped.value, gapsWhere[my[indexMy.indexMiniGap.value]]] = 0
54
+
55
+ def findGapsInitializeVariables(my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]], track: numpy.ndarray[Tuple[int, int], numpy.dtype[integer[Any]]]) -> None:
56
+ my[indexMy.dimensionsUnconstrained.value] = my[indexMy.dimensionsTotal.value]
57
+ my[indexMy.gap1ndexCeiling.value] = track[indexTrack.gapRangeStart.value, my[indexMy.leaf1ndex.value] - 1]
58
+ my[indexMy.indexDimension.value] = 0
59
+
60
+ def indexMiniGapIncrement(my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]) -> None:
61
+ my[indexMy.indexMiniGap.value] += 1
62
+
63
+ def indexMiniGapInitialization(my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]) -> None:
64
+ my[indexMy.indexMiniGap.value] = my[indexMy.gap1ndex.value]
65
+
66
+ def insertUnconstrainedLeaf(gapsWhere: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]], my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]) -> None:
67
+ my[indexMy.indexLeaf.value] = 0
68
+ while my[indexMy.indexLeaf.value] < my[indexMy.leaf1ndex.value]:
69
+ gapsWhere[my[indexMy.gap1ndexCeiling.value]] = my[indexMy.indexLeaf.value]
70
+ my[indexMy.gap1ndexCeiling.value] += 1
71
+ my[indexMy.indexLeaf.value] += 1
72
+
73
+ def leafBelowSentinelIs1Condition(track: numpy.ndarray[Tuple[int, int], numpy.dtype[integer[Any]]]) -> Any:
74
+ return track[indexTrack.leafBelow.value, 0] == 1
75
+
76
+ def leafConnecteeInitialization(connectionGraph: numpy.ndarray[Tuple[int, int, int], numpy.dtype[integer[Any]]], my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]) -> None:
77
+ my[indexMy.leafConnectee.value] = connectionGraph[my[indexMy.indexDimension.value], my[indexMy.leaf1ndex.value], my[indexMy.leaf1ndex.value]]
78
+
79
+ def leafConnecteeUpdate(connectionGraph: numpy.ndarray[Tuple[int, int, int], numpy.dtype[integer[Any]]], my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]], track: numpy.ndarray[Tuple[int, int], numpy.dtype[integer[Any]]]) -> None:
80
+ my[indexMy.leafConnectee.value] = connectionGraph[my[indexMy.indexDimension.value], my[indexMy.leaf1ndex.value], track[indexTrack.leafBelow.value, my[indexMy.leafConnectee.value]]]
81
+
82
+ def loopingLeavesConnectedToActiveLeaf(my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]) -> Any:
83
+ return my[indexMy.leafConnectee.value] != my[indexMy.leaf1ndex.value]
84
+
85
+ def loopingTheDimensions(my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]) -> Any:
86
+ return my[indexMy.indexDimension.value] < my[indexMy.dimensionsTotal.value]
87
+
88
+ def loopingToActiveGapCeiling(my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]) -> Any:
89
+ return my[indexMy.indexMiniGap.value] < my[indexMy.gap1ndexCeiling.value]
90
+
91
+ def placeLeaf(gapsWhere: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]], my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]], track: numpy.ndarray[Tuple[int, int], numpy.dtype[integer[Any]]]) -> None:
92
+ my[indexMy.gap1ndex.value] -= 1
93
+ track[indexTrack.leafAbove.value, my[indexMy.leaf1ndex.value]] = gapsWhere[my[indexMy.gap1ndex.value]]
94
+ track[indexTrack.leafBelow.value, my[indexMy.leaf1ndex.value]] = track[indexTrack.leafBelow.value, track[indexTrack.leafAbove.value, my[indexMy.leaf1ndex.value]]]
95
+ track[indexTrack.leafBelow.value, track[indexTrack.leafAbove.value, my[indexMy.leaf1ndex.value]]] = my[indexMy.leaf1ndex.value]
96
+ track[indexTrack.leafAbove.value, track[indexTrack.leafBelow.value, my[indexMy.leaf1ndex.value]]] = my[indexMy.leaf1ndex.value]
97
+ track[indexTrack.gapRangeStart.value, my[indexMy.leaf1ndex.value]] = my[indexMy.gap1ndex.value]
98
+ my[indexMy.leaf1ndex.value] += 1
99
+
100
+ def placeLeafCondition(my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]) -> Any:
101
+ return my[indexMy.leaf1ndex.value]
102
+
103
+ def thereAreComputationDivisionsYouMightSkip(my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]) -> Any:
104
+ return my[indexMy.leaf1ndex.value] != my[indexMy.taskDivisions.value] or my[indexMy.leafConnectee.value] % my[indexMy.taskDivisions.value] == my[indexMy.taskIndex.value]
105
+
106
+ def countInitialize(connectionGraph: numpy.ndarray[Tuple[int, int, int], numpy.dtype[integer[Any]]]
107
+ , gapsWhere: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]
108
+ , my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]
109
+ , track: numpy.ndarray[Tuple[int, int], numpy.dtype[integer[Any]]]) -> None:
110
+ while activeLeafGreaterThan0Condition(my=my):
111
+ if activeLeafIsTheFirstLeafCondition(my=my) or leafBelowSentinelIs1Condition(track=track):
112
+ findGapsInitializeVariables(my=my, track=track)
113
+ while loopingTheDimensions(my=my):
114
+ if dimensionsUnconstrainedCondition(connectionGraph=connectionGraph, my=my):
115
+ dimensionsUnconstrainedDecrement(my=my)
116
+ else:
117
+ leafConnecteeInitialization(connectionGraph=connectionGraph, my=my)
118
+ while loopingLeavesConnectedToActiveLeaf(my=my):
119
+ countGaps(gapsWhere=gapsWhere, my=my, track=track)
120
+ leafConnecteeUpdate(connectionGraph=connectionGraph, my=my, track=track)
121
+ dimension1ndexIncrement(my=my)
122
+ if allDimensionsAreUnconstrained(my=my):
123
+ insertUnconstrainedLeaf(gapsWhere=gapsWhere, my=my)
124
+ indexMiniGapInitialization(my=my)
125
+ while loopingToActiveGapCeiling(my=my):
126
+ filterCommonGaps(gapsWhere=gapsWhere, my=my, track=track)
127
+ indexMiniGapIncrement(my=my)
128
+ if placeLeafCondition(my=my):
129
+ placeLeaf(gapsWhere=gapsWhere, my=my, track=track)
130
+ if my[indexMy.gap1ndex.value] > 0:
131
+ return
132
+
133
+ def countParallel(connectionGraph: numpy.ndarray[Tuple[int, int, int], numpy.dtype[integer[Any]]]
134
+ , foldGroups: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]
135
+ , gapsWhere: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]
136
+ , my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]
137
+ , track: numpy.ndarray[Tuple[int, int], numpy.dtype[integer[Any]]]) -> None:
138
+ gapsWherePARALLEL = gapsWhere.copy()
139
+ myPARALLEL = my.copy()
140
+ trackPARALLEL = track.copy()
141
+ taskDivisionsPrange = myPARALLEL[indexMy.taskDivisions.value]
142
+ for indexSherpa in numba.prange(taskDivisionsPrange):
143
+ groupsOfFolds: int = 0
144
+ gapsWhere = gapsWherePARALLEL.copy()
145
+ my = myPARALLEL.copy()
146
+ my[indexMy.taskIndex.value] = indexSherpa
147
+ track = trackPARALLEL.copy()
148
+ while activeLeafGreaterThan0Condition(my=my):
149
+ if activeLeafIsTheFirstLeafCondition(my=my) or leafBelowSentinelIs1Condition(track=track):
150
+ if activeLeafGreaterThanLeavesTotalCondition(foldGroups=foldGroups, my=my):
151
+ groupsOfFolds += 1
152
+ else:
153
+ findGapsInitializeVariables(my=my, track=track)
154
+ while loopingTheDimensions(my=my):
155
+ if dimensionsUnconstrainedCondition(connectionGraph=connectionGraph, my=my):
156
+ dimensionsUnconstrainedDecrement(my=my)
157
+ else:
158
+ leafConnecteeInitialization(connectionGraph=connectionGraph, my=my)
159
+ while loopingLeavesConnectedToActiveLeaf(my=my):
160
+ if thereAreComputationDivisionsYouMightSkip(my=my):
161
+ countGaps(gapsWhere=gapsWhere, my=my, track=track)
162
+ leafConnecteeUpdate(connectionGraph=connectionGraph, my=my, track=track)
163
+ dimension1ndexIncrement(my=my)
164
+ indexMiniGapInitialization(my=my)
165
+ while loopingToActiveGapCeiling(my=my):
166
+ filterCommonGaps(gapsWhere=gapsWhere, my=my, track=track)
167
+ indexMiniGapIncrement(my=my)
168
+ while backtrackCondition(my=my, track=track):
169
+ backtrack(my=my, track=track)
170
+ if placeLeafCondition(my=my):
171
+ placeLeaf(gapsWhere=gapsWhere, my=my, track=track)
172
+ foldGroups[my[indexMy.taskIndex.value]] = groupsOfFolds
173
+
174
+ def countSequential(connectionGraph: numpy.ndarray[Tuple[int, int, int], numpy.dtype[integer[Any]]], foldGroups: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]], gapsWhere: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]], my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]], track: numpy.ndarray[Tuple[int, int], numpy.dtype[integer[Any]]]) -> None:
175
+ groupsOfFolds: int = 0
176
+ doFindGaps = True
177
+ while activeLeafGreaterThan0Condition(my=my):
178
+ if ((doFindGaps := activeLeafIsTheFirstLeafCondition(my=my) or leafBelowSentinelIs1Condition(track=track))
179
+ and activeLeafGreaterThanLeavesTotalCondition(foldGroups=foldGroups, my=my)):
180
+ groupsOfFolds += 1
181
+ elif doFindGaps:
182
+ findGapsInitializeVariables(my=my, track=track)
183
+ while loopingTheDimensions(my=my):
184
+ if dimensionsUnconstrainedCondition(connectionGraph=connectionGraph, my=my):
185
+ dimensionsUnconstrainedDecrement(my=my)
186
+ else:
187
+ leafConnecteeInitialization(connectionGraph=connectionGraph, my=my)
188
+ while loopingLeavesConnectedToActiveLeaf(my=my):
189
+ countGaps(gapsWhere=gapsWhere, my=my, track=track)
190
+ leafConnecteeUpdate(connectionGraph=connectionGraph, my=my, track=track)
191
+ dimension1ndexIncrement(my=my)
192
+ indexMiniGapInitialization(my=my)
193
+ while loopingToActiveGapCeiling(my=my):
194
+ filterCommonGaps(gapsWhere=gapsWhere, my=my, track=track)
195
+ indexMiniGapIncrement(my=my)
196
+ while backtrackCondition(my=my, track=track):
197
+ backtrack(my=my, track=track)
198
+ if placeLeafCondition(my=my):
199
+ placeLeaf(gapsWhere=gapsWhere, my=my, track=track)
200
+ foldGroups[my[indexMy.taskIndex.value]] = groupsOfFolds
201
+
202
+ def doTheNeedful(connectionGraph: numpy.ndarray[Tuple[int, int, int], numpy.dtype[integer[Any]]]
203
+ , foldGroups: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]
204
+ , gapsWhere: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]
205
+ , mapShape: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]
206
+ , my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]
207
+ , track: numpy.ndarray[Tuple[int, int], numpy.dtype[integer[Any]]]
208
+ ) -> None:
209
+ countInitialize(connectionGraph, gapsWhere, my, track)
210
+
211
+ if my[indexMy.taskDivisions.value] > 0:
212
+ countParallel(connectionGraph, foldGroups, gapsWhere, my, track)
213
+ else:
214
+ countSequential(connectionGraph, foldGroups, gapsWhere, my, track)
mapFolding/theSSOT.py ADDED
@@ -0,0 +1,269 @@
1
+ from collections import defaultdict
2
+ from numpy import integer
3
+ from types import ModuleType
4
+ from typing import Any, Callable, Dict, Final, Optional, Tuple, Type, TypedDict, cast
5
+ import enum
6
+ import numba
7
+ import numpy
8
+ import numpy.typing
9
+ import pathlib
10
+ import sys
11
+
12
+ """I have hobbled together:
13
+ TypedDict, Enum, defaultdict, and lookup dictionaries to make DIY immutability and delayed realization/instantiation.
14
+ Nevertheless, I am both confident that all of these processes will be replaced and completely ignorant of what will replace them."""
15
+
16
+ """Technical concepts I am likely using and likely want to use more effectively:
17
+ - Configuration Registry
18
+ - Write-Once, Read-Many (WORM) / Immutable Initialization
19
+ - Lazy Initialization
20
+ - Separation of Concerns: in the sense that configuration is separated from business logic
21
+
22
+ Furthermore, I want to more clearly divorce the concept of a single _source_ of (a) truth from
23
+ the _authority_ of that truth. The analogy to a registry of ownership is still apt: the registry
24
+ is, at most, a single (or centralized) source of truth, but it is merely the place to register/record
25
+ the truth determined by some other authority.
26
+
27
+ And, I almost certainly want to change the semiotics from "authority" (of truth) to "power" (to create a truth).
28
+ Here, "power" is a direct analogy to https://hunterthinks.com/opinion/a-hohfeldian-primer.
29
+ """
30
+
31
+ myPackageNameIs = "mapFolding"
32
+
33
+ moduleOfSyntheticModules = "syntheticModules"
34
+
35
+ def getPathPackage() -> pathlib.Path:
36
+ import importlib, inspect
37
+ pathPackage = pathlib.Path(inspect.getfile(importlib.import_module(myPackageNameIs)))
38
+ if pathPackage.is_file():
39
+ pathPackage = pathPackage.parent
40
+ return pathPackage
41
+
42
+ def getPathJobDEFAULT() -> pathlib.Path:
43
+ if 'google.colab' in sys.modules:
44
+ pathJobDEFAULT = pathlib.Path("/content/drive/MyDrive") / "jobs"
45
+ else:
46
+ pathJobDEFAULT = getPathPackage() / "jobs"
47
+ return pathJobDEFAULT
48
+
49
+ def getPathSyntheticModules() -> pathlib.Path:
50
+ pathSyntheticModules = getPathPackage() / moduleOfSyntheticModules
51
+ return pathSyntheticModules
52
+
53
+ def getAlgorithmSource() -> ModuleType:
54
+ from mapFolding import theDao
55
+ return theDao
56
+
57
+ def getAlgorithmCallable() -> Callable[..., None]:
58
+ algorithmSource = getAlgorithmSource()
59
+ return cast(Callable[..., None], algorithmSource.doTheNeedful)
60
+
61
+ def getDispatcherCallable() -> Callable[..., None]:
62
+ from mapFolding.syntheticModules import numba_doTheNeedful
63
+ return cast(Callable[..., None], numba_doTheNeedful.doTheNeedful)
64
+
65
+ # NOTE I want this _concept_ to be well implemented and usable everywhere: Python, Numba, Jax, CUDA, idc
66
+ class computationState(TypedDict):
67
+ connectionGraph: numpy.ndarray[Tuple[int, int, int], numpy.dtype[integer[Any]]]
68
+ foldGroups: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]
69
+ gapsWhere: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]
70
+ mapShape: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]
71
+ my: numpy.ndarray[Tuple[int], numpy.dtype[integer[Any]]]
72
+ track: numpy.ndarray[Tuple[int, int], numpy.dtype[integer[Any]]]
73
+
74
+ @enum.verify(enum.CONTINUOUS, enum.UNIQUE) if sys.version_info >= (3, 11) else lambda x: x
75
+ class EnumIndices(enum.IntEnum):
76
+ """Base class for index enums."""
77
+ @staticmethod
78
+ def _generate_next_value_(name: str, start: int, count: int, last_values: list[Any]) -> int:
79
+ """0-indexed."""
80
+ return count
81
+
82
+ def __index__(self) -> int:
83
+ """Adapt enum to the ultra-rare event of indexing a NumPy 'ndarray', which is not the
84
+ same as `array.array`. See NumPy.org; I think it will be very popular someday."""
85
+ return self.value
86
+
87
+ class indexMy(EnumIndices):
88
+ """Indices for scalar values."""
89
+ dimensionsTotal = enum.auto()
90
+ dimensionsUnconstrained = enum.auto()
91
+ gap1ndex = enum.auto()
92
+ gap1ndexCeiling = enum.auto()
93
+ indexDimension = enum.auto()
94
+ indexLeaf = enum.auto()
95
+ indexMiniGap = enum.auto()
96
+ leaf1ndex = enum.auto()
97
+ leafConnectee = enum.auto()
98
+ taskDivisions = enum.auto()
99
+ taskIndex = enum.auto()
100
+
101
+ class indexTrack(EnumIndices):
102
+ """Indices for state tracking array."""
103
+ leafAbove = enum.auto()
104
+ leafBelow = enum.auto()
105
+ countDimensionsGapped = enum.auto()
106
+ gapRangeStart = enum.auto()
107
+
108
+ class ParametersNumba(TypedDict):
109
+ _nrt: bool
110
+ boundscheck: bool
111
+ cache: bool
112
+ error_model: str
113
+ fastmath: bool
114
+ forceinline: bool
115
+ inline: str
116
+ looplift: bool
117
+ no_cfunc_wrapper: bool
118
+ no_cpython_wrapper: bool
119
+ nopython: bool
120
+ parallel: bool
121
+
122
+ parametersNumbaDEFAULT: Final[ParametersNumba] = {
123
+ '_nrt': True,
124
+ 'boundscheck': False,
125
+ 'cache': True,
126
+ 'error_model': 'numpy',
127
+ 'fastmath': True,
128
+ 'forceinline': False,
129
+ 'inline': 'never',
130
+ 'looplift': False,
131
+ 'no_cfunc_wrapper': True,
132
+ 'no_cpython_wrapper': True,
133
+ 'nopython': True,
134
+ 'parallel': False,
135
+ }
136
+
137
+ "delay realization/instantiation until a concrete value is desired"
138
+ "moment of truth: when the value is needed, not when the value is defined"
139
+
140
+ """What is a (not too complicated, integer) datatype?
141
+ - ecosystem/module
142
+ - must apathy|value|list of values
143
+ - mustn't apathy|value|list of values
144
+ - bit width
145
+ - bits maximum apathy|value
146
+ - bits minimum apathy|value
147
+ - magnitude maximum apathy|value
148
+ - ?magnitude minimum apathy|value
149
+ - signedness apathy|non-negative|non-positive|both
150
+ """
151
+
152
+ _datatypeDefault: Final[Dict[str, str]] = {
153
+ 'elephino': 'uint8',
154
+ 'foldsTotal': 'int64',
155
+ 'leavesTotal': 'uint8',
156
+ }
157
+ _datatypeModule = ''
158
+ _datatypeModuleDEFAULT: Final[str] = 'numpy'
159
+
160
+ _datatype: Dict[str, str] = defaultdict(str)
161
+
162
+ def reportDatatypeLimit(identifier: str, datatype: str, sourGrapes: Optional[bool] = False) -> str:
163
+ global _datatype
164
+ if not _datatype[identifier]:
165
+ _datatype[identifier] = datatype
166
+ elif _datatype[identifier] == datatype:
167
+ pass
168
+ elif sourGrapes:
169
+ raise Exception(f"Datatype is '{_datatype[identifier]}' not '{datatype}', so you can take your ball and go home.")
170
+ return _datatype[identifier]
171
+
172
+ def setDatatypeModule(datatypeModule: str, sourGrapes: Optional[bool] = False) -> str:
173
+ global _datatypeModule
174
+ if not _datatypeModule:
175
+ _datatypeModule = datatypeModule
176
+ elif _datatypeModule == datatypeModule:
177
+ pass
178
+ elif sourGrapes:
179
+ raise Exception(f"Datatype module is '{_datatypeModule}' not '{datatypeModule}', so you can take your ball and go home.")
180
+ return _datatypeModule
181
+
182
+ def setDatatypeElephino(datatype: str, sourGrapes: Optional[bool] = False) -> str:
183
+ return reportDatatypeLimit('elephino', datatype, sourGrapes)
184
+
185
+ def setDatatypeFoldsTotal(datatype: str, sourGrapes: Optional[bool] = False) -> str:
186
+ return reportDatatypeLimit('foldsTotal', datatype, sourGrapes)
187
+
188
+ def setDatatypeLeavesTotal(datatype: str, sourGrapes: Optional[bool] = False) -> str:
189
+ return reportDatatypeLimit('leavesTotal', datatype, sourGrapes)
190
+
191
+ def _get_datatype(identifier: str) -> str:
192
+ global _datatype
193
+ if not _datatype[identifier]:
194
+ if identifier in indexMy._member_names_:
195
+ _datatype[identifier] = _datatypeDefault.get(identifier) or _get_datatype('elephino')
196
+ elif identifier in indexTrack._member_names_:
197
+ _datatype[identifier] = _datatypeDefault.get(identifier) or _get_datatype('elephino')
198
+ else:
199
+ _datatype[identifier] = _datatypeDefault.get(identifier) or _get_datatype('foldsTotal')
200
+ return _datatype[identifier]
201
+
202
+ def _getDatatypeModule() -> str:
203
+ global _datatypeModule
204
+ if not _datatypeModule:
205
+ _datatypeModule = _datatypeModuleDEFAULT
206
+ return _datatypeModule
207
+
208
+ def setInStone(identifier: str) -> Type[Any]:
209
+ datatypeModule = _getDatatypeModule()
210
+ datatypeStr = _get_datatype(identifier)
211
+ return cast(Type[Any], getattr(eval(datatypeModule), datatypeStr))
212
+
213
+ def hackSSOTdtype(identifier: str) -> Type[Any]:
214
+ _hackSSOTdtype={
215
+ 'connectionGraph': 'dtypeLeavesTotal',
216
+ 'dtypeElephino': 'dtypeElephino',
217
+ 'dtypeFoldsTotal': 'dtypeFoldsTotal',
218
+ 'dtypeLeavesTotal': 'dtypeLeavesTotal',
219
+ 'foldGroups': 'dtypeFoldsTotal',
220
+ 'gapsWhere': 'dtypeLeavesTotal',
221
+ 'mapShape': 'dtypeLeavesTotal',
222
+ 'my': 'dtypeElephino',
223
+ 'track': 'dtypeElephino',
224
+ }
225
+ RubeGoldBerg = _hackSSOTdtype[identifier]
226
+ if RubeGoldBerg == 'dtypeElephino':
227
+ return setInStone('elephino')
228
+ elif RubeGoldBerg == 'dtypeFoldsTotal':
229
+ return setInStone('foldsTotal')
230
+ elif RubeGoldBerg == 'dtypeLeavesTotal':
231
+ return setInStone('leavesTotal')
232
+ raise Exception("Dude, you forgot to set a value in `hackSSOTdtype`.")
233
+
234
+ def hackSSOTdatatype(identifier: str) -> str:
235
+ _hackSSOTdatatype={
236
+ 'connectionGraph': 'datatypeLeavesTotal',
237
+ 'countDimensionsGapped': 'datatypeLeavesTotal',
238
+ 'datatypeElephino': 'datatypeElephino',
239
+ 'datatypeFoldsTotal': 'datatypeFoldsTotal',
240
+ 'datatypeLeavesTotal': 'datatypeLeavesTotal',
241
+ 'dimensionsTotal': 'datatypeLeavesTotal',
242
+ 'dimensionsUnconstrained': 'datatypeLeavesTotal',
243
+ 'foldGroups': 'datatypeFoldsTotal',
244
+ 'gap1ndex': 'datatypeLeavesTotal',
245
+ 'gap1ndexCeiling': 'datatypeElephino',
246
+ 'gapRangeStart': 'datatypeElephino',
247
+ 'gapsWhere': 'datatypeLeavesTotal',
248
+ 'groupsOfFolds': 'datatypeFoldsTotal',
249
+ 'indexDimension': 'datatypeLeavesTotal',
250
+ 'indexLeaf': 'datatypeLeavesTotal',
251
+ 'indexMiniGap': 'datatypeElephino',
252
+ 'leaf1ndex': 'datatypeLeavesTotal',
253
+ 'leafAbove': 'datatypeLeavesTotal',
254
+ 'leafBelow': 'datatypeLeavesTotal',
255
+ 'leafConnectee': 'datatypeLeavesTotal',
256
+ 'mapShape': 'datatypeLeavesTotal',
257
+ 'my': 'datatypeElephino',
258
+ 'taskDivisions': 'datatypeLeavesTotal',
259
+ 'taskIndex': 'datatypeLeavesTotal',
260
+ 'track': 'datatypeElephino',
261
+ }
262
+ RubeGoldBerg = _hackSSOTdatatype[identifier]
263
+ if RubeGoldBerg == 'datatypeElephino':
264
+ return _get_datatype('elephino')
265
+ elif RubeGoldBerg == 'datatypeFoldsTotal':
266
+ return _get_datatype('foldsTotal')
267
+ elif RubeGoldBerg == 'datatypeLeavesTotal':
268
+ return _get_datatype('leavesTotal')
269
+ raise Exception("Dude, you forgot to set a value in `hackSSOTdatatype`.")