dense-evolution 8.3.1__tar.gz → 8.3.2__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/PKG-INFO +11 -6
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/README.md +8 -5
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/__init__.py +8 -1
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/circuits/__init__.py +7 -0
- dense_evolution-8.3.2/dense_evolution/circuits/arithmetic_qasm.py +227 -0
- dense_evolution-8.3.2/dense_evolution/circuits/shor.py +70 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/native_hf/basis.py +12 -1
- dense_evolution-8.3.2/dense_evolution/native_hf/scf.py +870 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution.egg-info/PKG-INFO +11 -6
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution.egg-info/SOURCES.txt +2 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution.egg-info/requires.txt +3 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/pyproject.toml +4 -1
- dense_evolution-8.3.1/dense_evolution/native_hf/scf.py +0 -404
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/autodiff.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/backends/__init__.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/backends/chunk/__init__.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/backends/chunk/_engine_imports.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/backends/chunk/circuit_chunker.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/backends/chunk/core.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/backends/chunk/disk_overflow.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/backends/chunk/geometry.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/backends/chunk/guard.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/backends/chunk/kernels.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/backends/mps.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/backends/statevector.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/chunk.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/circuits/arithmetic.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/circuits/compiler.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/circuits/diagram.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/circuits/gates.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/circuits/parser.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/circuits/postselect.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/circuits/qft.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/circuits/random_circuit.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/circuits/registry.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/circuits/topology.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/circuits/trotter.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/circuits/uccsd.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/cli.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/compiler.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/config.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/drawing.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/entropy.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/fermions.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/gates.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/harrison_tb.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/healing.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/interop/__init__.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/interop/qiskit_pennylane.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/measurement.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/mitigation/__init__.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/mitigation/healing.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/mitigation/kl_divergence.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/mitigation/magic_entropy.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/mitigation/magic_entropy_shadows.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/mitigation/renyi.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/mitigation/stabilizer_renyi_entropy.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/mitigation/zne.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/mps.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/native_hf/__init__.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/native_hf/assembly.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/native_hf/boys.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/native_hf/bridge.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/native_hf/cartesian.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/native_hf/coulomb.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/native_hf/differentiable.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/native_hf/gaussians.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/native_hf/kinetic.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/native_hf/libcint_bridge.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/native_hf/overlap.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/noise/__init__.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/noise/coherent_attack.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/noise/cosmic_ray.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/noise/density_matrix_channels.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/noise/differentiable.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/noise/kraus/__init__.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/noise/kraus/amplitude_damping.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/noise/kraus/bitflip.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/noise/kraus/combined.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/noise/kraus/depolarizing.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/noise/kraus/ideal.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/noise/kraus/phaseflip.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/noise/kraus_channels.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/noise/oscillating.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/noise/pink.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/observables.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/parser.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/physics/__init__.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/physics/entropy.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/physics/fermions.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/physics/observables.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/physics/qec.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/physics/spectral.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/physics/states.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/protocols/__init__.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/protocols/bb84.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/protocols/di_qkd_ghz.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/protocols/dicka_protocol2.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/qec.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/qft.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/qmmm/__init__.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/qmmm/ase_bridge.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/qmmm/forces.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/qmmm/propagation.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/qmmm/region.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/random_circuit.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/registry.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/simulator.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/solvers/__init__.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/solvers/autodiff.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/solvers/harrison_tb.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/solvers/vhd_tb.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/states.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/topology.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/trotter.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/utils/__init__.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/utils/drawing.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/utils/mass_decomposition.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/utils/measurement.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution/vhd_tb.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution.egg-info/dependency_links.txt +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution.egg-info/entry_points.txt +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/dense_evolution.egg-info/top_level.txt +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/license.md +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/research/local_site/__init__.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/research/local_site/app/__init__.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/research/local_site/app/server.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/setup.cfg +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/__init__.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/_gate_tables.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/band_structure.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/circuit_builder_component.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/circuit_diagram.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/crypto_protocols.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/engine.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/graphical_builder.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/hamiltonians.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/mass_decomposition_tool.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/mitigation.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/native_hf_diagnostics.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/noise_tools.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/qasm_library.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/qmmm.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/rag_tool.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/state_visuals.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/system_limits.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/vector_healing.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/visuals.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/vqe.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/dashboard/core/wormhole.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/ia_utils/__init__.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/ia_utils/adversarial_vector_attack.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/ia_utils/rag.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/ia_utils/vector_healing.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/mcp_server/__init__.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/mcp_server/client.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/mcp_server/config.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/mcp_server/models.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/mcp_server/molecules.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/mcp_server/server.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/mcp_server/tools/__init__.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/mcp_server/tools/chemistry_tools.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/mcp_server/tools/circuit_tools.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/mcp_server/tools/crypto_tools.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/mcp_server/tools/mitigation_tools.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/mcp_server/tools/noise_tools.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/mcp_server/tools/retrieval_tools.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/mcp_server/tools/system_tools.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/mcp_server/tools/wormhole_tools.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/mcp_server/utils/__init__.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/mcp_server/utils/cache.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/mcp_server/utils/images.py +0 -0
- {dense_evolution-8.3.1 → dense_evolution-8.3.2}/tools/mcp_server/utils/truncation.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: dense-evolution
|
|
3
|
-
Version: 8.3.
|
|
3
|
+
Version: 8.3.2
|
|
4
4
|
Summary: High-performance quantum simulation toolkit -- Statevector/MPS engines with JIT compilation, noise modeling, VQE, QEC, quantum chemistry, and agent-native tooling
|
|
5
5
|
Author-email: Salvatore Pennacchio <jtatopenn@libero.it>
|
|
6
6
|
License: Business Source License 1.1
|
|
@@ -46,6 +46,8 @@ Requires-Dist: qiskit>=1.0.0; extra == "qiskit"
|
|
|
46
46
|
Provides-Extra: pennylane
|
|
47
47
|
Requires-Dist: pennylane>=0.35.0; extra == "pennylane"
|
|
48
48
|
Requires-Dist: basis_set_exchange>=0.9; extra == "pennylane"
|
|
49
|
+
Provides-Extra: hf
|
|
50
|
+
Requires-Dist: basis_set_exchange>=0.9; extra == "hf"
|
|
49
51
|
Provides-Extra: stim
|
|
50
52
|
Requires-Dist: stim>=1.13.0; extra == "stim"
|
|
51
53
|
Provides-Extra: pymatching
|
|
@@ -99,7 +101,7 @@ Requires-Dist: rdkit>=2023.9.1; extra == "docs"
|
|
|
99
101
|
Dynamic: license-file
|
|
100
102
|
|
|
101
103
|
<p align="center">
|
|
102
|
-
<img src="docs/assets/banner.
|
|
104
|
+
<img src="docs/assets/banner.png" alt="Dense Evolution — NISQ quantum simulation toolkit, JAX-native" width="900">
|
|
103
105
|
</p>
|
|
104
106
|
|
|
105
107
|
|
|
@@ -111,8 +113,8 @@ Statevector/MPS engines with compilation, noise, VQE, QEC, chemistry, and agent-
|
|
|
111
113
|
<p align="center">
|
|
112
114
|
<img src="docs/assets/favicon.svg" width="32" alt=""><br>
|
|
113
115
|
<b>Download the Dense Evolution Dashboard (Streamlit)</b><br>
|
|
114
|
-
<a href="https://
|
|
115
|
-
<a href="https://
|
|
116
|
+
<a href="https://tatopenn-cell.github.io/Dense-Evolution/assets/installer/install-dashboard.bat">Windows (.bat)</a> ·
|
|
117
|
+
<a href="https://tatopenn-cell.github.io/Dense-Evolution/assets/installer/install-dashboard.sh">macOS / Linux (.sh)</a>
|
|
116
118
|
</p>
|
|
117
119
|
|
|
118
120
|
[](https://github.com/tatopenn-cell/Dense-Evolution/actions/workflows/ci.yml)
|
|
@@ -165,6 +167,9 @@ pip install dense-evolution[full]
|
|
|
165
167
|
pip install dense-evolution[qiskit]
|
|
166
168
|
pip install dense-evolution[pennylane]
|
|
167
169
|
|
|
170
|
+
# native Hartree-Fock (basis-set data)
|
|
171
|
+
pip install dense-evolution[hf]
|
|
172
|
+
|
|
168
173
|
# Composer's local kernel (see "Composer" below)
|
|
169
174
|
pip install dense-evolution[composer]
|
|
170
175
|
|
|
@@ -302,8 +307,8 @@ sim.run_chunk(circuit.to_tuples(), chunk_size_gates=500)
|
|
|
302
307
|
- **Anti-OOM `Chunk` engine.** Circuits too large for one array, split dynamically and sized off the real compute device's own free memory — with disk-backed overflow past even that ceiling. [Chunk guide](https://tatopenn-cell.github.io/Dense-Evolution/api/chunk/).
|
|
303
308
|
- **Real noise, real mitigation.** Stochastic Kraus channels, real-device noise imported from Qiskit backends, and Zero-Noise Extrapolation, with the shot budget split optimally across noise factors and a single-qubit Bloch-vector variant that always returns a valid state, to correct for it. [Noise](https://tatopenn-cell.github.io/Dense-Evolution/api/noise/) · [Mitigation](https://tatopenn-cell.github.io/Dense-Evolution/api/mitigation/) · [what noise/mitigation/healing each mean](https://tatopenn-cell.github.io/Dense-Evolution/concepts/).
|
|
304
309
|
- **Differentiable VQE, from scratch.** `circuit_to_energy_fn` is the same JAX-differentiable engine real molecular VQE runs on — real Hartree-Fock Hamiltonians, UCCSD/hardware-efficient ansätze, Adam optimization. [Autodiff](https://tatopenn-cell.github.io/Dense-Evolution/api/autodiff/).
|
|
305
|
-
- **libcint integrals on Windows, macOS and Linux.** `pip install dense-evolution` ships libcint compiled for each system: the full two-electron tensor of ethanol in 6-31G* in 0.32 s. [native_hf](https://tatopenn-cell.github.io/Dense-Evolution/api/native_hf/).
|
|
306
|
-
- **Reversible arithmetic.** Register adders, subtraction, comparisons and modular arithmetic up to modular exponentiation, applied as exact basis permutations and
|
|
310
|
+
- **libcint integrals on Windows, macOS and Linux.** `pip install dense-evolution` ships libcint compiled for each system: the full two-electron tensor of ethanol in 6-31G* in 0.32 s. Open-shell molecules with UHF and ROHF (`run_uhf`, `run_cuhf`). [native_hf](https://tatopenn-cell.github.io/Dense-Evolution/api/native_hf/).
|
|
311
|
+
- **Reversible arithmetic.** Register adders, subtraction, comparisons and modular arithmetic up to modular exponentiation, applied as exact basis permutations, and as OPENQASM 2.0 gate circuits (Cuccaro, Draper and Beauregard adders, controlled modular multiplication), up to Shor order finding with one control qubit. [Arithmetic](https://tatopenn-cell.github.io/Dense-Evolution/api/arithmetic/).
|
|
307
312
|
- **Postselection.** Keep the branch where a qubit is found in `|0>`, `|1>`, `|±>` or `|±i>`, with its probability. [Postselection](https://tatopenn-cell.github.io/Dense-Evolution/api/postselect/).
|
|
308
313
|
- **OpenQASM 2.0/3.0, both directions.** A real parser, plus Qiskit/PennyLane interop bridges. [QASM Parser](https://tatopenn-cell.github.io/Dense-Evolution/api/parser/) · [Interop](https://tatopenn-cell.github.io/Dense-Evolution/api/interop/).
|
|
309
314
|
- **Code-agnostic QEC decoding**, Majorana/Jordan-Wigner fermion mapping, from-scratch Hartree-Fock for elements outside PennyLane's own basis set, a traversable-wormhole-inspired teleportation protocol, and real QM/MM region partitioning (ring-safe BFS, Diffuse2Seg-derived relevance propagation) — see the [full API reference](https://tatopenn-cell.github.io/Dense-Evolution/api/) for all of it.
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
<p align="center">
|
|
2
|
-
<img src="docs/assets/banner.
|
|
2
|
+
<img src="docs/assets/banner.png" alt="Dense Evolution — NISQ quantum simulation toolkit, JAX-native" width="900">
|
|
3
3
|
</p>
|
|
4
4
|
|
|
5
5
|
|
|
@@ -11,8 +11,8 @@ Statevector/MPS engines with compilation, noise, VQE, QEC, chemistry, and agent-
|
|
|
11
11
|
<p align="center">
|
|
12
12
|
<img src="docs/assets/favicon.svg" width="32" alt=""><br>
|
|
13
13
|
<b>Download the Dense Evolution Dashboard (Streamlit)</b><br>
|
|
14
|
-
<a href="https://
|
|
15
|
-
<a href="https://
|
|
14
|
+
<a href="https://tatopenn-cell.github.io/Dense-Evolution/assets/installer/install-dashboard.bat">Windows (.bat)</a> ·
|
|
15
|
+
<a href="https://tatopenn-cell.github.io/Dense-Evolution/assets/installer/install-dashboard.sh">macOS / Linux (.sh)</a>
|
|
16
16
|
</p>
|
|
17
17
|
|
|
18
18
|
[](https://github.com/tatopenn-cell/Dense-Evolution/actions/workflows/ci.yml)
|
|
@@ -65,6 +65,9 @@ pip install dense-evolution[full]
|
|
|
65
65
|
pip install dense-evolution[qiskit]
|
|
66
66
|
pip install dense-evolution[pennylane]
|
|
67
67
|
|
|
68
|
+
# native Hartree-Fock (basis-set data)
|
|
69
|
+
pip install dense-evolution[hf]
|
|
70
|
+
|
|
68
71
|
# Composer's local kernel (see "Composer" below)
|
|
69
72
|
pip install dense-evolution[composer]
|
|
70
73
|
|
|
@@ -202,8 +205,8 @@ sim.run_chunk(circuit.to_tuples(), chunk_size_gates=500)
|
|
|
202
205
|
- **Anti-OOM `Chunk` engine.** Circuits too large for one array, split dynamically and sized off the real compute device's own free memory — with disk-backed overflow past even that ceiling. [Chunk guide](https://tatopenn-cell.github.io/Dense-Evolution/api/chunk/).
|
|
203
206
|
- **Real noise, real mitigation.** Stochastic Kraus channels, real-device noise imported from Qiskit backends, and Zero-Noise Extrapolation, with the shot budget split optimally across noise factors and a single-qubit Bloch-vector variant that always returns a valid state, to correct for it. [Noise](https://tatopenn-cell.github.io/Dense-Evolution/api/noise/) · [Mitigation](https://tatopenn-cell.github.io/Dense-Evolution/api/mitigation/) · [what noise/mitigation/healing each mean](https://tatopenn-cell.github.io/Dense-Evolution/concepts/).
|
|
204
207
|
- **Differentiable VQE, from scratch.** `circuit_to_energy_fn` is the same JAX-differentiable engine real molecular VQE runs on — real Hartree-Fock Hamiltonians, UCCSD/hardware-efficient ansätze, Adam optimization. [Autodiff](https://tatopenn-cell.github.io/Dense-Evolution/api/autodiff/).
|
|
205
|
-
- **libcint integrals on Windows, macOS and Linux.** `pip install dense-evolution` ships libcint compiled for each system: the full two-electron tensor of ethanol in 6-31G* in 0.32 s. [native_hf](https://tatopenn-cell.github.io/Dense-Evolution/api/native_hf/).
|
|
206
|
-
- **Reversible arithmetic.** Register adders, subtraction, comparisons and modular arithmetic up to modular exponentiation, applied as exact basis permutations and
|
|
208
|
+
- **libcint integrals on Windows, macOS and Linux.** `pip install dense-evolution` ships libcint compiled for each system: the full two-electron tensor of ethanol in 6-31G* in 0.32 s. Open-shell molecules with UHF and ROHF (`run_uhf`, `run_cuhf`). [native_hf](https://tatopenn-cell.github.io/Dense-Evolution/api/native_hf/).
|
|
209
|
+
- **Reversible arithmetic.** Register adders, subtraction, comparisons and modular arithmetic up to modular exponentiation, applied as exact basis permutations, and as OPENQASM 2.0 gate circuits (Cuccaro, Draper and Beauregard adders, controlled modular multiplication), up to Shor order finding with one control qubit. [Arithmetic](https://tatopenn-cell.github.io/Dense-Evolution/api/arithmetic/).
|
|
207
210
|
- **Postselection.** Keep the branch where a qubit is found in `|0>`, `|1>`, `|±>` or `|±i>`, with its probability. [Postselection](https://tatopenn-cell.github.io/Dense-Evolution/api/postselect/).
|
|
208
211
|
- **OpenQASM 2.0/3.0, both directions.** A real parser, plus Qiskit/PennyLane interop bridges. [QASM Parser](https://tatopenn-cell.github.io/Dense-Evolution/api/parser/) · [Interop](https://tatopenn-cell.github.io/Dense-Evolution/api/interop/).
|
|
209
212
|
- **Code-agnostic QEC decoding**, Majorana/Jordan-Wigner fermion mapping, from-scratch Hartree-Fock for elements outside PennyLane's own basis set, a traversable-wormhole-inspired teleportation protocol, and real QM/MM region partitioning (ring-safe BFS, Diffuse2Seg-derived relevance propagation) — see the [full API reference](https://tatopenn-cell.github.io/Dense-Evolution/api/) for all of it.
|
|
@@ -50,6 +50,11 @@ from .circuits.arithmetic import (
|
|
|
50
50
|
compare_registers, compare_constant,
|
|
51
51
|
add_registers_mod, add_constant_mod, multiply_add_mod, multiply_mod, power_mod,
|
|
52
52
|
)
|
|
53
|
+
from .circuits.arithmetic_qasm import (
|
|
54
|
+
cuccaro_adder_qasm, draper_adder_qasm, constant_adder_qasm, modular_constant_adder_qasm,
|
|
55
|
+
cmult_mod_qasm, controlled_ua_qasm,
|
|
56
|
+
)
|
|
57
|
+
from .circuits.shor import shor_order_finding
|
|
53
58
|
from .circuits.postselect import postselect
|
|
54
59
|
from .circuits.random_circuit import random_circuit
|
|
55
60
|
from .utils.drawing import draw_circuit
|
|
@@ -68,7 +73,7 @@ from .physics.qec import (pauli_commutes, compute_syndrome, erasure_aware_decode
|
|
|
68
73
|
peeling_decode, union_find_decode, matching_erasure_decode,
|
|
69
74
|
estimate_edge_probabilities_from_detection_events)
|
|
70
75
|
|
|
71
|
-
__version__ = "8.3.
|
|
76
|
+
__version__ = "8.3.2"
|
|
72
77
|
|
|
73
78
|
__all__ = [
|
|
74
79
|
"__version__",
|
|
@@ -84,6 +89,8 @@ __all__ = [
|
|
|
84
89
|
"add_registers", "subtract_registers", "add_constant",
|
|
85
90
|
"compare_registers", "compare_constant",
|
|
86
91
|
"add_registers_mod", "add_constant_mod", "multiply_add_mod", "multiply_mod", "power_mod",
|
|
92
|
+
"cuccaro_adder_qasm", "draper_adder_qasm", "constant_adder_qasm", "modular_constant_adder_qasm",
|
|
93
|
+
"cmult_mod_qasm", "controlled_ua_qasm", "shor_order_finding",
|
|
87
94
|
"postselect",
|
|
88
95
|
"pauli_rotation_ops", "trotter_evolve_ops", "continuous_pulse_evolve",
|
|
89
96
|
"continuous_dissipative_evolve",
|
|
@@ -10,6 +10,11 @@ from .arithmetic import (
|
|
|
10
10
|
compare_registers, compare_constant,
|
|
11
11
|
add_registers_mod, add_constant_mod, multiply_add_mod, multiply_mod, power_mod,
|
|
12
12
|
)
|
|
13
|
+
from .arithmetic_qasm import (
|
|
14
|
+
cuccaro_adder_qasm, draper_adder_qasm, constant_adder_qasm, modular_constant_adder_qasm,
|
|
15
|
+
cmult_mod_qasm, controlled_ua_qasm,
|
|
16
|
+
)
|
|
17
|
+
from .shor import shor_order_finding
|
|
13
18
|
from .postselect import postselect
|
|
14
19
|
from .random_circuit import random_circuit
|
|
15
20
|
from .trotter import pauli_rotation_ops, trotter_evolve_ops
|
|
@@ -24,6 +29,8 @@ __all__ = [
|
|
|
24
29
|
"add_registers", "subtract_registers", "add_constant",
|
|
25
30
|
"compare_registers", "compare_constant",
|
|
26
31
|
"add_registers_mod", "add_constant_mod", "multiply_add_mod", "multiply_mod", "power_mod",
|
|
32
|
+
"cuccaro_adder_qasm", "draper_adder_qasm", "constant_adder_qasm", "modular_constant_adder_qasm",
|
|
33
|
+
"cmult_mod_qasm", "controlled_ua_qasm", "shor_order_finding",
|
|
27
34
|
"postselect",
|
|
28
35
|
"random_circuit",
|
|
29
36
|
"pauli_rotation_ops", "trotter_evolve_ops",
|
|
@@ -0,0 +1,227 @@
|
|
|
1
|
+
"""
|
|
2
|
+
Reversible arithmetic as gate circuits, written as OPENQASM 2.0.
|
|
3
|
+
|
|
4
|
+
`arithmetic.py` applies each operation as a basis permutation
|
|
5
|
+
|x> -> |f(x)>: exact, but not a circuit. The functions here return the
|
|
6
|
+
gate-level circuits of the original papers as OPENQASM 2.0 text, to be read
|
|
7
|
+
with `QASMParser` and run, noised, counted or exported like any other
|
|
8
|
+
circuit. Each one is checked exhaustively against the matching permutation
|
|
9
|
+
in `arithmetic.py`.
|
|
10
|
+
|
|
11
|
+
Registers are separate `qreg` declarations, least significant bit first
|
|
12
|
+
(`b[0]` is the lowest bit), so the parser's flattened qubit list matches the
|
|
13
|
+
register lists `arithmetic.py` takes.
|
|
14
|
+
|
|
15
|
+
References
|
|
16
|
+
----------
|
|
17
|
+
Cuccaro, Draper, Kutin, Moulton, quant-ph/0410184 (ripple-carry adder).
|
|
18
|
+
Draper, quant-ph/0008033 (addition on a quantum computer, QFT adder).
|
|
19
|
+
Beauregard, quant-ph/0205095 (circuit for Shor's algorithm using 2n+3 qubits).
|
|
20
|
+
"""
|
|
21
|
+
import math
|
|
22
|
+
import re
|
|
23
|
+
|
|
24
|
+
__all__ = [
|
|
25
|
+
"cuccaro_adder_qasm", "draper_adder_qasm",
|
|
26
|
+
"constant_adder_qasm", "modular_constant_adder_qasm",
|
|
27
|
+
"cmult_mod_qasm", "controlled_ua_qasm",
|
|
28
|
+
]
|
|
29
|
+
|
|
30
|
+
_HEADER = 'OPENQASM 2.0;\ninclude "qelib1.inc";\n'
|
|
31
|
+
|
|
32
|
+
_MAJ = "gate maj c, b, a { cx a, b; cx a, c; ccx c, b, a; }\n"
|
|
33
|
+
_UMA = "gate uma c, b, a { ccx c, b, a; cx a, c; cx c, b; }\n"
|
|
34
|
+
|
|
35
|
+
|
|
36
|
+
def _check_n(n):
|
|
37
|
+
if int(n) != n or n < 1:
|
|
38
|
+
raise ValueError(f"n must be a positive integer, got {n!r}.")
|
|
39
|
+
|
|
40
|
+
|
|
41
|
+
def _qft(reg, m):
|
|
42
|
+
lines = []
|
|
43
|
+
for k in range(m - 1, -1, -1):
|
|
44
|
+
lines.append(f"h {reg}[{k}];")
|
|
45
|
+
for j in range(k - 1, -1, -1):
|
|
46
|
+
lines.append(f"cp({math.pi / 2 ** (k - j)!r}) {reg}[{j}], {reg}[{k}];")
|
|
47
|
+
return lines
|
|
48
|
+
|
|
49
|
+
|
|
50
|
+
def _iqft(reg, m):
|
|
51
|
+
lines = []
|
|
52
|
+
for k in range(m):
|
|
53
|
+
for j in range(k):
|
|
54
|
+
lines.append(f"cp({-math.pi / 2 ** (k - j)!r}) {reg}[{j}], {reg}[{k}];")
|
|
55
|
+
lines.append(f"h {reg}[{k}];")
|
|
56
|
+
return lines
|
|
57
|
+
|
|
58
|
+
|
|
59
|
+
def _ccp(theta, c1, c2, target):
|
|
60
|
+
return [f"cp({theta / 2!r}) {c2}, {target};", f"cx {c1}, {c2};",
|
|
61
|
+
f"cp({-theta / 2!r}) {c2}, {target};", f"cx {c1}, {c2};",
|
|
62
|
+
f"cp({theta / 2!r}) {c1}, {target};"]
|
|
63
|
+
|
|
64
|
+
|
|
65
|
+
def _phi_add(reg, m, c, controls=()):
|
|
66
|
+
lines = []
|
|
67
|
+
for k in range(m):
|
|
68
|
+
theta = 2 * math.pi * (c % 2 ** (k + 1)) / 2 ** (k + 1)
|
|
69
|
+
if theta == 0.0:
|
|
70
|
+
continue
|
|
71
|
+
target = f"{reg}[{k}]"
|
|
72
|
+
if not controls:
|
|
73
|
+
lines.append(f"p({theta!r}) {target};")
|
|
74
|
+
elif len(controls) == 1:
|
|
75
|
+
lines.append(f"cp({theta!r}) {controls[0]}, {target};")
|
|
76
|
+
else:
|
|
77
|
+
lines += _ccp(theta, controls[0], controls[1], target)
|
|
78
|
+
return lines
|
|
79
|
+
|
|
80
|
+
|
|
81
|
+
def _phi_add_mod(reg, m, c, N, t, controls=()):
|
|
82
|
+
msb = f"{reg}[{m - 1}]"
|
|
83
|
+
lines = _phi_add(reg, m, c, controls) + _phi_add(reg, m, -N)
|
|
84
|
+
lines += _iqft(reg, m) + [f"cx {msb}, {t};"] + _qft(reg, m)
|
|
85
|
+
lines += _phi_add(reg, m, N, (t,)) + _phi_add(reg, m, -c, controls)
|
|
86
|
+
lines += _iqft(reg, m) + [f"x {msb};", f"cx {msb}, {t};", f"x {msb};"] + _qft(reg, m)
|
|
87
|
+
return lines + _phi_add(reg, m, c, controls)
|
|
88
|
+
|
|
89
|
+
|
|
90
|
+
def _cmult(a, N, n, control):
|
|
91
|
+
lines = _qft("b", n + 1)
|
|
92
|
+
for i in range(n):
|
|
93
|
+
lines += _phi_add_mod("b", n + 1, (2 ** i * a) % N, N, "t[0]", (control, f"x[{i}]"))
|
|
94
|
+
return lines + _iqft("b", n + 1)
|
|
95
|
+
|
|
96
|
+
|
|
97
|
+
_ANGLE = re.compile(r"^(c?p)\((.+?)\) ")
|
|
98
|
+
|
|
99
|
+
|
|
100
|
+
def _inverse(lines):
|
|
101
|
+
return [_ANGLE.sub(lambda mt: f"{mt.group(1)}({-float(mt.group(2))!r}) ", line) for line in reversed(lines)]
|
|
102
|
+
|
|
103
|
+
|
|
104
|
+
def _check_modular(n, N):
|
|
105
|
+
_check_n(n)
|
|
106
|
+
if not 0 < N < 2 ** n:
|
|
107
|
+
raise ValueError(f"need 0 < N < 2^n = {2 ** n}, got N={N}.")
|
|
108
|
+
|
|
109
|
+
|
|
110
|
+
def cuccaro_adder_qasm(n):
|
|
111
|
+
"""
|
|
112
|
+
Ripple-carry adder |a, b, 0> -> |a, a + b, 0> of Cuccaro et al.
|
|
113
|
+
(quant-ph/0410184, Fig. 1-4): MAJ gates carry the sum up, UMA gates
|
|
114
|
+
undo them and write each sum bit.
|
|
115
|
+
|
|
116
|
+
Registers: `a[n]`, `b[n+1]` (b[n] receives the carry out, so the sum
|
|
117
|
+
never overflows) and one ancilla `x[1]`, initially 0 and returned to 0.
|
|
118
|
+
2n Toffoli gates and 4n + 1 CNOTs. Matches
|
|
119
|
+
`arithmetic.add_registers(sv, 2n + 2, a, b)`.
|
|
120
|
+
"""
|
|
121
|
+
_check_n(n)
|
|
122
|
+
lines = [f"qreg a[{n}];", f"qreg b[{n + 1}];", "qreg x[1];",
|
|
123
|
+
"maj x[0], b[0], a[0];"]
|
|
124
|
+
lines += [f"maj a[{i - 1}], b[{i}], a[{i}];" for i in range(1, n)]
|
|
125
|
+
lines.append(f"cx a[{n - 1}], b[{n}];")
|
|
126
|
+
lines += [f"uma a[{i - 1}], b[{i}], a[{i}];" for i in range(n - 1, 0, -1)]
|
|
127
|
+
lines.append("uma x[0], b[0], a[0];")
|
|
128
|
+
return _HEADER + _MAJ + _UMA + "\n".join(lines) + "\n"
|
|
129
|
+
|
|
130
|
+
|
|
131
|
+
def draper_adder_qasm(n):
|
|
132
|
+
"""
|
|
133
|
+
QFT adder |a, b> -> |a, a + b> of Draper (quant-ph/0008033): b is
|
|
134
|
+
taken to Fourier space, each bit of a adds its phase with controlled
|
|
135
|
+
rotations, and the inverse QFT brings the sum back. No ancilla, no
|
|
136
|
+
carry gates.
|
|
137
|
+
|
|
138
|
+
Registers: `a[n]`, `b[n+1]` (b[n] holds the carry, so the sum never
|
|
139
|
+
overflows). Matches `arithmetic.add_registers(sv, 2n + 1, a, b)`.
|
|
140
|
+
"""
|
|
141
|
+
_check_n(n)
|
|
142
|
+
m = n + 1
|
|
143
|
+
lines = [f"qreg a[{n}];", f"qreg b[{m}];"] + _qft("b", m)
|
|
144
|
+
for i in range(n):
|
|
145
|
+
lines += _phi_add("b", m, 2 ** i, (f"a[{i}]",))
|
|
146
|
+
lines += _iqft("b", m)
|
|
147
|
+
return _HEADER + "\n".join(lines) + "\n"
|
|
148
|
+
|
|
149
|
+
|
|
150
|
+
def constant_adder_qasm(c, n):
|
|
151
|
+
"""
|
|
152
|
+
Adds a classical integer, |b> -> |(b + c) mod 2^n>: Beauregard's
|
|
153
|
+
phiADD(c) (quant-ph/0205095, Fig. 3), one phase gate per qubit of b in
|
|
154
|
+
Fourier space, between a QFT and an inverse QFT.
|
|
155
|
+
|
|
156
|
+
Register: `b[n]`. Matches `arithmetic.add_constant(sv, n, b, c)`.
|
|
157
|
+
"""
|
|
158
|
+
_check_n(n)
|
|
159
|
+
lines = [f"qreg b[{n}];"] + _qft("b", n) + _phi_add("b", n, int(c)) + _iqft("b", n)
|
|
160
|
+
return _HEADER + "\n".join(lines) + "\n"
|
|
161
|
+
|
|
162
|
+
|
|
163
|
+
def modular_constant_adder_qasm(c, N, n):
|
|
164
|
+
"""
|
|
165
|
+
Modular addition of a classical integer, |b, 0> -> |(b + c) mod N, 0>
|
|
166
|
+
for 0 <= b < N and 0 <= c < N: Beauregard's phiADD(c)MOD(N)
|
|
167
|
+
(quant-ph/0205095, Fig. 5, here without the two controls), between a
|
|
168
|
+
QFT and an inverse QFT.
|
|
169
|
+
|
|
170
|
+
Registers: `b[n+1]` (one bit more than N needs, used as the sign of
|
|
171
|
+
b + c - N) and one ancilla `t[1]`, initially 0 and returned to 0.
|
|
172
|
+
Requires N < 2^n. On inputs with b < N it matches
|
|
173
|
+
`arithmetic.add_constant_mod(sv, n + 2, b[:n], c, N)`; inputs with
|
|
174
|
+
b >= N are outside the circuit's contract.
|
|
175
|
+
"""
|
|
176
|
+
c, N = int(c), int(N)
|
|
177
|
+
_check_modular(n, N)
|
|
178
|
+
if not 0 <= c < N:
|
|
179
|
+
raise ValueError(f"need 0 <= c < N, got c={c}, N={N}.")
|
|
180
|
+
m = n + 1
|
|
181
|
+
lines = [f"qreg b[{m}];", "qreg t[1];"] + _qft("b", m)
|
|
182
|
+
lines += _phi_add_mod("b", m, c, N, "t[0]") + _iqft("b", m)
|
|
183
|
+
return _HEADER + "\n".join(lines) + "\n"
|
|
184
|
+
|
|
185
|
+
|
|
186
|
+
def cmult_mod_qasm(a, N, n):
|
|
187
|
+
"""
|
|
188
|
+
Controlled modular multiply-add, |c, x, b, 0> -> |c, x, (b + a*x) mod N, 0>
|
|
189
|
+
when c = 1 and unchanged when c = 0, for 0 <= b < N: Beauregard's
|
|
190
|
+
CMULT(a)MOD(N) (quant-ph/0205095, Fig. 6), n doubly controlled
|
|
191
|
+
phiADD(2^i a mod N)MOD(N) gates (Fig. 5) controlled by c and x[i],
|
|
192
|
+
between a QFT and an inverse QFT on b.
|
|
193
|
+
|
|
194
|
+
Registers: `c[1]`, `x[n]`, `b[n+1]` (b[n] is the sign bit, 0 on input
|
|
195
|
+
and output) and one ancilla `t[1]`, initially 0 and returned to 0.
|
|
196
|
+
Requires N < 2^n. On inputs with b < N it matches
|
|
197
|
+
`arithmetic.multiply_add_mod(sv, 2n + 3, x, b[:n], a, N, controls=(c,))`.
|
|
198
|
+
"""
|
|
199
|
+
a, N = int(a), int(N)
|
|
200
|
+
_check_modular(n, N)
|
|
201
|
+
lines = ["qreg c[1];", f"qreg x[{n}];", f"qreg b[{n + 1}];", "qreg t[1];"]
|
|
202
|
+
return _HEADER + "\n".join(lines + _cmult(a % N, N, n, "c[0]")) + "\n"
|
|
203
|
+
|
|
204
|
+
|
|
205
|
+
def controlled_ua_qasm(a, N, n):
|
|
206
|
+
"""
|
|
207
|
+
Controlled modular multiplication in place, |c, x, 0, 0> ->
|
|
208
|
+
|c, (a*x) mod N, 0, 0> when c = 1, unchanged when c = 0, for 0 <= x < N
|
|
209
|
+
and gcd(a, N) = 1: Beauregard's controlled-U_a (quant-ph/0205095, Fig. 7).
|
|
210
|
+
CMULT(a)MOD(N) writes a*x into b, a controlled swap exchanges x and b,
|
|
211
|
+
and the inverse of CMULT(a^-1 mod N)MOD(N) clears b back to 0.
|
|
212
|
+
|
|
213
|
+
Registers as in `cmult_mod_qasm`: `c[1]`, `x[n]`, `b[n+1]`, `t[1]`, with
|
|
214
|
+
b and t starting and ending at 0: 2n + 3 qubits, the count of the paper.
|
|
215
|
+
Matches `arithmetic.multiply_mod(sv, 2n + 3, x, a, N, controls=(c,))` on
|
|
216
|
+
inputs with x < N and b = t = 0.
|
|
217
|
+
"""
|
|
218
|
+
a, N = int(a), int(N)
|
|
219
|
+
_check_modular(n, N)
|
|
220
|
+
if math.gcd(a, N) != 1:
|
|
221
|
+
raise ValueError(f"a={a} has no inverse modulo N={N}.")
|
|
222
|
+
swap = []
|
|
223
|
+
for i in range(n):
|
|
224
|
+
swap += [f"cx b[{i}], x[{i}];", f"ccx c[0], x[{i}], b[{i}];", f"cx b[{i}], x[{i}];"]
|
|
225
|
+
lines = ["qreg c[1];", f"qreg x[{n}];", f"qreg b[{n + 1}];", "qreg t[1];"]
|
|
226
|
+
lines += _cmult(a % N, N, n, "c[0]") + swap + _inverse(_cmult(pow(a, -1, N), N, n, "c[0]"))
|
|
227
|
+
return _HEADER + "\n".join(lines) + "\n"
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
"""
|
|
2
|
+
Order finding for Shor's algorithm with one control qubit (Beauregard,
|
|
3
|
+
quant-ph/0205095, Sect. 2.5, Fig. 8): 2n + 3 qubits in total.
|
|
4
|
+
|
|
5
|
+
The 2n control qubits of the textbook circuit are replaced by a single one,
|
|
6
|
+
measured and reset after each controlled multiplication; the inverse QFT is
|
|
7
|
+
done semiclassically, a phase gate on that qubit set by the outcomes already
|
|
8
|
+
measured, then a Hadamard and the measurement. Each controlled-U_{a^(2^k)}
|
|
9
|
+
is the gate circuit of `controlled_ua_qasm`.
|
|
10
|
+
"""
|
|
11
|
+
import numpy as np
|
|
12
|
+
|
|
13
|
+
from .arithmetic_qasm import controlled_ua_qasm
|
|
14
|
+
from .parser import QASMParser
|
|
15
|
+
|
|
16
|
+
__all__ = ["shor_order_finding"]
|
|
17
|
+
|
|
18
|
+
|
|
19
|
+
def _hadamard_on_first(sv):
|
|
20
|
+
return np.stack([sv[0] + sv[1], sv[0] - sv[1]]) / np.sqrt(2.0)
|
|
21
|
+
|
|
22
|
+
|
|
23
|
+
def shor_order_finding(a, N, rng=None, noise_model=None, p=0.0):
|
|
24
|
+
"""
|
|
25
|
+
One run of quantum order finding for a modulo N, returns
|
|
26
|
+
(y, m): a measured integer 0 <= y < 2^m with m = 2n, n = N.bit_length().
|
|
27
|
+
y / 2^m is close to s / r for the order r of a and a random s, so the
|
|
28
|
+
continued-fraction expansion of y / 2^m recovers r with good probability
|
|
29
|
+
(`fractions.Fraction(y, 2**m).limit_denominator(N)`).
|
|
30
|
+
|
|
31
|
+
Iteration k = m-1, ..., 0 prepares the control in |+>, applies
|
|
32
|
+
controlled-U_{a^(2^k) mod N} to the work register (initially |1>),
|
|
33
|
+
applies the phase -2 pi sum_l r_l / 2^(l-k+1) over the bits r_l already
|
|
34
|
+
measured, a Hadamard, then measures and resets the control.
|
|
35
|
+
|
|
36
|
+
With `noise_model` (any model of `NoiseModel.apply_to_sv`, e.g.
|
|
37
|
+
"depolarizing") and probability `p`, one stochastic trajectory of that
|
|
38
|
+
channel acts on every qubit after each controlled multiplication, before
|
|
39
|
+
the control is measured.
|
|
40
|
+
"""
|
|
41
|
+
from ..backends.statevector import DenseSVSimulator
|
|
42
|
+
from ..noise import NoiseModel
|
|
43
|
+
|
|
44
|
+
a, N = int(a), int(N)
|
|
45
|
+
n = N.bit_length()
|
|
46
|
+
m, nq = 2 * n, 2 * n + 3
|
|
47
|
+
rng = np.random.default_rng(rng)
|
|
48
|
+
sv = np.zeros((2, 2 ** (nq - 1)), dtype=np.complex128)
|
|
49
|
+
sv[0, 1 << (nq - 2)] = 1.0
|
|
50
|
+
bits = {}
|
|
51
|
+
for k in range(m - 1, -1, -1):
|
|
52
|
+
sv = _hadamard_on_first(sv)
|
|
53
|
+
ak = pow(a, 2 ** k, N)
|
|
54
|
+
if ak != 1:
|
|
55
|
+
circ = QASMParser().parse(controlled_ua_qasm(ak, N, n))
|
|
56
|
+
sim = DenseSVSimulator(nq)
|
|
57
|
+
sim.set_initial_state(sv.reshape(-1))
|
|
58
|
+
sim.run_circuit_jit(circ.to_tuples())
|
|
59
|
+
sv = np.asarray(sim.get_statevector()).reshape(2, -1)
|
|
60
|
+
if noise_model is not None and p > 0:
|
|
61
|
+
sv = np.asarray(NoiseModel.apply_to_sv(sv.reshape(-1).copy(), nq, noise_model, p, rng=rng)).reshape(2, -1)
|
|
62
|
+
phase = -2 * np.pi * sum(bits[l] / 2 ** (l - k + 1) for l in bits)
|
|
63
|
+
sv[1] *= np.exp(1j * phase)
|
|
64
|
+
sv = _hadamard_on_first(sv)
|
|
65
|
+
p1 = float(np.sum(np.abs(sv[1]) ** 2))
|
|
66
|
+
bits[k] = int(rng.random() < p1)
|
|
67
|
+
kept = sv[bits[k]] / np.sqrt(p1 if bits[k] else 1.0 - p1)
|
|
68
|
+
sv = np.stack([kept, np.zeros_like(kept)])
|
|
69
|
+
y = sum(r << (m - 1 - k) for k, r in bits.items())
|
|
70
|
+
return y, m
|
|
@@ -17,7 +17,6 @@ itself: N = 1/sqrt(<primitive|primitive>).
|
|
|
17
17
|
|
|
18
18
|
import dataclasses
|
|
19
19
|
|
|
20
|
-
import basis_set_exchange as bse
|
|
21
20
|
import jax
|
|
22
21
|
import jax.numpy as jnp
|
|
23
22
|
import numpy as np
|
|
@@ -77,7 +76,19 @@ def _contracted_shell_from_bse(shell: dict, center: jax.Array, atom_index: int)
|
|
|
77
76
|
return shells
|
|
78
77
|
|
|
79
78
|
|
|
79
|
+
def _bse():
|
|
80
|
+
try:
|
|
81
|
+
import basis_set_exchange
|
|
82
|
+
except ModuleNotFoundError as exc:
|
|
83
|
+
raise ModuleNotFoundError(
|
|
84
|
+
"dense_evolution.native_hf needs basis_set_exchange for basis-set data: "
|
|
85
|
+
"pip install dense-evolution[hf]"
|
|
86
|
+
) from exc
|
|
87
|
+
return basis_set_exchange
|
|
88
|
+
|
|
89
|
+
|
|
80
90
|
def load_element_shells(basis_name: str, atomic_number: int, center: jax.Array, atom_index: int) -> list[ContractedShell]:
|
|
91
|
+
bse = _bse()
|
|
81
92
|
data = bse.get_basis(basis_name, elements=[atomic_number])
|
|
82
93
|
electron_shells = data["elements"][str(atomic_number)]["electron_shells"]
|
|
83
94
|
|