ket-lang 0.9.2.dev1__tar.gz → 0.9.2.dev2__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.
- {ket_lang-0.9.2.dev1/src/ket_lang.egg-info → ket_lang-0.9.2.dev2}/PKG-INFO +1 -1
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/__init__.py +1 -1
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/base.py +3 -1
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/kbw.py +8 -1
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/Cargo.toml +2 -1
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/examples/grover.rs +2 -2
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/src/bitwise.rs +12 -4
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/src/c_api.rs +10 -1
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/src/dense.rs +80 -59
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/src/dense_gpu.rs +37 -39
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/src/dense_v2.rs +62 -54
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/src/lib.rs +27 -3
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/src/sparse.rs +50 -47
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2/src/ket_lang.egg-info}/PKG-INFO +1 -1
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/tests/test_u3_gate.py +2 -2
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/tests/test_unitaty_gate.py +2 -2
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/LICENSE +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/MANIFEST.in +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/README.md +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/pyproject.toml +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/setup.cfg +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/setup.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/amazon.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/__init__.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libket.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/__init__.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/.git +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/.gitignore +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/.gitlab-ci.yml +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/.pre-commit-config.yaml +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/CHANGELOG.md +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/LICENSE +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/LICENSES/Apache-2.0.txt +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/README.md +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/REUSE.toml +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/build.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/examples/grover_gpu.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/src/convert.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/src/error.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/kbw/src/quantum_execution.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/.git +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/.gitignore +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/.gitlab-ci.yml +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/.pre-commit-config.yaml +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/CHANGELOG.md +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/Cargo.toml +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/LICENSE +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/LICENSES/Apache-2.0.txt +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/README.md +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/REUSE.toml +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/build.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/examples/grover.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/examples/qft.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/c_api/error.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/c_api/execution.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/c_api/mod.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/c_api/objects.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/c_api/process.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/circuit.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/decompose/mod.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/decompose/network.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/decompose/su2.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/decompose/u2.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/decompose/util.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/decompose/x/c2to4x.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/decompose/x/mod.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/decompose/x/single_aux.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/decompose/x/v_chain.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/error.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/ex_arch.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/execution.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/graph.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/ir/gate.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/ir/hamiltonian.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/ir/instructions.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/ir/mod.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/ir/qubit.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/lib.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/mapping/allocation.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/mapping/graph.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/mapping/map.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/mapping/mcpe.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/mapping/mod.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/prelude.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/process/aux.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/process/ctrl.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/process/execution.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/process/measure.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/process/mod.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/process/util.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/libs/libket/src/util.rs +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/clib/wrapper.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/expv.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/gates.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/ibm.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/npsim.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/operations.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/quantumstate.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/quforge.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/qulib/__init__.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/qulib/gates.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/qulib/ham.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/qulib/math.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/qulib/oracle.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/qulib/prepare.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket/remote.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket_lang.egg-info/SOURCES.txt +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket_lang.egg-info/dependency_links.txt +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket_lang.egg-info/not-zip-safe +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket_lang.egg-info/requires.txt +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/src/ket_lang.egg-info/top_level.txt +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/tests/test_decompose.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/tests/test_grover.py +0 -0
- {ket_lang-0.9.2.dev1 → ket_lang-0.9.2.dev2}/tests/test_phase_estimation.py +0 -0
|
@@ -127,7 +127,9 @@ class Process(LibketProcess):
|
|
|
127
127
|
self,
|
|
128
128
|
execution_target: BatchExecution | LiveExecution | None = None,
|
|
129
129
|
num_qubits: Optional[int] = None,
|
|
130
|
-
simulator: Optional[
|
|
130
|
+
simulator: Optional[
|
|
131
|
+
Literal["sparse", "dense", "dense v2", "dense gpu", "dense cuda"]
|
|
132
|
+
] = None,
|
|
131
133
|
execution: Optional[Literal["live", "batch"]] = None,
|
|
132
134
|
gradient: bool = False,
|
|
133
135
|
**kwargs,
|
|
@@ -60,6 +60,7 @@ _SIMULATOR = {
|
|
|
60
60
|
"sparse": 1,
|
|
61
61
|
"dense v2": 2,
|
|
62
62
|
"dense gpu": 3,
|
|
63
|
+
"dense cuda": 4,
|
|
63
64
|
}
|
|
64
65
|
|
|
65
66
|
|
|
@@ -69,7 +70,13 @@ _CLASSICAL_SHADOWS = {"bias": (1, 1, 1), "samples": 1_000, "shots": 2048}
|
|
|
69
70
|
def get_simulator( # pylint: disable=too-many-arguments,too-many-positional-arguments
|
|
70
71
|
num_qubits: int,
|
|
71
72
|
execution: Literal["live", "batch"] = "live",
|
|
72
|
-
simulator: Literal[
|
|
73
|
+
simulator: Literal[
|
|
74
|
+
"sparse",
|
|
75
|
+
"dense",
|
|
76
|
+
"dense v2",
|
|
77
|
+
"dense gpu",
|
|
78
|
+
"dense cuda",
|
|
79
|
+
] = "sparse",
|
|
73
80
|
coupling_graph: list[tuple[int, int]] | None = None,
|
|
74
81
|
gradient: bool = False,
|
|
75
82
|
classical_shadows=None,
|
|
@@ -32,8 +32,9 @@ build-info = { version = "0.0.42", default-features = false, features = [] }
|
|
|
32
32
|
serde = { version = "1.0.228", features = ["derive"] }
|
|
33
33
|
serde_json = "1.0.145"
|
|
34
34
|
indexmap = "2.12.1"
|
|
35
|
+
num-traits = "0.2"
|
|
35
36
|
|
|
36
|
-
cubecl = { version = "0.8.1", features = ["wgpu"] }
|
|
37
|
+
cubecl = { version = "0.8.1", features = ["wgpu", "cuda"] }
|
|
37
38
|
|
|
38
39
|
[build-dependencies]
|
|
39
40
|
build-info-build = "0.0.42"
|
|
@@ -4,12 +4,12 @@
|
|
|
4
4
|
|
|
5
5
|
use std::f64::consts::{FRAC_PI_2, FRAC_PI_4};
|
|
6
6
|
|
|
7
|
-
use kbw::
|
|
7
|
+
use kbw::DenseV2Simulator;
|
|
8
8
|
use ket::prelude::*;
|
|
9
9
|
|
|
10
10
|
fn main() -> Result<(), KetError> {
|
|
11
11
|
let size = 12;
|
|
12
|
-
let (target, execution) =
|
|
12
|
+
let (target, execution) = DenseV2Simulator::configuration(size, false, None, None, None, false);
|
|
13
13
|
|
|
14
14
|
let mut process = Process::new(target, execution);
|
|
15
15
|
|
|
@@ -3,8 +3,20 @@
|
|
|
3
3
|
//
|
|
4
4
|
// SPDX-License-Identifier: Apache-2.0
|
|
5
5
|
|
|
6
|
+
use std::ops::{BitOrAssign, Shl};
|
|
7
|
+
|
|
6
8
|
use num::Integer;
|
|
7
9
|
|
|
10
|
+
pub(crate) fn get_ctrl_mask<T: Integer + BitOrAssign + Shl<usize, Output = T>>(
|
|
11
|
+
control: &[usize],
|
|
12
|
+
) -> T {
|
|
13
|
+
let mut control_mask = T::zero();
|
|
14
|
+
for c in control {
|
|
15
|
+
control_mask |= T::one() << *c;
|
|
16
|
+
}
|
|
17
|
+
control_mask
|
|
18
|
+
}
|
|
19
|
+
|
|
8
20
|
pub(crate) fn bit_flip(state: usize, index: usize) -> usize {
|
|
9
21
|
state ^ (1 << index)
|
|
10
22
|
}
|
|
@@ -24,10 +36,6 @@ pub(crate) fn is_one_at_vec(state: &[u64], target: usize) -> bool {
|
|
|
24
36
|
state[outer_index] & (1 << inner_index) != 0
|
|
25
37
|
}
|
|
26
38
|
|
|
27
|
-
pub(crate) fn ctrl_check(state: usize, control: &[usize]) -> bool {
|
|
28
|
-
control.iter().all(|control| is_one_at(state, *control))
|
|
29
|
-
}
|
|
30
|
-
|
|
31
39
|
pub(crate) fn ctrl_check_vec(state: &[u64], control: &[usize]) -> bool {
|
|
32
40
|
control.iter().all(|control| is_one_at_vec(state, *control))
|
|
33
41
|
}
|
|
@@ -4,7 +4,8 @@
|
|
|
4
4
|
// SPDX-License-Identifier: Apache-2.0
|
|
5
5
|
|
|
6
6
|
use crate::{
|
|
7
|
-
error::KBWError, DenseGPUSimulator, DenseSimulator, DenseV2Simulator,
|
|
7
|
+
error::KBWError, DenseCUDASimulator, DenseGPUSimulator, DenseSimulator, DenseV2Simulator,
|
|
8
|
+
SparseSimulator,
|
|
8
9
|
};
|
|
9
10
|
use env_logger::Builder;
|
|
10
11
|
use ket::prelude::ExecutionTarget;
|
|
@@ -129,6 +130,14 @@ pub unsafe extern "C" fn kbw_make_configuration(
|
|
|
129
130
|
classical_shadows,
|
|
130
131
|
gradient,
|
|
131
132
|
),
|
|
133
|
+
4 => DenseCUDASimulator::configuration(
|
|
134
|
+
num_qubits,
|
|
135
|
+
use_live,
|
|
136
|
+
coupling_graph,
|
|
137
|
+
sample_base,
|
|
138
|
+
classical_shadows,
|
|
139
|
+
gradient,
|
|
140
|
+
),
|
|
132
141
|
_ => return KBWError::InvalidSimulator.error_code(),
|
|
133
142
|
}));
|
|
134
143
|
|
|
@@ -3,30 +3,30 @@
|
|
|
3
3
|
//
|
|
4
4
|
// SPDX-License-Identifier: Apache-2.0
|
|
5
5
|
|
|
6
|
-
use crate::bitwise::*;
|
|
7
6
|
use crate::error::{KBWError, Result};
|
|
8
7
|
use crate::quantum_execution::{ExecutionFeatures, QuantumExecution};
|
|
8
|
+
use crate::{bitwise::*, FloatOps};
|
|
9
9
|
use itertools::Itertools;
|
|
10
10
|
use ket::execution::*;
|
|
11
11
|
use ket::process::DumpData;
|
|
12
12
|
use log::error;
|
|
13
|
-
use num::
|
|
13
|
+
use num::complex::Complex;
|
|
14
|
+
use num::{One, Zero};
|
|
14
15
|
use rand::distr::weighted::WeightedIndex;
|
|
15
16
|
use rand::prelude::*;
|
|
16
17
|
use rayon::prelude::*;
|
|
17
18
|
use serde::{Deserialize, Serialize};
|
|
18
|
-
use std::f64::consts::FRAC_1_SQRT_2;
|
|
19
19
|
|
|
20
20
|
#[derive(Serialize, Deserialize)]
|
|
21
|
-
pub struct Dense {
|
|
22
|
-
state_0: Vec<
|
|
23
|
-
state_1: Vec<
|
|
21
|
+
pub struct Dense<F: FloatOps> {
|
|
22
|
+
state_0: Vec<Complex<F>>,
|
|
23
|
+
state_1: Vec<Complex<F>>,
|
|
24
24
|
state: bool,
|
|
25
25
|
num_states: usize,
|
|
26
26
|
}
|
|
27
27
|
|
|
28
|
-
impl Dense {
|
|
29
|
-
fn get_states(&mut self) -> (&mut [
|
|
28
|
+
impl<F: FloatOps> Dense<F> {
|
|
29
|
+
fn get_states(&mut self) -> (&mut [Complex<F>], &mut [Complex<F>]) {
|
|
30
30
|
self.state = !self.state;
|
|
31
31
|
if self.state {
|
|
32
32
|
(&mut self.state_1, &mut self.state_0)
|
|
@@ -35,7 +35,7 @@ impl Dense {
|
|
|
35
35
|
}
|
|
36
36
|
}
|
|
37
37
|
|
|
38
|
-
fn get_current_state(&self) -> &[
|
|
38
|
+
fn get_current_state(&self) -> &[Complex<F>] {
|
|
39
39
|
if self.state {
|
|
40
40
|
&self.state_0
|
|
41
41
|
} else {
|
|
@@ -44,7 +44,7 @@ impl Dense {
|
|
|
44
44
|
}
|
|
45
45
|
}
|
|
46
46
|
|
|
47
|
-
impl QuantumExecution for Dense {
|
|
47
|
+
impl<F: FloatOps> QuantumExecution for Dense<F> {
|
|
48
48
|
fn new(num_qubits: usize) -> Result<Self> {
|
|
49
49
|
if num_qubits > 32 {
|
|
50
50
|
error!("dense implementation supports up to 32 qubits");
|
|
@@ -54,10 +54,10 @@ impl QuantumExecution for Dense {
|
|
|
54
54
|
let num_states = 1 << num_qubits;
|
|
55
55
|
let mut state_0 = Vec::new();
|
|
56
56
|
let mut state_1 = Vec::new();
|
|
57
|
-
state_0.resize(num_states,
|
|
58
|
-
state_1.resize(num_states,
|
|
57
|
+
state_0.resize(num_states, Complex::<F>::zero());
|
|
58
|
+
state_1.resize(num_states, Complex::<F>::zero());
|
|
59
59
|
|
|
60
|
-
state_0[0] =
|
|
60
|
+
state_0[0] = Complex::<F>::one();
|
|
61
61
|
|
|
62
62
|
Ok(Dense {
|
|
63
63
|
state: true,
|
|
@@ -70,11 +70,13 @@ impl QuantumExecution for Dense {
|
|
|
70
70
|
fn pauli_x(&mut self, target: usize, control: &[usize]) {
|
|
71
71
|
let (current_state, next_state) = self.get_states();
|
|
72
72
|
|
|
73
|
+
let ctrl_mask: usize = get_ctrl_mask(control);
|
|
74
|
+
|
|
73
75
|
next_state
|
|
74
76
|
.par_iter_mut()
|
|
75
77
|
.enumerate()
|
|
76
78
|
.for_each(|(state, amp)| {
|
|
77
|
-
*amp = current_state[if
|
|
79
|
+
*amp = current_state[if (state & ctrl_mask) == ctrl_mask {
|
|
78
80
|
bit_flip(state, target)
|
|
79
81
|
} else {
|
|
80
82
|
state
|
|
@@ -85,16 +87,18 @@ impl QuantumExecution for Dense {
|
|
|
85
87
|
fn pauli_y(&mut self, target: usize, control: &[usize]) {
|
|
86
88
|
let (current_state, next_state) = self.get_states();
|
|
87
89
|
|
|
90
|
+
let ctrl_mask: usize = get_ctrl_mask(control);
|
|
91
|
+
|
|
88
92
|
next_state
|
|
89
93
|
.par_iter_mut()
|
|
90
94
|
.enumerate()
|
|
91
95
|
.for_each(|(state, amp)| {
|
|
92
|
-
if
|
|
96
|
+
if (state & ctrl_mask) == ctrl_mask {
|
|
93
97
|
*amp = current_state[bit_flip(state, target)]
|
|
94
98
|
* if is_one_at(state, target) {
|
|
95
|
-
|
|
99
|
+
Complex::<F>::i()
|
|
96
100
|
} else {
|
|
97
|
-
-
|
|
101
|
+
-Complex::<F>::i()
|
|
98
102
|
};
|
|
99
103
|
} else {
|
|
100
104
|
*amp = current_state[state];
|
|
@@ -105,11 +109,13 @@ impl QuantumExecution for Dense {
|
|
|
105
109
|
fn pauli_z(&mut self, target: usize, control: &[usize]) {
|
|
106
110
|
let (current_state, next_state) = self.get_states();
|
|
107
111
|
|
|
112
|
+
let ctrl_mask: usize = get_ctrl_mask(control);
|
|
113
|
+
|
|
108
114
|
next_state
|
|
109
115
|
.par_iter_mut()
|
|
110
116
|
.enumerate()
|
|
111
117
|
.for_each(|(state, amp)| {
|
|
112
|
-
if
|
|
118
|
+
if (state & ctrl_mask) == ctrl_mask && is_one_at(state, target) {
|
|
113
119
|
*amp = -current_state[state];
|
|
114
120
|
} else {
|
|
115
121
|
*amp = current_state[state];
|
|
@@ -120,14 +126,16 @@ impl QuantumExecution for Dense {
|
|
|
120
126
|
fn hadamard(&mut self, target: usize, control: &[usize]) {
|
|
121
127
|
let (current_state, next_state) = self.get_states();
|
|
122
128
|
|
|
129
|
+
let ctrl_mask: usize = get_ctrl_mask(control);
|
|
130
|
+
|
|
123
131
|
next_state
|
|
124
132
|
.par_iter_mut()
|
|
125
133
|
.enumerate()
|
|
126
134
|
.for_each(|(state, amp)| {
|
|
127
|
-
if
|
|
128
|
-
*amp = current_state[bit_flip(state, target)] * FRAC_1_SQRT_2;
|
|
135
|
+
if (state & ctrl_mask) == ctrl_mask {
|
|
136
|
+
*amp = current_state[bit_flip(state, target)] * F::FRAC_1_SQRT_2();
|
|
129
137
|
} else {
|
|
130
|
-
*amp =
|
|
138
|
+
*amp = Complex::<F>::zero();
|
|
131
139
|
}
|
|
132
140
|
});
|
|
133
141
|
|
|
@@ -135,11 +143,11 @@ impl QuantumExecution for Dense {
|
|
|
135
143
|
.par_iter_mut()
|
|
136
144
|
.enumerate()
|
|
137
145
|
.for_each(|(state, amp)| {
|
|
138
|
-
if
|
|
146
|
+
if (state & ctrl_mask) == ctrl_mask {
|
|
139
147
|
*amp *= if is_one_at(state, target) {
|
|
140
|
-
-FRAC_1_SQRT_2
|
|
148
|
+
-F::FRAC_1_SQRT_2()
|
|
141
149
|
} else {
|
|
142
|
-
FRAC_1_SQRT_2
|
|
150
|
+
F::FRAC_1_SQRT_2()
|
|
143
151
|
};
|
|
144
152
|
}
|
|
145
153
|
});
|
|
@@ -155,13 +163,15 @@ impl QuantumExecution for Dense {
|
|
|
155
163
|
fn phase(&mut self, lambda: f64, target: usize, control: &[usize]) {
|
|
156
164
|
let (current_state, next_state) = self.get_states();
|
|
157
165
|
|
|
158
|
-
let phase =
|
|
166
|
+
let phase = Complex::<F>::exp(Complex::<F>::i() * F::from(lambda).unwrap());
|
|
167
|
+
|
|
168
|
+
let ctrl_mask: usize = get_ctrl_mask(control);
|
|
159
169
|
|
|
160
170
|
next_state
|
|
161
171
|
.par_iter_mut()
|
|
162
172
|
.enumerate()
|
|
163
173
|
.for_each(|(state, amp)| {
|
|
164
|
-
if
|
|
174
|
+
if (state & ctrl_mask) == ctrl_mask && is_one_at(state, target) {
|
|
165
175
|
*amp = current_state[state] * phase;
|
|
166
176
|
} else {
|
|
167
177
|
*amp = current_state[state];
|
|
@@ -172,17 +182,19 @@ impl QuantumExecution for Dense {
|
|
|
172
182
|
fn rx(&mut self, theta: f64, target: usize, control: &[usize]) {
|
|
173
183
|
let (current_state, next_state) = self.get_states();
|
|
174
184
|
|
|
175
|
-
let cons_theta_2 =
|
|
176
|
-
let sin_theta_2 = -
|
|
185
|
+
let cons_theta_2 = Complex::<F>::from(F::cos(F::from(theta / 2.0).unwrap()));
|
|
186
|
+
let sin_theta_2 = -Complex::<F>::i() * F::sin(F::from(theta / 2.0).unwrap());
|
|
187
|
+
|
|
188
|
+
let ctrl_mask: usize = get_ctrl_mask(control);
|
|
177
189
|
|
|
178
190
|
next_state
|
|
179
191
|
.par_iter_mut()
|
|
180
192
|
.enumerate()
|
|
181
193
|
.for_each(|(state, amp)| {
|
|
182
|
-
if
|
|
194
|
+
if (state & ctrl_mask) == ctrl_mask {
|
|
183
195
|
*amp = current_state[bit_flip(state, target)] * sin_theta_2;
|
|
184
196
|
} else {
|
|
185
|
-
*amp =
|
|
197
|
+
*amp = Complex::<F>::zero();
|
|
186
198
|
}
|
|
187
199
|
});
|
|
188
200
|
|
|
@@ -190,7 +202,7 @@ impl QuantumExecution for Dense {
|
|
|
190
202
|
.par_iter_mut()
|
|
191
203
|
.enumerate()
|
|
192
204
|
.for_each(|(state, amp)| {
|
|
193
|
-
if
|
|
205
|
+
if (state & ctrl_mask) == ctrl_mask {
|
|
194
206
|
*amp *= cons_theta_2;
|
|
195
207
|
}
|
|
196
208
|
});
|
|
@@ -206,15 +218,17 @@ impl QuantumExecution for Dense {
|
|
|
206
218
|
fn ry(&mut self, theta: f64, target: usize, control: &[usize]) {
|
|
207
219
|
let (current_state, next_state) = self.get_states();
|
|
208
220
|
|
|
209
|
-
let cons_theta_2 =
|
|
210
|
-
let p_sin_theta_2 =
|
|
221
|
+
let cons_theta_2 = Complex::<F>::from(F::cos(F::from(theta / 2.0).unwrap()));
|
|
222
|
+
let p_sin_theta_2 = Complex::<F>::from(F::sin(F::from(theta / 2.0).unwrap()));
|
|
211
223
|
let m_sin_theta_2 = -p_sin_theta_2;
|
|
212
224
|
|
|
225
|
+
let ctrl_mask: usize = get_ctrl_mask(control);
|
|
226
|
+
|
|
213
227
|
next_state
|
|
214
228
|
.par_iter_mut()
|
|
215
229
|
.enumerate()
|
|
216
230
|
.for_each(|(state, amp)| {
|
|
217
|
-
if
|
|
231
|
+
if (state & ctrl_mask) == ctrl_mask {
|
|
218
232
|
*amp = current_state[bit_flip(state, target)]
|
|
219
233
|
* if is_one_at(state, target) {
|
|
220
234
|
p_sin_theta_2
|
|
@@ -222,7 +236,7 @@ impl QuantumExecution for Dense {
|
|
|
222
236
|
m_sin_theta_2
|
|
223
237
|
};
|
|
224
238
|
} else {
|
|
225
|
-
*amp =
|
|
239
|
+
*amp = Complex::<F>::zero();
|
|
226
240
|
}
|
|
227
241
|
});
|
|
228
242
|
|
|
@@ -230,7 +244,7 @@ impl QuantumExecution for Dense {
|
|
|
230
244
|
.par_iter_mut()
|
|
231
245
|
.enumerate()
|
|
232
246
|
.for_each(|(state, amp)| {
|
|
233
|
-
if
|
|
247
|
+
if (state & ctrl_mask) == ctrl_mask {
|
|
234
248
|
*amp *= cons_theta_2;
|
|
235
249
|
}
|
|
236
250
|
});
|
|
@@ -246,14 +260,16 @@ impl QuantumExecution for Dense {
|
|
|
246
260
|
fn rz(&mut self, theta: f64, target: usize, control: &[usize]) {
|
|
247
261
|
let (current_state, next_state) = self.get_states();
|
|
248
262
|
|
|
249
|
-
let phase_0 =
|
|
250
|
-
let phase_1 =
|
|
263
|
+
let phase_0 = Complex::<F>::exp(Complex::<F>::i() * F::from(-theta / 2.0).unwrap());
|
|
264
|
+
let phase_1 = Complex::<F>::exp(Complex::<F>::i() * F::from(theta / 2.0).unwrap());
|
|
265
|
+
|
|
266
|
+
let ctrl_mask: usize = get_ctrl_mask(control);
|
|
251
267
|
|
|
252
268
|
next_state
|
|
253
269
|
.par_iter_mut()
|
|
254
270
|
.enumerate()
|
|
255
271
|
.for_each(|(state, amp)| {
|
|
256
|
-
if
|
|
272
|
+
if (state & ctrl_mask) == ctrl_mask {
|
|
257
273
|
*amp = current_state[state]
|
|
258
274
|
* if is_one_at(state, target) {
|
|
259
275
|
phase_1
|
|
@@ -269,26 +285,29 @@ impl QuantumExecution for Dense {
|
|
|
269
285
|
fn measure<R: Rng>(&mut self, target: usize, rng: &mut R) -> bool {
|
|
270
286
|
let (current_state, next_state) = self.get_states();
|
|
271
287
|
|
|
272
|
-
let p1:
|
|
288
|
+
let p1: F = current_state
|
|
273
289
|
.par_iter()
|
|
274
290
|
.enumerate()
|
|
275
291
|
.map(|(state, amp)| {
|
|
276
292
|
if is_one_at(state, target) {
|
|
277
293
|
amp.norm().powi(2)
|
|
278
294
|
} else {
|
|
279
|
-
|
|
295
|
+
F::zero()
|
|
280
296
|
}
|
|
281
297
|
})
|
|
282
298
|
.sum();
|
|
283
299
|
|
|
284
|
-
let p0 = match
|
|
285
|
-
p0 if p0 >=
|
|
286
|
-
_ =>
|
|
300
|
+
let p0 = match F::one() - p1 {
|
|
301
|
+
p0 if p0 >= F::zero() => p0,
|
|
302
|
+
_ => F::zero(),
|
|
287
303
|
};
|
|
288
304
|
|
|
289
|
-
let result = WeightedIndex::new([p0, p1
|
|
305
|
+
let result = WeightedIndex::new([p0.to_f64().unwrap(), p1.to_f64().unwrap()])
|
|
306
|
+
.unwrap()
|
|
307
|
+
.sample(rng)
|
|
308
|
+
== 1;
|
|
290
309
|
|
|
291
|
-
let p =
|
|
310
|
+
let p = F::one() / F::sqrt(if result { p1 } else { p0 });
|
|
292
311
|
|
|
293
312
|
next_state
|
|
294
313
|
.par_iter_mut()
|
|
@@ -297,7 +316,7 @@ impl QuantumExecution for Dense {
|
|
|
297
316
|
*amp = if is_one_at(state, target) == result {
|
|
298
317
|
current_state[state] * p
|
|
299
318
|
} else {
|
|
300
|
-
|
|
319
|
+
Complex::<F>::zero()
|
|
301
320
|
};
|
|
302
321
|
});
|
|
303
322
|
|
|
@@ -306,10 +325,10 @@ impl QuantumExecution for Dense {
|
|
|
306
325
|
|
|
307
326
|
fn dump(&mut self, qubits: &[usize]) -> DumpData {
|
|
308
327
|
let state = self.get_current_state();
|
|
309
|
-
let (basis_states, amplitudes_real, amplitudes_imag): (Vec<_>, Vec<
|
|
328
|
+
let (basis_states, amplitudes_real, amplitudes_imag): (Vec<_>, Vec<f64>, Vec<f64>) = state
|
|
310
329
|
.iter()
|
|
311
330
|
.enumerate()
|
|
312
|
-
.filter(|(_state, amp)| amp.norm() > 1e-15)
|
|
331
|
+
.filter(|(_state, amp)| amp.norm() > F::from(1e-15).unwrap())
|
|
313
332
|
.map(|(state, amp)| {
|
|
314
333
|
let state = qubits
|
|
315
334
|
.iter()
|
|
@@ -319,7 +338,11 @@ impl QuantumExecution for Dense {
|
|
|
319
338
|
.reduce(|a, b| a | b)
|
|
320
339
|
.unwrap_or(0);
|
|
321
340
|
|
|
322
|
-
(
|
|
341
|
+
(
|
|
342
|
+
Vec::from([state as u64]),
|
|
343
|
+
amp.re.to_f64().unwrap(),
|
|
344
|
+
amp.im.to_f64().unwrap(),
|
|
345
|
+
)
|
|
323
346
|
})
|
|
324
347
|
.multiunzip();
|
|
325
348
|
|
|
@@ -333,24 +356,22 @@ impl QuantumExecution for Dense {
|
|
|
333
356
|
fn clear(&mut self) {
|
|
334
357
|
self.state_0.clear();
|
|
335
358
|
self.state_1.clear();
|
|
336
|
-
self.state_0.resize(self.num_states,
|
|
337
|
-
self.state_1.resize(self.num_states,
|
|
338
|
-
self.state_0[0] =
|
|
359
|
+
self.state_0.resize(self.num_states, Complex::<F>::zero());
|
|
360
|
+
self.state_1.resize(self.num_states, Complex::<F>::zero());
|
|
361
|
+
self.state_0[0] = Complex::<F>::one();
|
|
339
362
|
self.state = true;
|
|
340
363
|
}
|
|
341
364
|
|
|
342
365
|
fn save(&self) -> Vec<u8> {
|
|
343
|
-
|
|
366
|
+
unimplemented!()
|
|
344
367
|
}
|
|
345
368
|
|
|
346
|
-
fn load(&mut self,
|
|
347
|
-
|
|
348
|
-
*self = simulator;
|
|
349
|
-
}
|
|
369
|
+
fn load(&mut self, _data: &[u8]) {
|
|
370
|
+
unimplemented!()
|
|
350
371
|
}
|
|
351
372
|
}
|
|
352
373
|
|
|
353
|
-
impl ExecutionFeatures for Dense {
|
|
374
|
+
impl<F: FloatOps> ExecutionFeatures for Dense<F> {
|
|
354
375
|
fn feature_measure() -> Capability {
|
|
355
376
|
Capability::Advanced
|
|
356
377
|
}
|