mapFolding 0.16.0__py3-none-any.whl → 0.16.2__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.
- easyRun/A000682.py +25 -0
- easyRun/A005316.py +20 -0
- easyRun/NOTcountingFolds.py +36 -0
- easyRun/__init__.py +0 -0
- easyRun/countFolds.py +41 -0
- easyRun/meanders.py +69 -0
- mapFolding/__init__.py +8 -51
- mapFolding/_dataPacking.py +68 -0
- mapFolding/_theSSOT.py +33 -37
- mapFolding/_theTypes.py +21 -4
- mapFolding/algorithms/matrixMeanders.py +86 -517
- mapFolding/algorithms/matrixMeandersBeDry.py +182 -0
- mapFolding/algorithms/matrixMeandersNumPy.py +333 -0
- mapFolding/algorithms/matrixMeandersPandas.py +334 -0
- mapFolding/algorithms/oeisIDbyFormula.py +50 -29
- mapFolding/algorithms/zCuzDocStoopidoeisIDbyFormula.py +51 -29
- mapFolding/basecamp.py +167 -206
- mapFolding/beDRY.py +2 -30
- mapFolding/dataBaskets.py +75 -49
- mapFolding/oeis.py +11 -32
- mapFolding/reference/A000682facts.py +787 -652
- mapFolding/reference/A005316facts.py +961 -3
- mapFolding/reference/matrixMeandersAnalysis/prefixNotationNotes.py +15 -0
- mapFolding/reference/matrixMeandersAnalysis/signatures.py +2030 -0
- mapFolding/reference/meandersDumpingGround/A005316JavaPort.py +1 -1
- mapFolding/reference/meandersDumpingGround/A005316imperative.py +1 -1
- mapFolding/reference/meandersDumpingGround/matrixMeandersNumPyV1finalForm.py +424 -0
- mapFolding/someAssemblyRequired/A007822/A007822rawMaterials.py +3 -4
- mapFolding/someAssemblyRequired/A007822/makeA007822AsynchronousModules.py +103 -29
- mapFolding/someAssemblyRequired/A007822/makeA007822Modules.py +18 -14
- mapFolding/someAssemblyRequired/RecipeJob.py +2 -2
- mapFolding/someAssemblyRequired/makeJobTheorem2Numba.py +7 -6
- mapFolding/someAssemblyRequired/makeJobTheorem2codon.py +3 -4
- mapFolding/someAssemblyRequired/makingModules_count.py +88 -87
- mapFolding/someAssemblyRequired/makingModules_doTheNeedful.py +10 -9
- mapFolding/someAssemblyRequired/mapFolding/makeMapFoldingModules.py +3 -3
- mapFolding/someAssemblyRequired/meanders/__init__.py +0 -0
- mapFolding/someAssemblyRequired/meanders/makeMeandersModules.py +63 -0
- mapFolding/someAssemblyRequired/toolkitMakeModules.py +37 -37
- mapFolding/someAssemblyRequired/transformationTools.py +8 -8
- mapFolding/syntheticModules/A007822/algorithm.py +3 -3
- mapFolding/syntheticModules/A007822/algorithmNumba.py +1 -2
- mapFolding/syntheticModules/A007822/asynchronous.py +6 -4
- mapFolding/syntheticModules/A007822/asynchronousAnnex.py +5 -7
- mapFolding/syntheticModules/A007822/asynchronousAnnexNumba.py +70 -0
- mapFolding/syntheticModules/A007822/asynchronousNumba.py +79 -0
- mapFolding/syntheticModules/A007822/asynchronousTheorem2.py +15 -3
- mapFolding/syntheticModules/A007822/asynchronousTrimmed.py +12 -3
- mapFolding/syntheticModules/A007822/initializeState.py +1 -2
- mapFolding/syntheticModules/A007822/theorem2.py +7 -2
- mapFolding/syntheticModules/A007822/theorem2Numba.py +31 -4
- mapFolding/syntheticModules/A007822/theorem2Trimmed.py +8 -3
- mapFolding/syntheticModules/countParallelNumba.py +5 -2
- mapFolding/syntheticModules/dataPacking.py +1 -1
- mapFolding/syntheticModules/dataPackingA007822.py +92 -26
- mapFolding/syntheticModules/meanders/__init__.py +1 -0
- mapFolding/syntheticModules/meanders/bigInt.py +52 -0
- mapFolding/syntheticModules/theorem2.py +6 -0
- mapFolding/syntheticModules/theorem2Numba.py +8 -2
- mapFolding/syntheticModules/theorem2Trimmed.py +6 -0
- mapFolding/tests/conftest.py +28 -13
- mapFolding/tests/test_computations.py +68 -61
- mapFolding/tests/test_oeis.py +6 -6
- mapFolding/zCuzDocStoopid/__init__.py +4 -1
- mapFolding/zCuzDocStoopid/makeDocstrings.py +35 -28
- mapfolding-0.16.2.dist-info/METADATA +99 -0
- mapfolding-0.16.2.dist-info/RECORD +115 -0
- {mapfolding-0.16.0.dist-info → mapfolding-0.16.2.dist-info}/top_level.txt +1 -0
- mapFolding/algorithms/getBucketsTotal.py +0 -137
- mapFolding/reference/matrixMeandersAnalysis/evenEven.py +0 -144
- mapFolding/reference/matrixMeandersAnalysis/oddEven.py +0 -54
- mapFolding/trim_memory.py +0 -62
- mapfolding-0.16.0.dist-info/METADATA +0 -85
- mapfolding-0.16.0.dist-info/RECORD +0 -100
- {mapfolding-0.16.0.dist-info → mapfolding-0.16.2.dist-info}/WHEEL +0 -0
- {mapfolding-0.16.0.dist-info → mapfolding-0.16.2.dist-info}/entry_points.txt +0 -0
- {mapfolding-0.16.0.dist-info → mapfolding-0.16.2.dist-info}/licenses/LICENSE +0 -0
mapFolding/basecamp.py
CHANGED
|
@@ -1,17 +1,19 @@
|
|
|
1
1
|
"""Unified interface for map folding computation."""
|
|
2
2
|
|
|
3
3
|
from collections.abc import Sequence
|
|
4
|
-
from functools import cache
|
|
5
4
|
from mapFolding import (
|
|
6
|
-
getPathFilenameFoldsTotal,
|
|
7
|
-
setProcessorLimit, validateListDimensions)
|
|
8
|
-
from mapFolding.algorithms.matrixMeanders import doTheNeedful
|
|
5
|
+
getPathFilenameFoldsTotal, packageSettings, saveFoldsTotal, saveFoldsTotalFAILearly, validateListDimensions)
|
|
9
6
|
from os import PathLike
|
|
10
7
|
from pathlib import PurePath
|
|
11
|
-
import
|
|
8
|
+
from typing import Literal
|
|
12
9
|
|
|
10
|
+
# ruff: noqa: PLC0415
|
|
13
11
|
"""TODO new flow paradigm, incomplete
|
|
14
12
|
|
|
13
|
+
I don't want to FORCE people to use the meaningless OEIS ids without providing the definition of the ID at the same time.
|
|
14
|
+
|
|
15
|
+
On the other hand, I don't have any evidence that anyone is using this package except me.
|
|
16
|
+
|
|
15
17
|
algorithms directory
|
|
16
18
|
manually coded algorithms or formulas
|
|
17
19
|
`countFolds` will be a stable interface for multidimensional map folding, including synthetic modules
|
|
@@ -21,6 +23,7 @@ algorithms directory
|
|
|
21
23
|
an enhanced version of `oeisIDfor_n` will be a stable interface for calling by ID and n
|
|
22
24
|
|
|
23
25
|
General flow structure
|
|
26
|
+
basecamp should call `doTheNeedful` instead of `count` and `doTheNeedful` should handle things like `initializeState`.
|
|
24
27
|
doTheNeedful
|
|
25
28
|
specific to that version of that algorithm
|
|
26
29
|
abstracts the API for that algorithm, so that algorithm (such as multidimensional map folding) has a stable interface
|
|
@@ -76,8 +79,6 @@ def countFolds(listDimensions: Sequence[int] | None = None
|
|
|
76
79
|
# , * # TODO improve `standardizedEqualToCallableReturn` so it will work with keyword arguments
|
|
77
80
|
, CPUlimit: bool | float | int | None = None # noqa: FBT001
|
|
78
81
|
, mapShape: tuple[int, ...] | None = None
|
|
79
|
-
, oeisID: str | None = None
|
|
80
|
-
, oeis_n: int | None = None
|
|
81
82
|
, flow: str | None = None
|
|
82
83
|
) -> int:
|
|
83
84
|
"""
|
|
@@ -102,8 +103,7 @@ def countFolds(listDimensions: Sequence[int] | None = None
|
|
|
102
103
|
- 'maximum': divides the computation into `leavesTotal`-many tasks.
|
|
103
104
|
- 'cpu': divides the computation into the number of available CPUs.
|
|
104
105
|
CPUlimit : bool | float | int | None = None
|
|
105
|
-
If relevant, whether and how to limit the number of processors `countFolds` will use.
|
|
106
|
-
unless the computation is divided into more than one task with the `computationDivisions` parameter.
|
|
106
|
+
If relevant, whether and how to limit the number of processors `countFolds` will use.
|
|
107
107
|
- `False`, `None`, or `0`: No limits on processor usage; uses all available processors. All other values will
|
|
108
108
|
potentially limit processor usage.
|
|
109
109
|
- `True`: Yes, limit the processor usage; limits to 1 processor.
|
|
@@ -118,10 +118,6 @@ def countFolds(listDimensions: Sequence[int] | None = None
|
|
|
118
118
|
"dimensions", such as in the seminal paper, "Multi-dimensional map-folding". Nevertheless, in contemporary Python
|
|
119
119
|
programming, in the context of these algorithms, the term "shape" makes it much easier to align the mathematics with the
|
|
120
120
|
syntax of the programming language.
|
|
121
|
-
oeisID : str | None = None
|
|
122
|
-
The On-Line Encyclopedia of Integer Sequences (OEIS) ID for which to compute a(n) for value of 'n' set in `oeis_n`.
|
|
123
|
-
oeis_n : int | None = None
|
|
124
|
-
The 'n' value for the `oeisID`.
|
|
125
121
|
flow : str | None = None
|
|
126
122
|
My stupid way of selecting the version of the algorithm to use in the computation. There are certainly better ways to do
|
|
127
123
|
this, but I have not yet solved this issue. As of 2025 Aug 14, these values will work:
|
|
@@ -153,20 +149,12 @@ def countFolds(listDimensions: Sequence[int] | None = None
|
|
|
153
149
|
|
|
154
150
|
if mapShape:
|
|
155
151
|
pass
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
from mapFolding.oeis import dictionaryOEISMapFolding # noqa: PLC0415
|
|
159
|
-
with contextlib.suppress(KeyError):
|
|
160
|
-
mapShape = dictionaryOEISMapFolding[oeisID]['getMapShape'](oeis_n)
|
|
161
|
-
if not mapShape and listDimensions:
|
|
162
|
-
mapShape = validateListDimensions(listDimensions)
|
|
152
|
+
elif listDimensions:
|
|
153
|
+
mapShape = validateListDimensions(listDimensions)
|
|
163
154
|
|
|
164
155
|
if mapShape is None:
|
|
165
|
-
message = (
|
|
166
|
-
|
|
167
|
-
`{listDimensions = }`,
|
|
168
|
-
`{mapShape = }`,
|
|
169
|
-
`{oeisID = }` and `{oeis_n = }`,
|
|
156
|
+
message = (f"""I received these values:
|
|
157
|
+
`{listDimensions = }` and `{mapShape = }`,
|
|
170
158
|
but I was unable to select a map for which to count the folds."""
|
|
171
159
|
)
|
|
172
160
|
raise ValueError(message)
|
|
@@ -174,10 +162,10 @@ def countFolds(listDimensions: Sequence[int] | None = None
|
|
|
174
162
|
# task division instructions -----------------------------------------------------
|
|
175
163
|
|
|
176
164
|
if computationDivisions:
|
|
165
|
+
from mapFolding.beDRY import getLeavesTotal, getTaskDivisions, setProcessorLimit
|
|
177
166
|
concurrencyLimit: int = setProcessorLimit(CPUlimit, packageSettings.concurrencyPackage)
|
|
178
|
-
from mapFolding.beDRY import getLeavesTotal, getTaskDivisions # noqa: PLC0415
|
|
179
167
|
leavesTotal: int = getLeavesTotal(mapShape)
|
|
180
|
-
taskDivisions = getTaskDivisions(computationDivisions, concurrencyLimit, leavesTotal)
|
|
168
|
+
taskDivisions: int = getTaskDivisions(computationDivisions, concurrencyLimit, leavesTotal)
|
|
181
169
|
del leavesTotal
|
|
182
170
|
else:
|
|
183
171
|
concurrencyLimit = 1
|
|
@@ -193,169 +181,46 @@ def countFolds(listDimensions: Sequence[int] | None = None
|
|
|
193
181
|
|
|
194
182
|
# Flow control until I can figure out a good way ---------------------------------
|
|
195
183
|
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
`if oeisID == 'A007822'` precedes the `elif flow ==` cascade because A007822 is fundamentally incompatible with those flow
|
|
201
|
-
paths and it will cause `Exception` or incorrect computations.
|
|
202
|
-
|
|
203
|
-
Parallel version:
|
|
204
|
-
idk. The computation division logic will try to execute. As of 2025 Aug 13 at 11 PM, I haven't tried or thought about
|
|
205
|
-
a parallel version. And I don't really care. Potential parallelism is certainly present in `filterAsymmetricFolds`.
|
|
206
|
-
But, if I want to implement that, I should almost certainly replace `filterAsymmetricFolds` with a non-blocking
|
|
207
|
-
function to which `count` can pass the necessary values to. TODO Watch out for errors.
|
|
208
|
-
|
|
209
|
-
"""
|
|
210
|
-
match flow:
|
|
211
|
-
case 'asynchronous':
|
|
212
|
-
from mapFolding.dataBaskets import MapFoldingState # noqa: PLC0415
|
|
213
|
-
mapFoldingState: MapFoldingState = MapFoldingState(mapShape)
|
|
214
|
-
|
|
215
|
-
from mapFolding.syntheticModules.A007822.asynchronous import doTheNeedful # noqa: PLC0415
|
|
216
|
-
mapFoldingState = doTheNeedful(mapFoldingState)
|
|
217
|
-
|
|
218
|
-
case 'asynchronousTheorem2':
|
|
219
|
-
from mapFolding.dataBaskets import MapFoldingState # noqa: PLC0415
|
|
220
|
-
mapFoldingState: MapFoldingState = MapFoldingState(mapShape)
|
|
221
|
-
|
|
222
|
-
from mapFolding.syntheticModules.A007822.initializeState import transitionOnGroupsOfFolds # noqa: PLC0415
|
|
223
|
-
mapFoldingState = transitionOnGroupsOfFolds(mapFoldingState)
|
|
224
|
-
|
|
225
|
-
from mapFolding.syntheticModules.A007822.asynchronousAnnex import initializeConcurrencyManager # noqa: PLC0415
|
|
226
|
-
initializeConcurrencyManager(groupsOfFolds=mapFoldingState.groupsOfFolds)
|
|
227
|
-
mapFoldingState.groupsOfFolds = 0
|
|
228
|
-
|
|
229
|
-
from mapFolding.syntheticModules.A007822.asynchronousTheorem2 import count # noqa: PLC0415
|
|
230
|
-
mapFoldingState = count(mapFoldingState)
|
|
231
|
-
|
|
232
|
-
case 'asynchronousTrimmed':
|
|
233
|
-
from mapFolding.dataBaskets import MapFoldingState # noqa: PLC0415
|
|
234
|
-
mapFoldingState: MapFoldingState = MapFoldingState(mapShape)
|
|
235
|
-
|
|
236
|
-
from mapFolding.syntheticModules.A007822.initializeState import transitionOnGroupsOfFolds # noqa: PLC0415
|
|
237
|
-
mapFoldingState = transitionOnGroupsOfFolds(mapFoldingState)
|
|
238
|
-
|
|
239
|
-
from mapFolding.syntheticModules.A007822.asynchronousAnnex import initializeConcurrencyManager # noqa: PLC0415
|
|
240
|
-
initializeConcurrencyManager(groupsOfFolds=mapFoldingState.groupsOfFolds)
|
|
241
|
-
mapFoldingState.groupsOfFolds = 0
|
|
242
|
-
|
|
243
|
-
from mapFolding.syntheticModules.A007822.asynchronousTrimmed import count # noqa: PLC0415
|
|
244
|
-
mapFoldingState = count(mapFoldingState)
|
|
245
|
-
|
|
246
|
-
case 'numba':
|
|
247
|
-
from mapFolding.dataBaskets import MapFoldingState # noqa: PLC0415
|
|
248
|
-
mapFoldingState: MapFoldingState = MapFoldingState(mapShape)
|
|
249
|
-
|
|
250
|
-
from mapFolding.syntheticModules.A007822.algorithmNumba import doTheNeedful # noqa: PLC0415
|
|
251
|
-
mapFoldingState = doTheNeedful(mapFoldingState)
|
|
252
|
-
|
|
253
|
-
case 'theorem2':
|
|
254
|
-
from mapFolding.dataBaskets import MapFoldingState # noqa: PLC0415
|
|
255
|
-
mapFoldingState: MapFoldingState = MapFoldingState(mapShape)
|
|
256
|
-
|
|
257
|
-
from mapFolding.syntheticModules.A007822.initializeState import transitionOnGroupsOfFolds # noqa: PLC0415
|
|
258
|
-
mapFoldingState = transitionOnGroupsOfFolds(mapFoldingState)
|
|
259
|
-
|
|
260
|
-
from mapFolding.syntheticModules.A007822.theorem2 import count # noqa: PLC0415
|
|
261
|
-
mapFoldingState = count(mapFoldingState)
|
|
262
|
-
|
|
263
|
-
case 'theorem2Numba':
|
|
264
|
-
from mapFolding.dataBaskets import MapFoldingState # noqa: PLC0415
|
|
265
|
-
mapFoldingState: MapFoldingState = MapFoldingState(mapShape)
|
|
266
|
-
|
|
267
|
-
from mapFolding.syntheticModules.A007822.initializeState import transitionOnGroupsOfFolds # noqa: PLC0415
|
|
268
|
-
mapFoldingState = transitionOnGroupsOfFolds(mapFoldingState)
|
|
269
|
-
|
|
270
|
-
from mapFolding.syntheticModules.dataPackingA007822 import sequential # noqa: PLC0415
|
|
271
|
-
mapFoldingState = sequential(mapFoldingState)
|
|
272
|
-
|
|
273
|
-
case 'theorem2Trimmed':
|
|
274
|
-
from mapFolding.dataBaskets import MapFoldingState # noqa: PLC0415
|
|
275
|
-
mapFoldingState: MapFoldingState = MapFoldingState(mapShape)
|
|
276
|
-
|
|
277
|
-
from mapFolding.syntheticModules.A007822.initializeState import transitionOnGroupsOfFolds # noqa: PLC0415
|
|
278
|
-
mapFoldingState = transitionOnGroupsOfFolds(mapFoldingState)
|
|
279
|
-
|
|
280
|
-
from mapFolding.syntheticModules.A007822.theorem2Trimmed import count # noqa: PLC0415
|
|
281
|
-
mapFoldingState = count(mapFoldingState)
|
|
282
|
-
|
|
283
|
-
case _:
|
|
284
|
-
from mapFolding.dataBaskets import MapFoldingState # noqa: PLC0415
|
|
285
|
-
mapFoldingState: MapFoldingState = MapFoldingState(mapShape)
|
|
286
|
-
|
|
287
|
-
from mapFolding.syntheticModules.A007822.algorithm import doTheNeedful # noqa: PLC0415
|
|
288
|
-
mapFoldingState = doTheNeedful(mapFoldingState)
|
|
289
|
-
|
|
290
|
-
foldsTotal = mapFoldingState.groupsOfFolds
|
|
291
|
-
|
|
292
|
-
elif flow == 'daoOfMapFolding':
|
|
293
|
-
from mapFolding.dataBaskets import MapFoldingState # noqa: PLC0415
|
|
294
|
-
mapFoldingState: MapFoldingState = MapFoldingState(mapShape)
|
|
295
|
-
|
|
296
|
-
from mapFolding.algorithms.daoOfMapFolding import doTheNeedful # noqa: PLC0415
|
|
297
|
-
mapFoldingState = doTheNeedful(mapFoldingState)
|
|
298
|
-
foldsTotal = mapFoldingState.foldsTotal
|
|
299
|
-
|
|
300
|
-
elif flow == 'numba':
|
|
301
|
-
from mapFolding.dataBaskets import MapFoldingState # noqa: PLC0415
|
|
302
|
-
mapFoldingState: MapFoldingState = MapFoldingState(mapShape)
|
|
303
|
-
|
|
304
|
-
from mapFolding.syntheticModules.daoOfMapFoldingNumba import doTheNeedful # noqa: PLC0415
|
|
305
|
-
mapFoldingState = doTheNeedful(mapFoldingState)
|
|
306
|
-
foldsTotal = mapFoldingState.foldsTotal
|
|
307
|
-
|
|
308
|
-
elif flow == 'theorem2' and any(dimension > 2 for dimension in mapShape):
|
|
309
|
-
from mapFolding.dataBaskets import MapFoldingState # noqa: PLC0415
|
|
310
|
-
mapFoldingState: MapFoldingState = MapFoldingState(mapShape)
|
|
311
|
-
|
|
312
|
-
from mapFolding.syntheticModules.initializeState import transitionOnGroupsOfFolds # noqa: PLC0415
|
|
313
|
-
mapFoldingState = transitionOnGroupsOfFolds(mapFoldingState)
|
|
314
|
-
|
|
315
|
-
from mapFolding.syntheticModules.theorem2 import count # noqa: PLC0415
|
|
316
|
-
mapFoldingState = count(mapFoldingState)
|
|
317
|
-
|
|
318
|
-
foldsTotal = mapFoldingState.foldsTotal
|
|
319
|
-
|
|
320
|
-
elif flow == 'theorem2Trimmed' and any(dimension > 2 for dimension in mapShape):
|
|
321
|
-
from mapFolding.dataBaskets import MapFoldingState # noqa: PLC0415
|
|
322
|
-
mapFoldingState: MapFoldingState = MapFoldingState(mapShape)
|
|
184
|
+
if taskDivisions > 1:
|
|
185
|
+
from mapFolding.dataBaskets import ParallelMapFoldingState
|
|
186
|
+
mapFoldingParallelState: ParallelMapFoldingState = ParallelMapFoldingState(mapShape, taskDivisions=taskDivisions)
|
|
323
187
|
|
|
324
|
-
from mapFolding.syntheticModules.
|
|
325
|
-
mapFoldingState = transitionOnGroupsOfFolds(mapFoldingState)
|
|
188
|
+
from mapFolding.syntheticModules.countParallelNumba import doTheNeedful
|
|
326
189
|
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
foldsTotal = mapFoldingState.foldsTotal
|
|
190
|
+
# `listStatesParallel` exists so you can research the parallel computation.
|
|
191
|
+
foldsTotal, listStatesParallel = doTheNeedful(mapFoldingParallelState, concurrencyLimit) # pyright: ignore[reportUnusedVariable] # noqa: RUF059
|
|
331
192
|
|
|
332
|
-
|
|
333
|
-
from mapFolding.dataBaskets import MapFoldingState
|
|
193
|
+
else:
|
|
194
|
+
from mapFolding.dataBaskets import MapFoldingState
|
|
334
195
|
mapFoldingState: MapFoldingState = MapFoldingState(mapShape)
|
|
335
196
|
|
|
336
|
-
|
|
337
|
-
|
|
197
|
+
if flow == 'daoOfMapFolding':
|
|
198
|
+
from mapFolding.algorithms.daoOfMapFolding import doTheNeedful
|
|
199
|
+
mapFoldingState = doTheNeedful(mapFoldingState)
|
|
338
200
|
|
|
339
|
-
|
|
340
|
-
|
|
201
|
+
elif flow == 'numba':
|
|
202
|
+
from mapFolding.syntheticModules.daoOfMapFoldingNumba import doTheNeedful
|
|
203
|
+
mapFoldingState = doTheNeedful(mapFoldingState)
|
|
341
204
|
|
|
342
|
-
|
|
205
|
+
elif flow == 'theorem2' and any(dimension > 2 for dimension in mapShape):
|
|
206
|
+
from mapFolding.syntheticModules.theorem2 import doTheNeedful
|
|
207
|
+
mapFoldingState = doTheNeedful(mapFoldingState)
|
|
343
208
|
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
|
|
209
|
+
elif (flow == 'theorem2Numba' or taskDivisions == 0) and any(dimension > 2 for dimension in mapShape):
|
|
210
|
+
from mapFolding.syntheticModules.initializeState import transitionOnGroupsOfFolds
|
|
211
|
+
mapFoldingState = transitionOnGroupsOfFolds(mapFoldingState)
|
|
347
212
|
|
|
348
|
-
|
|
213
|
+
from mapFolding.syntheticModules.dataPacking import sequential
|
|
214
|
+
mapFoldingState = sequential(mapFoldingState)
|
|
349
215
|
|
|
350
|
-
|
|
351
|
-
|
|
216
|
+
elif flow == 'theorem2Trimmed' and any(dimension > 2 for dimension in mapShape):
|
|
217
|
+
from mapFolding.syntheticModules.theorem2Trimmed import doTheNeedful
|
|
218
|
+
mapFoldingState = doTheNeedful(mapFoldingState)
|
|
352
219
|
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
220
|
+
else:
|
|
221
|
+
from mapFolding.algorithms.daoOfMapFolding import doTheNeedful
|
|
222
|
+
mapFoldingState = doTheNeedful(mapFoldingState)
|
|
356
223
|
|
|
357
|
-
from mapFolding.syntheticModules.daoOfMapFoldingNumba import doTheNeedful # noqa: PLC0415
|
|
358
|
-
mapFoldingState = doTheNeedful(mapFoldingState)
|
|
359
224
|
foldsTotal = mapFoldingState.foldsTotal
|
|
360
225
|
|
|
361
226
|
# Follow memorialization instructions ---------------------------------------------
|
|
@@ -365,42 +230,138 @@ def countFolds(listDimensions: Sequence[int] | None = None
|
|
|
365
230
|
|
|
366
231
|
return foldsTotal
|
|
367
232
|
|
|
368
|
-
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
|
|
233
|
+
def NOTcountingFolds(oeisID: str, oeis_n: int, flow: str | None = None
|
|
234
|
+
# , pathLikeWriteFoldsTotal: PathLike[str] | PurePath | None = None # noqa: ERA001
|
|
235
|
+
, CPUlimit: bool | float | int | None = None # noqa: FBT001
|
|
236
|
+
) -> int:
|
|
237
|
+
"""Do stuff."""
|
|
238
|
+
countTotal: int = -31212012 # ERROR
|
|
239
|
+
matched_oeisID: bool = True
|
|
240
|
+
|
|
241
|
+
match oeisID:
|
|
242
|
+
case 'A000136':
|
|
243
|
+
from mapFolding.algorithms.oeisIDbyFormula import A000136 as doTheNeedful
|
|
244
|
+
case 'A000560':
|
|
245
|
+
from mapFolding.algorithms.oeisIDbyFormula import A000560 as doTheNeedful
|
|
246
|
+
case 'A001010':
|
|
247
|
+
from mapFolding.algorithms.oeisIDbyFormula import A001010 as doTheNeedful
|
|
248
|
+
case 'A001011':
|
|
249
|
+
from mapFolding.algorithms.oeisIDbyFormula import A001011 as doTheNeedful
|
|
250
|
+
case 'A005315':
|
|
251
|
+
from mapFolding.algorithms.oeisIDbyFormula import A005315 as doTheNeedful
|
|
252
|
+
case 'A060206':
|
|
253
|
+
from mapFolding.algorithms.oeisIDbyFormula import A060206 as doTheNeedful
|
|
254
|
+
case 'A077460':
|
|
255
|
+
from mapFolding.algorithms.oeisIDbyFormula import A077460 as doTheNeedful
|
|
256
|
+
case 'A078591':
|
|
257
|
+
from mapFolding.algorithms.oeisIDbyFormula import A078591 as doTheNeedful
|
|
258
|
+
case 'A178961':
|
|
259
|
+
from mapFolding.algorithms.oeisIDbyFormula import A178961 as doTheNeedful
|
|
260
|
+
case 'A223094':
|
|
261
|
+
from mapFolding.algorithms.oeisIDbyFormula import A223094 as doTheNeedful
|
|
262
|
+
case 'A259702':
|
|
263
|
+
from mapFolding.algorithms.oeisIDbyFormula import A259702 as doTheNeedful
|
|
264
|
+
case 'A301620':
|
|
265
|
+
from mapFolding.algorithms.oeisIDbyFormula import A301620 as doTheNeedful
|
|
266
|
+
case _:
|
|
267
|
+
matched_oeisID = False
|
|
268
|
+
if matched_oeisID:
|
|
269
|
+
countTotal = doTheNeedful(oeis_n) # pyright: ignore[reportPossiblyUnboundVariable]
|
|
270
|
+
else:
|
|
271
|
+
matched_oeisID = True
|
|
272
|
+
match oeisID:
|
|
273
|
+
case 'A000682' | 'A005316':
|
|
274
|
+
match flow:
|
|
275
|
+
case 'matrixNumPy':
|
|
276
|
+
from mapFolding.algorithms.matrixMeandersNumPy import doTheNeedful
|
|
277
|
+
from mapFolding.dataBaskets import MatrixMeandersNumPyState as State
|
|
278
|
+
case 'matrixPandas':
|
|
279
|
+
from mapFolding.algorithms.matrixMeandersPandas import doTheNeedful
|
|
280
|
+
from mapFolding.dataBaskets import MatrixMeandersNumPyState as State
|
|
281
|
+
case _:
|
|
282
|
+
from mapFolding.algorithms.matrixMeanders import doTheNeedful
|
|
283
|
+
from mapFolding.dataBaskets import MatrixMeandersState as State
|
|
284
|
+
|
|
285
|
+
boundary: int = oeis_n - 1
|
|
286
|
+
|
|
287
|
+
if oeisID == 'A000682':
|
|
288
|
+
if oeis_n == 1:
|
|
289
|
+
return 1
|
|
290
|
+
elif oeis_n & 0b1:
|
|
291
|
+
arcCode: int = 0b101
|
|
292
|
+
else:
|
|
293
|
+
arcCode = 0b1
|
|
294
|
+
listArcCodes: list[int] = [(arcCode << 1) | arcCode]
|
|
295
|
+
# 0b1010 | 0b0101 is 0b1111, or 0xf
|
|
296
|
+
# 0b10 | 0b01 is 0b11, or 0x3
|
|
297
|
+
|
|
298
|
+
MAXIMUMarcCode: int = 1 << (2 * boundary + 4)
|
|
299
|
+
while listArcCodes[-1] < MAXIMUMarcCode:
|
|
300
|
+
arcCode = (arcCode << 4) | 0b0101 # e.g., 0b 10000 | 0b 0101 = 0b 10101
|
|
301
|
+
listArcCodes.append((arcCode << 1) | arcCode) # e.g., 0b 101010 | 0b 1010101 = 0b 111111 = 0x3f
|
|
302
|
+
# Thereafter, append 0b1111 or 0xf, so, e.g., 0x3f, 0x3ff, 0x3fff, 0x3ffff, ...
|
|
303
|
+
# See "mapFolding/reference/A000682facts.py"
|
|
304
|
+
dictionaryMeanders=dict.fromkeys(listArcCodes, 1)
|
|
305
|
+
|
|
306
|
+
elif oeisID == 'A005316':
|
|
307
|
+
if oeis_n & 0b1:
|
|
308
|
+
dictionaryMeanders: dict[int, int] = {0b1111: 1} # 0xf
|
|
309
|
+
else:
|
|
310
|
+
dictionaryMeanders = {0b10110: 1}
|
|
311
|
+
else:
|
|
312
|
+
message = f"Programming error: I should never have received `{oeisID = }`."
|
|
313
|
+
raise ValueError(message)
|
|
314
|
+
|
|
315
|
+
state = State(oeis_n, oeisID, boundary, dictionaryMeanders)
|
|
316
|
+
countTotal = doTheNeedful(state) # pyright: ignore[reportArgumentType]
|
|
317
|
+
case 'A007822':
|
|
318
|
+
mapShape: tuple[Literal[1], int] = (1, 2 * oeis_n)
|
|
319
|
+
from mapFolding import setProcessorLimit
|
|
320
|
+
concurrencyLimit: int = setProcessorLimit(CPUlimit)
|
|
321
|
+
|
|
322
|
+
from mapFolding.dataBaskets import MapFoldingState
|
|
323
|
+
mapFoldingState: MapFoldingState = MapFoldingState(mapShape)
|
|
324
|
+
|
|
325
|
+
match flow:
|
|
326
|
+
case 'asynchronous':
|
|
327
|
+
from mapFolding.syntheticModules.A007822.asynchronous import doTheNeedful
|
|
328
|
+
mapFoldingState = doTheNeedful(mapFoldingState, concurrencyLimit)
|
|
372
329
|
|
|
373
|
-
|
|
330
|
+
case 'asynchronousNumba':
|
|
331
|
+
from mapFolding.syntheticModules.A007822.asynchronousNumba import doTheNeedful
|
|
332
|
+
mapFoldingState = doTheNeedful(mapFoldingState, concurrencyLimit)
|
|
374
333
|
|
|
375
|
-
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
curveLocations = 1
|
|
379
|
-
listCurveLocations: list[int] = [(curveLocations << 1) | curveLocations]
|
|
334
|
+
case 'asynchronousTheorem2':
|
|
335
|
+
from mapFolding.syntheticModules.A007822.asynchronousTheorem2 import doTheNeedful
|
|
336
|
+
mapFoldingState = doTheNeedful(mapFoldingState, concurrencyLimit)
|
|
380
337
|
|
|
381
|
-
|
|
382
|
-
|
|
383
|
-
|
|
384
|
-
listCurveLocations.append((curveLocations << 1) | curveLocations)
|
|
338
|
+
case 'asynchronousTrimmed':
|
|
339
|
+
from mapFolding.syntheticModules.A007822.asynchronousTrimmed import doTheNeedful
|
|
340
|
+
mapFoldingState = doTheNeedful(mapFoldingState, concurrencyLimit)
|
|
385
341
|
|
|
386
|
-
|
|
342
|
+
case 'numba':
|
|
343
|
+
from mapFolding.syntheticModules.A007822.algorithmNumba import doTheNeedful
|
|
344
|
+
mapFoldingState = doTheNeedful(mapFoldingState)
|
|
387
345
|
|
|
388
|
-
|
|
346
|
+
case 'theorem2':
|
|
347
|
+
from mapFolding.syntheticModules.A007822.theorem2 import doTheNeedful
|
|
348
|
+
mapFoldingState = doTheNeedful(mapFoldingState)
|
|
389
349
|
|
|
390
|
-
|
|
350
|
+
case 'theorem2Numba':
|
|
351
|
+
from mapFolding.syntheticModules.A007822.theorem2Numba import doTheNeedful
|
|
352
|
+
mapFoldingState = doTheNeedful(mapFoldingState)
|
|
391
353
|
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
oeisID = 'A005316'
|
|
354
|
+
case 'theorem2Trimmed':
|
|
355
|
+
from mapFolding.syntheticModules.A007822.theorem2Trimmed import doTheNeedful
|
|
356
|
+
mapFoldingState = doTheNeedful(mapFoldingState)
|
|
396
357
|
|
|
397
|
-
|
|
358
|
+
case _:
|
|
359
|
+
from mapFolding.syntheticModules.A007822.algorithm import doTheNeedful
|
|
360
|
+
mapFoldingState = doTheNeedful(mapFoldingState)
|
|
398
361
|
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
dictionaryCurveLocations = {22: 1}
|
|
362
|
+
countTotal = mapFoldingState.groupsOfFolds
|
|
363
|
+
case _:
|
|
364
|
+
matched_oeisID = False
|
|
403
365
|
|
|
404
|
-
|
|
366
|
+
return countTotal
|
|
405
367
|
|
|
406
|
-
return doTheNeedful(state)
|
mapFolding/beDRY.py
CHANGED
|
@@ -1,26 +1,4 @@
|
|
|
1
|
-
"""
|
|
2
|
-
Core computational utilities implementing Lunnon's map folding algorithm.
|
|
3
|
-
|
|
4
|
-
(AI generated docstring)
|
|
5
|
-
|
|
6
|
-
With the configuration foundation established and the type system defined, this
|
|
7
|
-
module provides the essential building blocks that transform mathematical theory
|
|
8
|
-
into executable computation. These utilities implement the fundamental operations
|
|
9
|
-
required by Lunnon's 1971 algorithm, handling dimension validation, connection
|
|
10
|
-
graph generation, and computational resource management.
|
|
11
|
-
|
|
12
|
-
The connection graph generation represents the mathematical heart of the algorithm,
|
|
13
|
-
calculating how leaves connect across dimensions using coordinate systems, parity
|
|
14
|
-
rules, and boundary conditions. This graph becomes the foundation upon which the
|
|
15
|
-
recursive folding analysis operates. Validation functions ensure computational
|
|
16
|
-
of large-scale problems. Validation functions ensure computational
|
|
17
|
-
integrity, while task division management enables experimental task division strategies.
|
|
18
|
-
|
|
19
|
-
These utilities follow DRY and SSOT principles, providing reusable functions that
|
|
20
|
-
serve as the computational assembly-line components. They prepare the essential
|
|
21
|
-
data structures and computational parameters that the state management system
|
|
22
|
-
requires to orchestrate the complex recursive algorithms.
|
|
23
|
-
"""
|
|
1
|
+
"""Oft-needed computations or actions, especially for multi-dimensional map folding."""
|
|
24
2
|
|
|
25
3
|
from collections.abc import Sequence
|
|
26
4
|
from hunterMakesPy import defineConcurrencyLimit, intInnit, oopsieKwargsie
|
|
@@ -33,8 +11,6 @@ import numpy
|
|
|
33
11
|
def getLeavesTotal(mapShape: tuple[int, ...]) -> int:
|
|
34
12
|
"""Calculate the total number of leaves in a map with the given dimensions.
|
|
35
13
|
|
|
36
|
-
(AI generated docstring)
|
|
37
|
-
|
|
38
14
|
The total number of leaves is the product of all dimensions in the map shape.
|
|
39
15
|
|
|
40
16
|
Parameters
|
|
@@ -66,8 +42,6 @@ def getLeavesTotal(mapShape: tuple[int, ...]) -> int:
|
|
|
66
42
|
def getTaskDivisions(computationDivisions: int | str | None, concurrencyLimit: int, leavesTotal: int) -> int:
|
|
67
43
|
"""Determine whether to divide the computation into tasks and how many divisions.
|
|
68
44
|
|
|
69
|
-
(AI generated docstring)
|
|
70
|
-
|
|
71
45
|
Parameters
|
|
72
46
|
----------
|
|
73
47
|
computationDivisions : int | str | None
|
|
@@ -214,12 +188,10 @@ def makeDataContainer(shape: int | tuple[int, ...], datatype: type[NumPyIntegerT
|
|
|
214
188
|
def setProcessorLimit(CPUlimit: Any | None, concurrencyPackage: str | None = None) -> int:
|
|
215
189
|
"""Set the CPU usage limit for concurrent operations.
|
|
216
190
|
|
|
217
|
-
(AI generated docstring)
|
|
218
|
-
|
|
219
191
|
Parameters
|
|
220
192
|
----------
|
|
221
193
|
CPUlimit : Any | None
|
|
222
|
-
Please see the documentation
|
|
194
|
+
Please see the documentation in `countFolds` for details. I know it is annoying, but I want to be sure you
|
|
223
195
|
have the most accurate information.
|
|
224
196
|
concurrencyPackage : str | None = None
|
|
225
197
|
Specifies which concurrency package to use.
|