synkit 1.6.5__py3-none-win_amd64.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.
- synkit/CRN/Benchmark/__init__.py +53 -0
- synkit/CRN/Benchmark/crosschecks.py +13 -0
- synkit/CRN/Benchmark/kegg.py +12 -0
- synkit/CRN/Benchmark/networks.py +13 -0
- synkit/CRN/Benchmark/scaling.py +13 -0
- synkit/CRN/Benchmark/validate.py +13 -0
- synkit/CRN/Construct/__init__.py +16 -0
- synkit/CRN/Construct/abstract.py +668 -0
- synkit/CRN/Construct/arity.py +36 -0
- synkit/CRN/Construct/builder.py +619 -0
- synkit/CRN/Construct/derivation.py +63 -0
- synkit/CRN/Construct/flattener.py +100 -0
- synkit/CRN/Construct/keys.py +14 -0
- synkit/CRN/Construct/mixtures.py +117 -0
- synkit/CRN/Construct/rdkit_worker.py +69 -0
- synkit/CRN/Construct/smiles.py +99 -0
- synkit/CRN/Construct/state.py +31 -0
- synkit/CRN/Construct/strategy.py +75 -0
- synkit/CRN/Construct/worker.py +42 -0
- synkit/CRN/IO/__init__.py +36 -0
- synkit/CRN/IO/sbml.py +925 -0
- synkit/CRN/Pathway/__init__.py +72 -0
- synkit/CRN/Pathway/_adapter.py +333 -0
- synkit/CRN/Pathway/pathfinder.py +500 -0
- synkit/CRN/Pathway/reachability.py +796 -0
- synkit/CRN/Pathway/realizability.py +1322 -0
- synkit/CRN/Petrinet/__init__.py +93 -0
- synkit/CRN/Petrinet/analyzer.py +486 -0
- synkit/CRN/Petrinet/minimal_semiflows.py +436 -0
- synkit/CRN/Petrinet/net.py +1041 -0
- synkit/CRN/Petrinet/persistence.py +97 -0
- synkit/CRN/Petrinet/semiflows.py +483 -0
- synkit/CRN/Petrinet/siphon_search.py +402 -0
- synkit/CRN/Petrinet/structure.py +286 -0
- synkit/CRN/Props/__init__.py +130 -0
- synkit/CRN/Props/_rank.py +29 -0
- synkit/CRN/Props/deficiency.py +953 -0
- synkit/CRN/Props/dynamics.py +832 -0
- synkit/CRN/Props/helper.py +151 -0
- synkit/CRN/Props/stoich.py +751 -0
- synkit/CRN/Props/thermo.py +584 -0
- synkit/CRN/Query/__init__.py +66 -0
- synkit/CRN/Query/cache.py +41 -0
- synkit/CRN/Query/kegg_api.py +99 -0
- synkit/CRN/Query/kegg_extract.py +714 -0
- synkit/CRN/Query/kegg_impute.py +707 -0
- synkit/CRN/Query/kegg_parse.py +480 -0
- synkit/CRN/Query/to_syncrn.py +290 -0
- synkit/CRN/README.md +234 -0
- synkit/CRN/Structure/__init__.py +12 -0
- synkit/CRN/Structure/_graph_io.py +713 -0
- synkit/CRN/Structure/_matrices.py +88 -0
- synkit/CRN/Structure/_parse.py +544 -0
- synkit/CRN/Structure/reaction.py +237 -0
- synkit/CRN/Structure/rule.py +55 -0
- synkit/CRN/Structure/species.py +46 -0
- synkit/CRN/Structure/syncrn.py +929 -0
- synkit/CRN/Symmetry/__init__.py +20 -0
- synkit/CRN/Symmetry/_common.py +1059 -0
- synkit/CRN/Symmetry/_ir.py +940 -0
- synkit/CRN/Symmetry/automorphism.py +472 -0
- synkit/CRN/Symmetry/canon.py +441 -0
- synkit/CRN/Symmetry/isomorphism.py +412 -0
- synkit/CRN/Symmetry/symmetry.py +61 -0
- synkit/CRN/Symmetry/wl_canon.py +967 -0
- synkit/CRN/Visualize/__init__.py +11 -0
- synkit/CRN/Visualize/labels.py +113 -0
- synkit/CRN/Visualize/layout.py +708 -0
- synkit/CRN/Visualize/palette.py +292 -0
- synkit/CRN/Visualize/validation.py +122 -0
- synkit/CRN/Visualize/vis.py +1152 -0
- synkit/CRN/__init__.py +233 -0
- synkit/CRN/_build.py +50 -0
- synkit/CRN/_native_build.py +175 -0
- synkit/CRN/analysis.py +629 -0
- synkit/CRN/backend.py +74 -0
- synkit/CRN/cpp/CMakeLists.txt +58 -0
- synkit/CRN/cpp/algebra.cpp +46 -0
- synkit/CRN/cpp/closure.cpp +29 -0
- synkit/CRN/cpp/exact.h +55 -0
- synkit/CRN/cpp/pathway.cpp +46 -0
- synkit/CRN/cpp/semiflows.cpp +209 -0
- synkit/CRN/cpp/structural.cpp +240 -0
- synkit/CRN/cpp/symmetry.cpp +45 -0
- synkit/CRN/cpp/write_manifest.cmake +28 -0
- synkit/CRN/kinds.py +137 -0
- synkit/CRN/lib/synkit_crn.dll +0 -0
- synkit/CRN/lib/synkit_crn.json +33 -0
- synkit/CRN/native.py +388 -0
- synkit/CRN/native_analysis.py +459 -0
- synkit/Chem/Cluster/__init__.py +0 -0
- synkit/Chem/Cluster/butina.py +140 -0
- synkit/Chem/Fingerprint/__init__.py +0 -0
- synkit/Chem/Fingerprint/fp_calculator.py +155 -0
- synkit/Chem/Fingerprint/smiles_featurizer.py +258 -0
- synkit/Chem/Fingerprint/transformation_fp.py +139 -0
- synkit/Chem/Mapper/README.rst +43 -0
- synkit/Chem/Mapper/__init__.py +255 -0
- synkit/Chem/Mapper/_compat.py +130 -0
- synkit/Chem/Mapper/adapters/__init__.py +1 -0
- synkit/Chem/Mapper/adapters/prediction.py +126 -0
- synkit/Chem/Mapper/adapters/template.py +412 -0
- synkit/Chem/Mapper/chem/__init__.py +52 -0
- synkit/Chem/Mapper/chem/aam.py +673 -0
- synkit/Chem/Mapper/chem/blind.py +160 -0
- synkit/Chem/Mapper/chem/its.py +309 -0
- synkit/Chem/Mapper/chem/smiles.py +564 -0
- synkit/Chem/Mapper/graph/__init__.py +66 -0
- synkit/Chem/Mapper/graph/automorphism.py +395 -0
- synkit/Chem/Mapper/graph/blockcut.py +98 -0
- synkit/Chem/Mapper/graph/labeled_graph.py +104 -0
- synkit/Chem/Mapper/graph/refine.py +176 -0
- synkit/Chem/Mapper/graph/synkit_adapter.py +110 -0
- synkit/Chem/Mapper/io/__init__.py +13 -0
- synkit/Chem/Mapper/io/idxmapstr.py +82 -0
- synkit/Chem/Mapper/mapper.py +685 -0
- synkit/Chem/Mapper/reaction_search.py +554 -0
- synkit/Chem/Mapper/reporting/__init__.py +1 -0
- synkit/Chem/Mapper/reporting/alternatives.py +451 -0
- synkit/Chem/Mapper/reporting/analysis.py +681 -0
- synkit/Chem/Mapper/reporting/native_analysis.py +485 -0
- synkit/Chem/Mapper/reporting/spectrum.py +642 -0
- synkit/Chem/Mapper/solvers/__init__.py +1 -0
- synkit/Chem/Mapper/solvers/exact/__init__.py +141 -0
- synkit/Chem/Mapper/solvers/exact/assignment/__init__.py +1 -0
- synkit/Chem/Mapper/solvers/exact/assignment/assignment_certificate.py +113 -0
- synkit/Chem/Mapper/solvers/exact/assignment/assignment_domains.py +162 -0
- synkit/Chem/Mapper/solvers/exact/assignment/assignment_verification.py +58 -0
- synkit/Chem/Mapper/solvers/exact/assignment/incremental_assignment.py +247 -0
- synkit/Chem/Mapper/solvers/exact/certificate.py +128 -0
- synkit/Chem/Mapper/solvers/exact/core.py +183 -0
- synkit/Chem/Mapper/solvers/exact/distance_search/__init__.py +1 -0
- synkit/Chem/Mapper/solvers/exact/distance_search/bounds.py +319 -0
- synkit/Chem/Mapper/solvers/exact/distance_search/exhaustive.py +179 -0
- synkit/Chem/Mapper/solvers/exact/distance_search/inputs.py +283 -0
- synkit/Chem/Mapper/solvers/exact/distance_search/records.py +242 -0
- synkit/Chem/Mapper/solvers/exact/distance_search/search.py +1025 -0
- synkit/Chem/Mapper/solvers/exact/distance_search/verify.py +378 -0
- synkit/Chem/Mapper/solvers/exact/edit_support.py +375 -0
- synkit/Chem/Mapper/solvers/exact/hybrid.py +224 -0
- synkit/Chem/Mapper/solvers/exact/hydrogen.py +264 -0
- synkit/Chem/Mapper/solvers/exact/kernel_solvers/__init__.py +1 -0
- synkit/Chem/Mapper/solvers/exact/kernel_solvers/branching.py +499 -0
- synkit/Chem/Mapper/solvers/exact/kernel_solvers/enumerate.py +1050 -0
- synkit/Chem/Mapper/solvers/exact/kernel_solvers/enumeration_result.py +30 -0
- synkit/Chem/Mapper/solvers/exact/kernel_solvers/kernel.py +256 -0
- synkit/Chem/Mapper/solvers/exact/kernel_solvers/milp.py +194 -0
- synkit/Chem/Mapper/solvers/exact/native/__init__.py +1 -0
- synkit/Chem/Mapper/solvers/exact/native/build.py +154 -0
- synkit/Chem/Mapper/solvers/exact/native/candidates.py +593 -0
- synkit/Chem/Mapper/solvers/exact/native/canonical.py +396 -0
- synkit/Chem/Mapper/solvers/exact/native/disk_frontier.py +415 -0
- synkit/Chem/Mapper/solvers/exact/native/frontier.py +390 -0
- synkit/Chem/Mapper/solvers/exact/native/hydrogen_quotient.py +213 -0
- synkit/Chem/Mapper/solvers/exact/native/its.py +528 -0
- synkit/Chem/Mapper/solvers/exact/native/native_distance.cpp +2803 -0
- synkit/Chem/Mapper/solvers/exact/native/orbit_aggregation.py +328 -0
- synkit/Chem/Mapper/solvers/exact/native/parallel.py +205 -0
- synkit/Chem/Mapper/solvers/exact/native/pmcd.py +203 -0
- synkit/Chem/Mapper/solvers/exact/native/runtime.py +40 -0
- synkit/Chem/Mapper/solvers/exact/native/search.py +294 -0
- synkit/Chem/Mapper/solvers/exact/native/separator.py +224 -0
- synkit/Chem/Mapper/solvers/exact/native_build.py +12 -0
- synkit/Chem/Mapper/solvers/exact/pabs/__init__.py +1 -0
- synkit/Chem/Mapper/solvers/exact/pabs/cost_lattice.py +43 -0
- synkit/Chem/Mapper/solvers/exact/pabs/factor_spectrum.py +110 -0
- synkit/Chem/Mapper/solvers/exact/pabs/multi_shell.py +368 -0
- synkit/Chem/Mapper/solvers/exact/pabs/propagation.py +679 -0
- synkit/Chem/Mapper/solvers/exact/pabs/propagation_bounds.py +436 -0
- synkit/Chem/Mapper/solvers/exact/pabs/propagation_limits.py +13 -0
- synkit/Chem/Mapper/solvers/exact/pabs/propagation_search.py +856 -0
- synkit/Chem/Mapper/solvers/exact/pabs/propagation_symmetry.py +66 -0
- synkit/Chem/Mapper/solvers/exact/pabs/residual_typed_bonds.py +136 -0
- synkit/Chem/Mapper/solvers/exact/pabs/reward_frontier.py +201 -0
- synkit/Chem/Mapper/solvers/exact/pabs/separator_bound.py +258 -0
- synkit/Chem/Mapper/solvers/exact/pabs/separator_spectrum.py +308 -0
- synkit/Chem/Mapper/solvers/exact/pabs/sparse_reward_bound.py +207 -0
- synkit/Chem/Mapper/solvers/exact/pabs/suffix_spectrum.py +299 -0
- synkit/Chem/Mapper/solvers/exact/search.py +55 -0
- synkit/Chem/Mapper/solvers/exact/seeds/__init__.py +1 -0
- synkit/Chem/Mapper/solvers/exact/seeds/seed.py +104 -0
- synkit/Chem/Mapper/solvers/exact/seeds/seed_fragments.py +148 -0
- synkit/Chem/Mapper/solvers/exact/seeds/seed_relaxation.py +181 -0
- synkit/Chem/Mapper/solvers/exact/symmetry.py +223 -0
- synkit/Chem/Mapper/solvers/native/__init__.py +4 -0
- synkit/Chem/Mapper/solvers/native/assignment.py +99 -0
- synkit/Chem/Mapper/solvers/native/astar.py +22 -0
- synkit/Chem/Mapper/solvers/native/build.py +385 -0
- synkit/Chem/Mapper/solvers/native/classification.py +641 -0
- synkit/Chem/Mapper/solvers/native/core.py +378 -0
- synkit/Chem/Mapper/solvers/native/cpp/CMakeLists.txt +120 -0
- synkit/Chem/Mapper/solvers/native/cpp/examples/map_reaction.cpp +29 -0
- synkit/Chem/Mapper/solvers/native/cpp/examples/slap_graph.cpp +63 -0
- synkit/Chem/Mapper/solvers/native/cpp/include/synkit_mapper/assignment/assignment.h +18 -0
- synkit/Chem/Mapper/solvers/native/cpp/include/synkit_mapper/astar/astar.h +18 -0
- synkit/Chem/Mapper/solvers/native/cpp/include/synkit_mapper/astar/bound.h +33 -0
- synkit/Chem/Mapper/solvers/native/cpp/include/synkit_mapper/core/pmcd_witness.h +16 -0
- synkit/Chem/Mapper/solvers/native/cpp/include/synkit_mapper/core/runtime.h +130 -0
- synkit/Chem/Mapper/solvers/native/cpp/include/synkit_mapper/hydrogen/hydrogen.h +73 -0
- synkit/Chem/Mapper/solvers/native/cpp/include/synkit_mapper/mapper.h +175 -0
- synkit/Chem/Mapper/solvers/native/cpp/include/synkit_mapper/mces/mces.h +9 -0
- synkit/Chem/Mapper/solvers/native/cpp/include/synkit_mapper/pabs/seed.h +34 -0
- synkit/Chem/Mapper/solvers/native/cpp/include/synkit_mapper/reaction/reaction.h +30 -0
- synkit/Chem/Mapper/solvers/native/cpp/include/synkit_mapper/sepdp/sepdp.h +21 -0
- synkit/Chem/Mapper/solvers/native/cpp/include/synkit_mapper/slap.h +72 -0
- synkit/Chem/Mapper/solvers/native/cpp/include/synkit_mapper/solvers/solvers.h +16 -0
- synkit/Chem/Mapper/solvers/native/cpp/include/synkit_mapper/symmetry/classification.h +140 -0
- synkit/Chem/Mapper/solvers/native/cpp/include/synkit_mapper/symmetry/cpabs.h +33 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/assignment/abb.cpp +302 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/astar/CMakeLists.txt +12 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/astar/README.md +47 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/astar/astar.cpp +228 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/astar/astar_graph.cpp +37 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/astar/bound.cpp +212 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/core/dispatch.cpp +272 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/core/pmcd_witness.cpp +36 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/hydrogen/hydrogen.cpp +380 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/mces/README.md +57 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/mces/mces.cpp +287 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/pabs/bridge.cpp +334 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/pabs/chemical_floor.inc +181 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/pabs/endpoint_symmetry.inc +104 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/pabs/exact_helpers.h +20 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/pabs/lp_assignment_certificate.h +165 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/pabs/lp_certificate.h +125 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/pabs/lp_model.h +365 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/pabs/lp_provider.inc +319 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/pabs/lp_rounding.inc +170 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/pabs/lp_test_hooks.h +342 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/pabs/objective_reduction.inc +137 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/pabs/overlap_dual.inc +351 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/pabs/profile_seed.inc +214 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/pabs/seed_heuristics.inc +640 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/pabs/sparse_embedding.cpp +430 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/pabs/sparse_root_lp.h +176 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/pabs/test_hooks.inc +262 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/reaction/reaction.cpp +611 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/sepdp/README.md +61 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/sepdp/sepdp.cpp +253 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/slap.cpp +810 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/solvers/formulation.h +138 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/solvers/maxsat.cpp +526 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/solvers/ortools.cpp +475 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/solvers/seed.h +80 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/solvers/weighted_cnf.h +256 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/supporting/README.md +43 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/supporting/dfs.cpp +123 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/supporting/edit_support.cpp +224 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/classification.cpp +553 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/classification_pipeline.cpp +124 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/classification_stream.h +13 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/cpabs.cpp +455 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/edge_deck.cpp +743 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/vendor/nauty/COPYRIGHT +44 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/vendor/nauty/LICENSE-2.0.txt +202 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/vendor/nauty/naugraph.c +732 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/vendor/nauty/naurng.c +94 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/vendor/nauty/naurng.h +49 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/vendor/nauty/nausparse.c +1771 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/vendor/nauty/nausparse.h +133 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/vendor/nauty/nautil.c +750 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/vendor/nauty/naututil.h +355 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/vendor/nauty/nauty.c +1256 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/vendor/nauty/nauty.h +1544 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/vendor/nauty/schreier.c +1131 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/vendor/nauty/schreier.h +70 -0
- synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/vendor/nauty/sorttemplates.c +580 -0
- synkit/Chem/Mapper/solvers/native/hydrogen.py +711 -0
- synkit/Chem/Mapper/solvers/native/implicit.py +506 -0
- synkit/Chem/Mapper/solvers/native/implicit_certificate.py +187 -0
- synkit/Chem/Mapper/solvers/native/implicit_preparation.py +309 -0
- synkit/Chem/Mapper/solvers/native/lib/synkit_mapper.dll +0 -0
- synkit/Chem/Mapper/solvers/native/mces.py +16 -0
- synkit/Chem/Mapper/solvers/native/reaction.py +179 -0
- synkit/Chem/Mapper/solvers/native/reaction_build.py +277 -0
- synkit/Chem/Mapper/solvers/native/reaction_text.py +26 -0
- synkit/Chem/Mapper/solvers/native/runtime.py +242 -0
- synkit/Chem/Mapper/solvers/native/sepdp.py +47 -0
- synkit/Chem/Mapper/solvers/native/slap.py +266 -0
- synkit/Chem/Mapper/solvers/native/solvers.py +67 -0
- synkit/Chem/Mapper/solvers/native/stereo.py +86 -0
- synkit/Chem/Mapper/solvers/native/supporting.py +34 -0
- synkit/Chem/Mapper/solvers/native/symmetry.py +91 -0
- synkit/Chem/Mapper/solvers/slap/__init__.py +29 -0
- synkit/Chem/Mapper/solvers/slap/lap.py +174 -0
- synkit/Chem/Mapper/solvers/slap/sequential.py +696 -0
- synkit/Chem/Mapper/validation/__init__.py +1 -0
- synkit/Chem/Mapper/validation/aam_validator.py +442 -0
- synkit/Chem/Mapper/validation/annotations.py +274 -0
- synkit/Chem/Mapper/validation/bonds.py +124 -0
- synkit/Chem/Mapper/validation/cohorts.py +72 -0
- synkit/Chem/Mapper/validation/identifiability.py +150 -0
- synkit/Chem/Mapper/validation/numerical_scope.py +36 -0
- synkit/Chem/Mapper/validation/orbits.py +137 -0
- synkit/Chem/Molecule/__init__.py +0 -0
- synkit/Chem/Molecule/_chirality_loci.py +165 -0
- synkit/Chem/Molecule/_chirality_types.py +231 -0
- synkit/Chem/Molecule/_helical_loci.py +167 -0
- synkit/Chem/Molecule/_stereo_axis_evidence.py +202 -0
- synkit/Chem/Molecule/_stereo_element_detection.py +193 -0
- synkit/Chem/Molecule/_stereo_orientation_constraints.py +511 -0
- synkit/Chem/Molecule/_tetrahedral_carriers.py +63 -0
- synkit/Chem/Molecule/atom_features.py +379 -0
- synkit/Chem/Molecule/chirality.py +1041 -0
- synkit/Chem/Molecule/cip_assignment.py +569 -0
- synkit/Chem/Molecule/cip_ranking.py +843 -0
- synkit/Chem/Molecule/coordinate_stereo.py +503 -0
- synkit/Chem/Molecule/derived_stereo_naming.py +165 -0
- synkit/Chem/Molecule/descriptors.py +452 -0
- synkit/Chem/Molecule/formula.py +249 -0
- synkit/Chem/Molecule/global_stereo.py +175 -0
- synkit/Chem/Molecule/graph_annotator.py +300 -0
- synkit/Chem/Molecule/standardize.py +817 -0
- synkit/Chem/Molecule/stereo_evidence.py +179 -0
- synkit/Chem/Molecule/stereo_perception.py +1032 -0
- synkit/Chem/Molecule/valence.py +123 -0
- synkit/Chem/Reaction/Mapper/__init__.py +44 -0
- synkit/Chem/Reaction/__init__.py +20 -0
- synkit/Chem/Reaction/aam_validator.py +5 -0
- synkit/Chem/Reaction/balance_check.py +138 -0
- synkit/Chem/Reaction/canon_rsmi.py +249 -0
- synkit/Chem/Reaction/cleaning.py +58 -0
- synkit/Chem/Reaction/deionize.py +199 -0
- synkit/Chem/Reaction/explicit_h_audit.py +232 -0
- synkit/Chem/Reaction/fix_aam.py +64 -0
- synkit/Chem/Reaction/neutralize.py +207 -0
- synkit/Chem/Reaction/radical_wildcard.py +224 -0
- synkit/Chem/Reaction/standardize.py +203 -0
- synkit/Chem/Reaction/tautomerize.py +205 -0
- synkit/Chem/__init__.py +1 -0
- synkit/Chem/utils.py +315 -0
- synkit/Data/__init__.py +0 -0
- synkit/Data/aldol.json.gz +1 -0
- synkit/Data/gen_partial_aam.py +147 -0
- synkit/Data/paracetamol.json.gz +1 -0
- synkit/Graph/Canon/__init__.py +16 -0
- synkit/Graph/Canon/_native/__init__.py +13 -0
- synkit/Graph/Canon/_native/build.py +93 -0
- synkit/Graph/Canon/_native/lib/synkit_canon.dll +0 -0
- synkit/Graph/Canon/_native/prepare.py +49 -0
- synkit/Graph/Canon/_native/runtime.py +140 -0
- synkit/Graph/Canon/_native/search.py +137 -0
- synkit/Graph/Canon/canon_algs.py +228 -0
- synkit/Graph/Canon/canon_graph.py +531 -0
- synkit/Graph/Canon/cpp/CMakeLists.txt +42 -0
- synkit/Graph/Canon/cpp/README.md +123 -0
- synkit/Graph/Canon/cpp/examples/canonical_graph.cpp +16 -0
- synkit/Graph/Canon/cpp/include/synkit_canon/canon.h +85 -0
- synkit/Graph/Canon/cpp/src/canonical.cpp +391 -0
- synkit/Graph/Canon/cpp/src/symmetry.h +83 -0
- synkit/Graph/Canon/cpp/tests/symmetry.cpp +93 -0
- synkit/Graph/Canon/exact.py +1020 -0
- synkit/Graph/Canon/exact_refinement.py +368 -0
- synkit/Graph/Canon/nauty.py +143 -0
- synkit/Graph/Context/__init__.py +0 -0
- synkit/Graph/Context/hier_context.py +244 -0
- synkit/Graph/Context/radius_expand.py +252 -0
- synkit/Graph/FG/__init__.py +19 -0
- synkit/Graph/FG/api.py +39 -0
- synkit/Graph/FG/audit.py +155 -0
- synkit/Graph/FG/catalog.py +919 -0
- synkit/Graph/FG/detector.py +288 -0
- synkit/Graph/FG/model.py +97 -0
- synkit/Graph/FG/recognizers.py +274 -0
- synkit/Graph/FG/ring_system.py +154 -0
- synkit/Graph/Feature/Descriptors/topology.py +857 -0
- synkit/Graph/Feature/Fingerprint/__init__.py +0 -0
- synkit/Graph/Feature/Fingerprint/wl_rxn_fps.py +222 -0
- synkit/Graph/Feature/__init__.py +5 -0
- synkit/Graph/Feature/graph_descriptors.py +323 -0
- synkit/Graph/Feature/graph_fps.py +96 -0
- synkit/Graph/Feature/graph_signature.py +239 -0
- synkit/Graph/Feature/hash_fps.py +133 -0
- synkit/Graph/Feature/morgan_fps.py +88 -0
- synkit/Graph/Feature/path_fps.py +81 -0
- synkit/Graph/Feature/wl_hash.py +134 -0
- synkit/Graph/Fusion/__init__.py +85 -0
- synkit/Graph/Fusion/candidate.py +559 -0
- synkit/Graph/Fusion/constructor.py +877 -0
- synkit/Graph/Fusion/identity.py +184 -0
- synkit/Graph/Fusion/interface.py +700 -0
- synkit/Graph/Fusion/search.py +241 -0
- synkit/Graph/Hyrogen/__init__.py +6 -0
- synkit/Graph/Hyrogen/_misc.py +591 -0
- synkit/Graph/Hyrogen/hcomplete.py +995 -0
- synkit/Graph/Hyrogen/hcomplete_legacy.py +368 -0
- synkit/Graph/Hyrogen/hcompletion_algorithms.py +713 -0
- synkit/Graph/Hyrogen/hextend.py +570 -0
- synkit/Graph/Hyrogen/hextend_legacy.py +215 -0
- synkit/Graph/ITS/__init__.py +4 -0
- synkit/Graph/ITS/its_builder.py +120 -0
- synkit/Graph/ITS/its_construction.py +719 -0
- synkit/Graph/ITS/its_decompose.py +572 -0
- synkit/Graph/ITS/its_destruction.py +331 -0
- synkit/Graph/ITS/its_expand.py +1251 -0
- synkit/Graph/ITS/its_relabel.py +187 -0
- synkit/Graph/ITS/its_reverter.py +356 -0
- synkit/Graph/ITS/normalize_aam.py +145 -0
- synkit/Graph/ITS/partial_its.py +238 -0
- synkit/Graph/ITS/rc_extractor.py +656 -0
- synkit/Graph/ITS/stereo.py +74 -0
- synkit/Graph/MTG/__init__.py +107 -0
- synkit/Graph/MTG/gluing.py +451 -0
- synkit/Graph/MTG/history.py +928 -0
- synkit/Graph/MTG/inventory.py +118 -0
- synkit/Graph/MTG/local.py +447 -0
- synkit/Graph/MTG/mcs_matcher.py +246 -0
- synkit/Graph/MTG/mtg.py +611 -0
- synkit/Graph/MTG/mtg_explore.py +74 -0
- synkit/Graph/MTG/observation.py +209 -0
- synkit/Graph/MTG/process.py +577 -0
- synkit/Graph/MTG/queries.py +66 -0
- synkit/Graph/MTG/realization.py +95 -0
- synkit/Graph/MTG/series_parallel.py +107 -0
- synkit/Graph/MTG/utils.py +424 -0
- synkit/Graph/Matcher/__init__.py +10 -0
- synkit/Graph/Matcher/approx_mcs.py +1264 -0
- synkit/Graph/Matcher/auto_est.py +736 -0
- synkit/Graph/Matcher/automorphism.py +314 -0
- synkit/Graph/Matcher/batch_cluster.py +224 -0
- synkit/Graph/Matcher/dedup_matches.py +247 -0
- synkit/Graph/Matcher/graph_cluster.py +191 -0
- synkit/Graph/Matcher/graph_matcher.py +312 -0
- synkit/Graph/Matcher/graph_morphism.py +421 -0
- synkit/Graph/Matcher/mcs_matcher.py +804 -0
- synkit/Graph/Matcher/multi_turbo_iso.py +186 -0
- synkit/Graph/Matcher/orbit.py +284 -0
- synkit/Graph/Matcher/partial_matcher.py +694 -0
- synkit/Graph/Matcher/sing.py +544 -0
- synkit/Graph/Matcher/subgraph_matcher.py +812 -0
- synkit/Graph/Matcher/turbo_iso.py +272 -0
- synkit/Graph/Matcher/wl_sel.py +537 -0
- synkit/Graph/Mech/__init__.py +26 -0
- synkit/Graph/Mech/conversion.py +1466 -0
- synkit/Graph/Mech/conversion_debug.py +237 -0
- synkit/Graph/Mech/electron_accounting.py +200 -0
- synkit/Graph/Mech/lwg_editor.py +406 -0
- synkit/Graph/Mech/lwg_ops.py +313 -0
- synkit/Graph/Morphism/__init__.py +99 -0
- synkit/Graph/Morphism/constraints.py +460 -0
- synkit/Graph/Morphism/llg.py +999 -0
- synkit/Graph/Morphism/morphism.py +349 -0
- synkit/Graph/Morphism/stereo.py +258 -0
- synkit/Graph/Morphism/stereo_morphism.py +383 -0
- synkit/Graph/Morphism/stereo_morphism_helpers.py +957 -0
- synkit/Graph/Morphism/stereo_morphism_types.py +117 -0
- synkit/Graph/Stereo/__init__.py +376 -0
- synkit/Graph/Stereo/_descriptor_core.py +207 -0
- synkit/Graph/Stereo/_descriptor_serialization.py +138 -0
- synkit/Graph/Stereo/canonical.py +648 -0
- synkit/Graph/Stereo/changes.py +964 -0
- synkit/Graph/Stereo/composition.py +391 -0
- synkit/Graph/Stereo/configured.py +946 -0
- synkit/Graph/Stereo/couplings.py +245 -0
- synkit/Graph/Stereo/descriptors.py +1030 -0
- synkit/Graph/Stereo/enumeration.py +597 -0
- synkit/Graph/Stereo/extended_descriptors.py +406 -0
- synkit/Graph/Stereo/global_configured.py +152 -0
- synkit/Graph/Stereo/global_stereo.py +304 -0
- synkit/Graph/Stereo/identity.py +648 -0
- synkit/Graph/Stereo/interchange.py +496 -0
- synkit/Graph/Stereo/legacy.py +460 -0
- synkit/Graph/Stereo/matching.py +899 -0
- synkit/Graph/Stereo/native.py +154 -0
- synkit/Graph/Stereo/orbits.py +668 -0
- synkit/Graph/Stereo/outcomes.py +99 -0
- synkit/Graph/Stereo/pairwise.py +350 -0
- synkit/Graph/Stereo/rdkit_adapter.py +662 -0
- synkit/Graph/Stereo/rdkit_identity.py +118 -0
- synkit/Graph/Stereo/rdkit_resonance.py +140 -0
- synkit/Graph/Stereo/reaction_interchange.py +266 -0
- synkit/Graph/Stereo/semantics.py +296 -0
- synkit/Graph/Stereo/supports.py +257 -0
- synkit/Graph/Stereo/wire.py +339 -0
- synkit/Graph/Wildcard/__init__.py +0 -0
- synkit/Graph/Wildcard/fuse_graph.py +156 -0
- synkit/Graph/Wildcard/graph_wc.py +303 -0
- synkit/Graph/Wildcard/its_merge.py +857 -0
- synkit/Graph/Wildcard/radwc.py +114 -0
- synkit/Graph/Wildcard/wc_matcher.py +576 -0
- synkit/Graph/Wildcard/wildcard.py +225 -0
- synkit/Graph/__init__.py +17 -0
- synkit/Graph/canon_graph.py +14 -0
- synkit/Graph/syn_graph.py +199 -0
- synkit/Graph/utils.py +324 -0
- synkit/IO/__init__.py +4 -0
- synkit/IO/chem_converter.py +1059 -0
- synkit/IO/combinatorial/__init__.py +8 -0
- synkit/IO/combinatorial/gml_to_graph.py +223 -0
- synkit/IO/combinatorial/graph_to_gml.py +280 -0
- synkit/IO/combinatorial/graph_to_smarts.py +186 -0
- synkit/IO/combinatorial/smarts_expander.py +147 -0
- synkit/IO/combinatorial/smarts_generalizer.py +133 -0
- synkit/IO/combinatorial/smarts_to_graph.py +179 -0
- synkit/IO/conversion.py +42 -0
- synkit/IO/data_io.py +269 -0
- synkit/IO/data_process.py +143 -0
- synkit/IO/debug.py +73 -0
- synkit/IO/gml_to_nx.py +150 -0
- synkit/IO/graph_to_mol.py +199 -0
- synkit/IO/mol_to_graph.py +1105 -0
- synkit/IO/mol_to_graph_chemistry.py +545 -0
- synkit/IO/nx_to_gml.py +209 -0
- synkit/IO/smiles_to_id.py +123 -0
- synkit/Mechanism/__init__.py +151 -0
- synkit/Mechanism/adapters.py +136 -0
- synkit/Mechanism/audit.py +323 -0
- synkit/Mechanism/benchmark.py +638 -0
- synkit/Mechanism/compatibility.py +13 -0
- synkit/Mechanism/drawing.py +85 -0
- synkit/Mechanism/electron_models.py +725 -0
- synkit/Mechanism/equivalence.py +521 -0
- synkit/Mechanism/evidence.py +262 -0
- synkit/Mechanism/interchange.py +141 -0
- synkit/Mechanism/model.py +918 -0
- synkit/Mechanism/neighbor_stereo.py +312 -0
- synkit/Mechanism/radical_data.py +740 -0
- synkit/Mechanism/replay.py +986 -0
- synkit/Mechanism/schema.py +264 -0
- synkit/Mechanism/stereo_state.py +416 -0
- synkit/Mechanism/symbols.py +91 -0
- synkit/Rule/Apply/__init__.py +35 -0
- synkit/Rule/Apply/conditions.py +45 -0
- synkit/Rule/Apply/dpo.py +998 -0
- synkit/Rule/Apply/rule_matcher.py +218 -0
- synkit/Rule/Apply/validation.py +354 -0
- synkit/Rule/Compose/__init__.py +106 -0
- synkit/Rule/Compose/_identity.py +43 -0
- synkit/Rule/Compose/composition.py +976 -0
- synkit/Rule/Compose/laws.py +439 -0
- synkit/Rule/Compose/search.py +771 -0
- synkit/Rule/Compose/synrule.py +170 -0
- synkit/Rule/Modify/__init__.py +0 -0
- synkit/Rule/Modify/implict_rule.py +56 -0
- synkit/Rule/Modify/longest_path.py +92 -0
- synkit/Rule/Modify/molecule_rule.py +115 -0
- synkit/Rule/Modify/prune_templates.py +78 -0
- synkit/Rule/Modify/rule_utils.py +194 -0
- synkit/Rule/Modify/strip_rule.py +97 -0
- synkit/Rule/__init__.py +28 -0
- synkit/Rule/generic_stereo.py +884 -0
- synkit/Rule/stereo_identity.py +271 -0
- synkit/Rule/syn_rule.py +1090 -0
- synkit/Synthesis/MSR/__init__.py +0 -0
- synkit/Synthesis/MSR/path_finder.py +239 -0
- synkit/Synthesis/Metrics/__init__.py +0 -0
- synkit/Synthesis/Metrics/_base.py +52 -0
- synkit/Synthesis/Metrics/_plot.py +129 -0
- synkit/Synthesis/Metrics/_ranking.py +179 -0
- synkit/Synthesis/RBL/__init__.py +80 -0
- synkit/Synthesis/RBL/engine.py +1249 -0
- synkit/Synthesis/RBL/matching.py +652 -0
- synkit/Synthesis/RBL/overlap.py +336 -0
- synkit/Synthesis/RBL/pipeline.py +376 -0
- synkit/Synthesis/RBL/policy.py +139 -0
- synkit/Synthesis/RBL/proof.py +370 -0
- synkit/Synthesis/RBL/reaction.py +506 -0
- synkit/Synthesis/RBL/state.py +169 -0
- synkit/Synthesis/RBL/validation.py +1060 -0
- synkit/Synthesis/Reactor/__init__.py +60 -0
- synkit/Synthesis/Reactor/core/__init__.py +1 -0
- synkit/Synthesis/Reactor/core/engine.py +967 -0
- synkit/Synthesis/Reactor/core/product.py +621 -0
- synkit/Synthesis/Reactor/core/rewrite.py +561 -0
- synkit/Synthesis/Reactor/core/strategy.py +44 -0
- synkit/Synthesis/Reactor/matching/__init__.py +1 -0
- synkit/Synthesis/Reactor/matching/mixin.py +920 -0
- synkit/Synthesis/Reactor/matching/policy.py +345 -0
- synkit/Synthesis/Reactor/matching/symmetry.py +309 -0
- synkit/Synthesis/Reactor/output/__init__.py +1 -0
- synkit/Synthesis/Reactor/output/deduplication.py +703 -0
- synkit/Synthesis/Reactor/output/policy.py +16 -0
- synkit/Synthesis/Reactor/output/serialization.py +485 -0
- synkit/Synthesis/Reactor/output/structural.py +893 -0
- synkit/Synthesis/Reactor/stereo/__init__.py +1 -0
- synkit/Synthesis/Reactor/stereo/assignment.py +35 -0
- synkit/Synthesis/Reactor/stereo/mixin.py +780 -0
- synkit/Synthesis/Reactor/variants/__init__.py +1 -0
- synkit/Synthesis/Reactor/variants/imbalanced.py +180 -0
- synkit/Synthesis/Reactor/variants/partial.py +84 -0
- synkit/Synthesis/Reactor/workflow/__init__.py +1 -0
- synkit/Synthesis/Reactor/workflow/batch.py +550 -0
- synkit/Synthesis/Reactor/workflow/benchmark.py +143 -0
- synkit/Synthesis/Reactor/workflow/postprocess.py +267 -0
- synkit/Synthesis/Reactor/workflow/rule_filter.py +210 -0
- synkit/Synthesis/__init__.py +0 -0
- synkit/Synthesis/reactor_utils.py +316 -0
- synkit/Utils/__init__.py +0 -0
- synkit/Utils/utils.py +172 -0
- synkit/Vis/__init__.py +91 -0
- synkit/Vis/crn/__init__.py +40 -0
- synkit/Vis/epd/__init__.py +20 -0
- synkit/Vis/epd/arrows.py +425 -0
- synkit/Vis/epd/chem.py +197 -0
- synkit/Vis/epd/constants.py +83 -0
- synkit/Vis/epd/layout.py +283 -0
- synkit/Vis/epd/mapping.py +51 -0
- synkit/Vis/epd/models.py +136 -0
- synkit/Vis/epd/render.py +543 -0
- synkit/Vis/epd/utils.py +108 -0
- synkit/Vis/epd/visualizer.py +811 -0
- synkit/Vis/graph_visualizer.py +375 -0
- synkit/Vis/its/__init__.py +19 -0
- synkit/Vis/its/drawer.py +615 -0
- synkit/Vis/its_drawer.py +35 -0
- synkit/Vis/molecule/__init__.py +31 -0
- synkit/Vis/molecule/drawer.py +563 -0
- synkit/Vis/molecule/reaction.py +285 -0
- synkit/Vis/molecule_drawer.py +33 -0
- synkit/Vis/mtg/__init__.py +17 -0
- synkit/Vis/mtg/drawer.py +769 -0
- synkit/Vis/mtg_drawer.py +34 -0
- synkit/Vis/pdf_writer.py +146 -0
- synkit/Vis/reaction/__init__.py +19 -0
- synkit/Vis/reaction/rule.py +141 -0
- synkit/Vis/reaction/rxn.py +532 -0
- synkit/Vis/reaction_drawer.py +41 -0
- synkit/Vis/space/__init__.py +17 -0
- synkit/Vis/space/chemical.py +80 -0
- synkit/Vis/space/embedding.py +87 -0
- synkit/Vis/vis_synedu/Vis/__init__.py +7 -0
- synkit/Vis/vis_synedu/Vis/dpo.py +862 -0
- synkit/Vis/vis_synedu/rxn_vis.py +377 -0
- synkit/Vis/vis_synedu/vis.py +501 -0
- synkit/Vis/visual_drawer.py +215 -0
- synkit/Vis/visual_model.py +520 -0
- synkit/__init__.py +3 -0
- synkit/_native.py +91 -0
- synkit/examples.py +50 -0
- synkit/version.py +23 -0
- synkit-1.6.5.dist-info/METADATA +156 -0
- synkit-1.6.5.dist-info/RECORD +636 -0
- synkit-1.6.5.dist-info/WHEEL +4 -0
- synkit-1.6.5.dist-info/licenses/LICENSE +21 -0
- synkit-1.6.5.dist-info/licenses/synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/vendor/nauty/COPYRIGHT +44 -0
- synkit-1.6.5.dist-info/licenses/synkit/Chem/Mapper/solvers/native/cpp/src/symmetry/vendor/nauty/LICENSE-2.0.txt +202 -0
|
@@ -0,0 +1,141 @@
|
|
|
1
|
+
"""
|
|
2
|
+
Exact mapping methods, enumeration, and optimality certificates.
|
|
3
|
+
|
|
4
|
+
Full-space search and kernel refinement are distinct workflows. PABS
|
|
5
|
+
(Propagation and Assignment-Bounded Search) selects Python propagation or
|
|
6
|
+
optional C++ full-space search. The kernel solvers optimize a reduced
|
|
7
|
+
uncertainty region supplied by the SLAP workflow. A LAP (linear assignment
|
|
8
|
+
problem) provides a bound or a matching step in several of these methods.
|
|
9
|
+
|
|
10
|
+
Submodules
|
|
11
|
+
----------
|
|
12
|
+
search
|
|
13
|
+
PABS public interface with explicit Python or C++ backend selection.
|
|
14
|
+
distance_search
|
|
15
|
+
Full atom-compatible distance enumeration, replay certificates, admissible
|
|
16
|
+
bounds, and the standalone small-graph exhaustive mapper.
|
|
17
|
+
kernel_solvers
|
|
18
|
+
WL/SLAP uncertainty-kernel extraction, orbital branching, optional MILP,
|
|
19
|
+
and enumeration within the supplied kernel restrictions.
|
|
20
|
+
pabs
|
|
21
|
+
Python reversible-domain propagation search and residual cost spectra.
|
|
22
|
+
native
|
|
23
|
+
Optional C++ search, canonicalization, orbit scheduling, and explicit
|
|
24
|
+
compilation of the adjacent ``native_distance.cpp`` source. Execution
|
|
25
|
+
requires a supplied library path.
|
|
26
|
+
assignment
|
|
27
|
+
Shared LAP domains, incremental solves, and integer primal-dual proofs.
|
|
28
|
+
seeds
|
|
29
|
+
Feasible-incumbent heuristics; these do not establish optimality.
|
|
30
|
+
hybrid, edit_support
|
|
31
|
+
Exact-backend selection and binary edit-support enumeration.
|
|
32
|
+
core, hydrogen, symmetry, certificate
|
|
33
|
+
Reference-component reduction, hydrogen lifting, permutation-group helpers,
|
|
34
|
+
and optimality-gap reporting.
|
|
35
|
+
|
|
36
|
+
Historical flat modules remain aliases to these canonical implementations.
|
|
37
|
+
"""
|
|
38
|
+
|
|
39
|
+
from .kernel_solvers.kernel import Kernel, extract_kernel, apply_kernel_solution
|
|
40
|
+
from .kernel_solvers.branching import KernelSolution, solve_kernel, solve_kernel_blockwise
|
|
41
|
+
from .distance_search.exhaustive import ExactResult, ExactMapper
|
|
42
|
+
from .certificate import Certificate, certify_result, certify_results_exact
|
|
43
|
+
from .kernel_solvers.enumerate import (
|
|
44
|
+
EnumerationResult,
|
|
45
|
+
canonical_mapping_key,
|
|
46
|
+
canonical_partial_mapping_key,
|
|
47
|
+
dedup_mappings_by_automorphism,
|
|
48
|
+
enumerate_kernel_optima,
|
|
49
|
+
enumerate_symmetry_distinct_optima,
|
|
50
|
+
)
|
|
51
|
+
from .distance_search.search import (
|
|
52
|
+
CertificateVerificationError,
|
|
53
|
+
DistanceEnumerationCertificate,
|
|
54
|
+
DistanceEnumerationResult,
|
|
55
|
+
EnumerationStatus,
|
|
56
|
+
ExactEnumerationLimitError,
|
|
57
|
+
enumerate_distance_mappings,
|
|
58
|
+
verify_distance_enumeration_certificate,
|
|
59
|
+
)
|
|
60
|
+
from .core import ITSComponentReduction, reduce_to_reference_its_components
|
|
61
|
+
from .hydrogen import (
|
|
62
|
+
HydrogenEnumerationResult,
|
|
63
|
+
HydrogenLiftSummary,
|
|
64
|
+
HydrogenTransferPlan,
|
|
65
|
+
enumerate_lgp_hydrogen_transfers,
|
|
66
|
+
enumerate_minimal_hydrogen_transfers,
|
|
67
|
+
summarize_minimal_hydrogen_lifts,
|
|
68
|
+
)
|
|
69
|
+
from .edit_support import (
|
|
70
|
+
BinaryEditBudget,
|
|
71
|
+
BinaryEditSupportResult,
|
|
72
|
+
binary_edit_budget,
|
|
73
|
+
enumerate_binary_edit_support_mappings,
|
|
74
|
+
)
|
|
75
|
+
from .hybrid import (
|
|
76
|
+
HybridBackend,
|
|
77
|
+
HybridBackendDecision,
|
|
78
|
+
enumerate_hybrid_distance_mappings,
|
|
79
|
+
)
|
|
80
|
+
from .pabs.propagation import PropagationConfig, enumerate_synister_cp_mappings
|
|
81
|
+
from .search import enumerate_pabs_mappings
|
|
82
|
+
from .pabs.multi_shell import enumerate_pabs_shells
|
|
83
|
+
|
|
84
|
+
from ..._compat import (
|
|
85
|
+
EXACT_MODULE_ALIASES as _EXACT_MODULE_ALIASES,
|
|
86
|
+
register_module_aliases as _register_module_aliases,
|
|
87
|
+
)
|
|
88
|
+
|
|
89
|
+
_register_module_aliases(__name__, _EXACT_MODULE_ALIASES)
|
|
90
|
+
|
|
91
|
+
__all__ = [
|
|
92
|
+
# kernel
|
|
93
|
+
"Kernel",
|
|
94
|
+
"extract_kernel",
|
|
95
|
+
"apply_kernel_solution",
|
|
96
|
+
# branching
|
|
97
|
+
"KernelSolution",
|
|
98
|
+
"solve_kernel",
|
|
99
|
+
"solve_kernel_blockwise",
|
|
100
|
+
# exhaustive
|
|
101
|
+
"ExactResult",
|
|
102
|
+
"ExactMapper",
|
|
103
|
+
# certificate
|
|
104
|
+
"Certificate",
|
|
105
|
+
"certify_result",
|
|
106
|
+
"certify_results_exact",
|
|
107
|
+
# enumerate
|
|
108
|
+
"EnumerationResult",
|
|
109
|
+
"canonical_mapping_key",
|
|
110
|
+
"canonical_partial_mapping_key",
|
|
111
|
+
"dedup_mappings_by_automorphism",
|
|
112
|
+
"enumerate_kernel_optima",
|
|
113
|
+
"enumerate_symmetry_distinct_optima",
|
|
114
|
+
# distance
|
|
115
|
+
"CertificateVerificationError",
|
|
116
|
+
"DistanceEnumerationCertificate",
|
|
117
|
+
"DistanceEnumerationResult",
|
|
118
|
+
"EnumerationStatus",
|
|
119
|
+
"ExactEnumerationLimitError",
|
|
120
|
+
"enumerate_distance_mappings",
|
|
121
|
+
"verify_distance_enumeration_certificate",
|
|
122
|
+
"ITSComponentReduction",
|
|
123
|
+
"reduce_to_reference_its_components",
|
|
124
|
+
"HydrogenEnumerationResult",
|
|
125
|
+
"HydrogenLiftSummary",
|
|
126
|
+
"HydrogenTransferPlan",
|
|
127
|
+
"enumerate_lgp_hydrogen_transfers",
|
|
128
|
+
"enumerate_minimal_hydrogen_transfers",
|
|
129
|
+
"summarize_minimal_hydrogen_lifts",
|
|
130
|
+
"BinaryEditBudget",
|
|
131
|
+
"BinaryEditSupportResult",
|
|
132
|
+
"binary_edit_budget",
|
|
133
|
+
"enumerate_binary_edit_support_mappings",
|
|
134
|
+
"HybridBackend",
|
|
135
|
+
"HybridBackendDecision",
|
|
136
|
+
"enumerate_hybrid_distance_mappings",
|
|
137
|
+
"PropagationConfig",
|
|
138
|
+
"enumerate_synister_cp_mappings",
|
|
139
|
+
"enumerate_pabs_mappings",
|
|
140
|
+
"enumerate_pabs_shells",
|
|
141
|
+
]
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"""Shared reversible LAP domains and bounded-integer assignment certificates."""
|
|
@@ -0,0 +1,113 @@
|
|
|
1
|
+
"""Integer primal--dual certificates for bounded quarter-lattice assignments.
|
|
2
|
+
|
|
3
|
+
The floating-point LAP routine supplies a candidate permutation, not a trusted
|
|
4
|
+
lower bound. Exact integer dual feasibility and equality certify optimality.
|
|
5
|
+
This module does not certify the surrounding graph-search arithmetic.
|
|
6
|
+
"""
|
|
7
|
+
|
|
8
|
+
from dataclasses import dataclass
|
|
9
|
+
from numbers import Integral
|
|
10
|
+
|
|
11
|
+
import numpy as np
|
|
12
|
+
from scipy.optimize import linear_sum_assignment
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
MAX_ORDER = 512
|
|
16
|
+
MAX_SCALED_ENTRY = 2**40
|
|
17
|
+
SCALE = 4
|
|
18
|
+
|
|
19
|
+
|
|
20
|
+
@dataclass(frozen=True)
|
|
21
|
+
class AssignmentCertificate:
|
|
22
|
+
"""All objective and potential values are scaled by four."""
|
|
23
|
+
|
|
24
|
+
permutation: tuple[int, ...]
|
|
25
|
+
row_potentials: tuple[int, ...]
|
|
26
|
+
column_potentials: tuple[int, ...]
|
|
27
|
+
scaled_objective: int
|
|
28
|
+
|
|
29
|
+
|
|
30
|
+
def scaled_lattice_costs(costs):
|
|
31
|
+
"""Validate the supported domain before any fixed-width integer algebra."""
|
|
32
|
+
array = np.asarray(costs, dtype=float)
|
|
33
|
+
if array.ndim != 2 or array.shape[0] != array.shape[1]:
|
|
34
|
+
raise ValueError("Assignment costs must be a square matrix")
|
|
35
|
+
if array.shape[0] > MAX_ORDER or not np.isfinite(array).all():
|
|
36
|
+
raise ValueError("Assignment certificate domain requires finite order <= 512")
|
|
37
|
+
if np.max(np.abs(array), initial=0) > MAX_SCALED_ENTRY / SCALE:
|
|
38
|
+
raise ValueError("Assignment entry exceeds the certified lattice range")
|
|
39
|
+
scaled = array * SCALE
|
|
40
|
+
if not np.equal(scaled, np.rint(scaled)).all():
|
|
41
|
+
raise ValueError("Assignment costs must lie on the quarter-integer lattice")
|
|
42
|
+
return scaled.astype(np.int64)
|
|
43
|
+
|
|
44
|
+
|
|
45
|
+
def verify_assignment_certificate(costs, certificate):
|
|
46
|
+
"""Check a candidate with Python integers, independent of LAP/dual search.
|
|
47
|
+
|
|
48
|
+
For every i,p, u[i]+v[p] <= C[i,p]. Equality of the feasible matching
|
|
49
|
+
objective and sum(u)+sum(v) then proves its minimum by weak duality.
|
|
50
|
+
Invalid certificates return False; unsupported cost matrices raise ValueError.
|
|
51
|
+
"""
|
|
52
|
+
matrix = scaled_lattice_costs(costs)
|
|
53
|
+
n = len(matrix)
|
|
54
|
+
if not isinstance(certificate, AssignmentCertificate):
|
|
55
|
+
return False
|
|
56
|
+
permutation = certificate.permutation
|
|
57
|
+
u, v = certificate.row_potentials, certificate.column_potentials
|
|
58
|
+
if not all(isinstance(value, tuple) for value in (permutation, u, v)):
|
|
59
|
+
return False
|
|
60
|
+
if len(permutation) != n or len(u) != n or len(v) != n:
|
|
61
|
+
return False
|
|
62
|
+
values = (*permutation, *u, *v, certificate.scaled_objective)
|
|
63
|
+
if any(isinstance(x, bool) or not isinstance(x, Integral) for x in values):
|
|
64
|
+
return False
|
|
65
|
+
if sorted(permutation) != list(range(n)):
|
|
66
|
+
return False
|
|
67
|
+
# Explicit Python-int operations avoid trusting fixed-width arithmetic
|
|
68
|
+
# when verifying an externally supplied, possibly malicious certificate.
|
|
69
|
+
primal = sum(int(matrix[i, p]) for i, p in enumerate(permutation))
|
|
70
|
+
dual = sum(map(int, u)) + sum(map(int, v))
|
|
71
|
+
if primal != int(certificate.scaled_objective) or primal != dual:
|
|
72
|
+
return False
|
|
73
|
+
return all(int(u[i]) + int(v[p]) <= int(matrix[i, p])
|
|
74
|
+
for i in range(n) for p in range(n))
|
|
75
|
+
|
|
76
|
+
|
|
77
|
+
def certified_lattice_assignment(costs):
|
|
78
|
+
"""Return a minimum assignment and an exact independently checkable proof.
|
|
79
|
+
|
|
80
|
+
For candidate permutation p define d[i,j] = C[i,p[j]]-C[i,p[i]].
|
|
81
|
+
A minimum matching has no negative alternating cycle. Synchronous
|
|
82
|
+
Bellman--Ford from an implicit zero-cost source finds potentials t with
|
|
83
|
+
t[j]-t[i] <= d[i,j]. Set u[i]=C[i,p[i]]-t[i], v[p[i]]=t[i].
|
|
84
|
+
|
|
85
|
+
With n<=512 and |C|<=2**40, each n-edge path has magnitude <=2**50;
|
|
86
|
+
all intermediate distance/difference additions fit signed int64. The
|
|
87
|
+
independent verifier uses unbounded Python integers. A bad LAP candidate
|
|
88
|
+
is refused rather than returned as an unsafe pruning bound.
|
|
89
|
+
"""
|
|
90
|
+
matrix = scaled_lattice_costs(costs)
|
|
91
|
+
n = len(matrix)
|
|
92
|
+
if not n:
|
|
93
|
+
return AssignmentCertificate((), (), (), 0)
|
|
94
|
+
rows, permutation = linear_sum_assignment(np.asarray(costs, dtype=float))
|
|
95
|
+
if list(rows) != list(range(n)) or sorted(permutation.tolist()) != list(range(n)):
|
|
96
|
+
raise ArithmeticError("LAP returned an invalid permutation")
|
|
97
|
+
matched = matrix[np.arange(n), permutation]
|
|
98
|
+
edges = matrix[:, permutation] - matched[:, None]
|
|
99
|
+
potentials = np.zeros(n, dtype=np.int64)
|
|
100
|
+
for _ in range(n-1):
|
|
101
|
+
updated = np.minimum(potentials, np.min(potentials[:, None] + edges, axis=0))
|
|
102
|
+
if np.array_equal(updated, potentials):
|
|
103
|
+
break
|
|
104
|
+
potentials = updated
|
|
105
|
+
row_dual = matched - potentials
|
|
106
|
+
column_dual = np.empty(n, dtype=np.int64)
|
|
107
|
+
column_dual[permutation] = potentials
|
|
108
|
+
certificate = AssignmentCertificate(
|
|
109
|
+
tuple(map(int, permutation)), tuple(map(int, row_dual)),
|
|
110
|
+
tuple(map(int, column_dual)), sum(map(int, matched)))
|
|
111
|
+
if not verify_assignment_certificate(costs, certificate):
|
|
112
|
+
raise ArithmeticError("LAP candidate failed exact primal-dual verification")
|
|
113
|
+
return certificate
|
|
@@ -0,0 +1,162 @@
|
|
|
1
|
+
"""Reversible assignment domains and exact AllDifferent support filtering.
|
|
2
|
+
|
|
3
|
+
For balanced domains, an unmatched edge belongs to a perfect matching exactly
|
|
4
|
+
when it lies on an alternating cycle. Strong components in the graph of matched
|
|
5
|
+
rows identify these cycles. Filtering uses no bond-preservation assumption.
|
|
6
|
+
"""
|
|
7
|
+
|
|
8
|
+
from __future__ import annotations
|
|
9
|
+
|
|
10
|
+
import numpy as np
|
|
11
|
+
from scipy.sparse import csr_matrix
|
|
12
|
+
from scipy.sparse.csgraph import connected_components, maximum_bipartite_matching
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
def bits(mask):
|
|
16
|
+
"""Yield set-bit indices without allocating a full Boolean vector."""
|
|
17
|
+
while mask:
|
|
18
|
+
bit = mask & -mask
|
|
19
|
+
yield bit.bit_length() - 1
|
|
20
|
+
mask ^= bit
|
|
21
|
+
|
|
22
|
+
|
|
23
|
+
class AssignmentDomains:
|
|
24
|
+
"""Candidate image bitsets with a reversible change trail."""
|
|
25
|
+
|
|
26
|
+
def __init__(self, masks):
|
|
27
|
+
self.masks = list(map(int, masks))
|
|
28
|
+
self.trail = []
|
|
29
|
+
self._supported_state = None
|
|
30
|
+
|
|
31
|
+
def checkpoint(self):
|
|
32
|
+
"""Return a token for exact restoration after a child search."""
|
|
33
|
+
return len(self.trail)
|
|
34
|
+
|
|
35
|
+
def intersect(self, row, permitted):
|
|
36
|
+
"""Restrict one domain and record only actual changes."""
|
|
37
|
+
previous = self.masks[row]
|
|
38
|
+
updated = previous & int(permitted)
|
|
39
|
+
if updated != previous:
|
|
40
|
+
self.trail.append((row, previous))
|
|
41
|
+
self.masks[row] = updated
|
|
42
|
+
return previous.bit_count() - updated.bit_count()
|
|
43
|
+
|
|
44
|
+
def restore(self, token):
|
|
45
|
+
"""Restore all domains changed since a checkpoint."""
|
|
46
|
+
while len(self.trail) > token:
|
|
47
|
+
row, previous = self.trail.pop()
|
|
48
|
+
self.masks[row] = previous
|
|
49
|
+
|
|
50
|
+
def matrix(self, rows, columns):
|
|
51
|
+
"""Return the current residual bipartite adjacency matrix."""
|
|
52
|
+
if not rows:
|
|
53
|
+
return np.empty((0, len(columns)), dtype=bool)
|
|
54
|
+
extent = max(
|
|
55
|
+
max(self.masks[row].bit_length() for row in rows),
|
|
56
|
+
max(columns, default=-1) + 1,
|
|
57
|
+
)
|
|
58
|
+
width = max(1, (extent + 7) // 8)
|
|
59
|
+
data = b"".join(self.masks[row].to_bytes(width, "little") for row in rows)
|
|
60
|
+
packed = np.frombuffer(data, dtype=np.uint8).reshape(len(rows), width)
|
|
61
|
+
return np.unpackbits(packed, axis=1, bitorder="little")[:, columns].astype(bool)
|
|
62
|
+
|
|
63
|
+
def _balanced_blocks(self, rows):
|
|
64
|
+
"""Recognize disjoint complete bipartite blocks with perfect support."""
|
|
65
|
+
blocks = {}
|
|
66
|
+
for row in rows:
|
|
67
|
+
mask = self.masks[row]
|
|
68
|
+
blocks[mask] = blocks.get(mask, 0) + 1
|
|
69
|
+
union = 0
|
|
70
|
+
for mask, count in blocks.items():
|
|
71
|
+
if mask.bit_count() != count or union & mask:
|
|
72
|
+
return False
|
|
73
|
+
union |= mask
|
|
74
|
+
return True
|
|
75
|
+
|
|
76
|
+
def restrict_matrix(self, rows, columns, allowed):
|
|
77
|
+
"""Convert a residual Boolean domain matrix to global bitsets in bulk."""
|
|
78
|
+
extent = max(columns, default=-1) + 1
|
|
79
|
+
images = np.zeros((len(rows), extent), dtype=bool)
|
|
80
|
+
images[:, columns] = allowed
|
|
81
|
+
packed = np.packbits(images, axis=1, bitorder="little")
|
|
82
|
+
return sum(
|
|
83
|
+
self.intersect(row, int.from_bytes(packed[i].tobytes(), "little"))
|
|
84
|
+
for i, row in enumerate(rows)
|
|
85
|
+
)
|
|
86
|
+
|
|
87
|
+
def propagate(self, rows, available, *, full=True, matching=None, cache=True):
|
|
88
|
+
"""Remove unsupported edges, returning feasibility and removed count.
|
|
89
|
+
|
|
90
|
+
Singleton propagation precedes a Hopcroft--Karp matching. The stronger
|
|
91
|
+
mode then removes edges outside every perfect matching using alternating
|
|
92
|
+
strong components. A False result is an exact Hall infeasibility claim.
|
|
93
|
+
"""
|
|
94
|
+
signature = (
|
|
95
|
+
tuple(rows),
|
|
96
|
+
int(available),
|
|
97
|
+
tuple(self.masks[row] for row in rows),
|
|
98
|
+
)
|
|
99
|
+
if full and cache and signature == self._supported_state:
|
|
100
|
+
return True, 0
|
|
101
|
+
feasible, removed = self._propagate(
|
|
102
|
+
rows, available, full=full, matching=matching
|
|
103
|
+
)
|
|
104
|
+
if full and cache and feasible:
|
|
105
|
+
self._supported_state = (
|
|
106
|
+
tuple(rows),
|
|
107
|
+
int(available),
|
|
108
|
+
tuple(self.masks[row] for row in rows),
|
|
109
|
+
)
|
|
110
|
+
return feasible, removed
|
|
111
|
+
|
|
112
|
+
def _propagate(self, rows, available, *, full, matching):
|
|
113
|
+
"""Perform singleton filtering followed by optional perfect support."""
|
|
114
|
+
removed = sum(self.intersect(row, available) for row in rows)
|
|
115
|
+
pending = [row for row in rows if self.masks[row].bit_count() == 1]
|
|
116
|
+
processed = set()
|
|
117
|
+
while pending:
|
|
118
|
+
row = pending.pop()
|
|
119
|
+
if row in processed:
|
|
120
|
+
continue
|
|
121
|
+
processed.add(row)
|
|
122
|
+
singleton = self.masks[row]
|
|
123
|
+
for other in rows:
|
|
124
|
+
if other == row or not self.masks[other] & singleton:
|
|
125
|
+
continue
|
|
126
|
+
removed += self.intersect(other, ~singleton)
|
|
127
|
+
if not self.masks[other]:
|
|
128
|
+
return False, removed
|
|
129
|
+
if self.masks[other].bit_count() == 1:
|
|
130
|
+
pending.append(other)
|
|
131
|
+
if any(not self.masks[row] for row in rows):
|
|
132
|
+
return False, removed
|
|
133
|
+
if not rows or not full:
|
|
134
|
+
return True, removed
|
|
135
|
+
columns = list(bits(available))
|
|
136
|
+
if len(rows) != len(columns):
|
|
137
|
+
return False, removed
|
|
138
|
+
# Disjoint balanced complete blocks need no matching/SCC calculation.
|
|
139
|
+
# This is common after atom-type or attained-profile filtering.
|
|
140
|
+
if self._balanced_blocks(rows):
|
|
141
|
+
return True, removed
|
|
142
|
+
feasible, filtered = self._filter_support(rows, columns, matching)
|
|
143
|
+
return feasible, removed + filtered
|
|
144
|
+
|
|
145
|
+
def _filter_support(self, rows, columns, matching):
|
|
146
|
+
"""Keep precisely the edges supported by a residual perfect matching."""
|
|
147
|
+
allowed = self.matrix(rows, columns)
|
|
148
|
+
if matching is None or not allowed[np.arange(len(rows)), matching].all():
|
|
149
|
+
matching = maximum_bipartite_matching(
|
|
150
|
+
csr_matrix(allowed), perm_type="column"
|
|
151
|
+
)
|
|
152
|
+
matching = np.asarray(matching, dtype=int)
|
|
153
|
+
if np.any(matching < 0):
|
|
154
|
+
return False, 0
|
|
155
|
+
owner = np.empty(len(rows), dtype=int)
|
|
156
|
+
owner[matching] = np.arange(len(rows))
|
|
157
|
+
_, component = connected_components(
|
|
158
|
+
csr_matrix(allowed[:, matching]), directed=True, connection="strong"
|
|
159
|
+
)
|
|
160
|
+
supported = allowed & (component[:, None] == component[owner][None, :])
|
|
161
|
+
removed = self.restrict_matrix(rows, columns, supported)
|
|
162
|
+
return True, removed
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
"""Independent bounded-integer verification of supported-domain LAP proofs."""
|
|
2
|
+
|
|
3
|
+
from numbers import Integral
|
|
4
|
+
|
|
5
|
+
import numpy as np
|
|
6
|
+
|
|
7
|
+
from .assignment_certificate import AssignmentCertificate
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
def verify_supported_assignment(costs, allowed, certificate):
|
|
11
|
+
"""Verify primal/dual equality and every allowed-edge dual inequality.
|
|
12
|
+
|
|
13
|
+
Matrix entries are at most 2**40 and potentials at most 2**50 in absolute
|
|
14
|
+
value; their differences fit int64. Objective sums use Python integers.
|
|
15
|
+
Unsupported edges do not constrain this domain-restricted assignment.
|
|
16
|
+
"""
|
|
17
|
+
matrix = np.asarray(costs)
|
|
18
|
+
domain = np.asarray(allowed, dtype=bool)
|
|
19
|
+
if (
|
|
20
|
+
matrix.ndim != 2
|
|
21
|
+
or matrix.shape[0] != matrix.shape[1]
|
|
22
|
+
or domain.shape != matrix.shape
|
|
23
|
+
):
|
|
24
|
+
return False
|
|
25
|
+
n = len(matrix)
|
|
26
|
+
if (
|
|
27
|
+
n > 512
|
|
28
|
+
or matrix.dtype.kind not in "iu"
|
|
29
|
+
or np.any(matrix < 0)
|
|
30
|
+
or np.max(matrix, initial=0) > 2**40
|
|
31
|
+
):
|
|
32
|
+
return False
|
|
33
|
+
if not isinstance(certificate, AssignmentCertificate):
|
|
34
|
+
return False
|
|
35
|
+
p, u, v = (
|
|
36
|
+
certificate.permutation,
|
|
37
|
+
certificate.row_potentials,
|
|
38
|
+
certificate.column_potentials,
|
|
39
|
+
)
|
|
40
|
+
if any(not isinstance(values, tuple) or len(values) != n for values in (p, u, v)):
|
|
41
|
+
return False
|
|
42
|
+
values = (*p, *u, *v, certificate.scaled_objective)
|
|
43
|
+
if any(isinstance(x, bool) or not isinstance(x, Integral) for x in values):
|
|
44
|
+
return False
|
|
45
|
+
if sorted(p) != list(range(n)) or any(abs(int(x)) > 2**50 for x in (*u, *v)):
|
|
46
|
+
return False
|
|
47
|
+
if not domain[np.arange(n), p].all():
|
|
48
|
+
return False
|
|
49
|
+
primal = sum(int(matrix[i, j]) for i, j in enumerate(p))
|
|
50
|
+
dual = sum(map(int, u)) + sum(map(int, v))
|
|
51
|
+
if primal != int(certificate.scaled_objective) or primal != dual:
|
|
52
|
+
return False
|
|
53
|
+
reduced = (
|
|
54
|
+
matrix.astype(np.int64)
|
|
55
|
+
- np.asarray(u, dtype=np.int64)[:, None]
|
|
56
|
+
- np.asarray(v, dtype=np.int64)[None, :]
|
|
57
|
+
)
|
|
58
|
+
return bool(np.all(reduced[domain] >= 0))
|