cirq-core 1.1.0.dev20221220224914__py3-none-any.whl → 1.2.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- cirq/__init__.py +8 -0
- cirq/_compat.py +29 -4
- cirq/_compat_test.py +24 -26
- cirq/_version.py +32 -1
- cirq/_version_test.py +1 -1
- cirq/circuits/_block_diagram_drawer_test.py +4 -3
- cirq/circuits/circuit.py +109 -63
- cirq/circuits/circuit_operation.py +2 -3
- cirq/circuits/circuit_operation_test.py +4 -4
- cirq/circuits/circuit_test.py +11 -0
- cirq/circuits/frozen_circuit.py +13 -1
- cirq/circuits/frozen_circuit_test.py +5 -1
- cirq/circuits/moment.py +39 -14
- cirq/circuits/moment_test.py +7 -0
- cirq/circuits/text_diagram_drawer.py +1 -1
- cirq/circuits/text_diagram_drawer_test.py +3 -7
- cirq/contrib/acquaintance/bipartite.py +1 -1
- cirq/contrib/acquaintance/devices.py +2 -2
- cirq/contrib/acquaintance/executor.py +5 -2
- cirq/contrib/acquaintance/gates.py +3 -2
- cirq/contrib/acquaintance/permutation.py +13 -2
- cirq/contrib/acquaintance/testing.py +3 -5
- cirq/contrib/paulistring/recombine.py +3 -6
- cirq/contrib/qasm_import/_parser.py +17 -21
- cirq/contrib/qasm_import/_parser_test.py +30 -45
- cirq/contrib/qcircuit/qcircuit_test.py +3 -7
- cirq/contrib/quantum_volume/quantum_volume.py +3 -3
- cirq/contrib/quimb/mps_simulator.py +1 -1
- cirq/contrib/quimb/state_vector.py +2 -0
- cirq/contrib/quirk/quirk_gate.py +1 -0
- cirq/contrib/svg/svg.py +4 -7
- cirq/contrib/svg/svg_test.py +29 -1
- cirq/devices/grid_qubit.py +26 -28
- cirq/devices/grid_qubit_test.py +21 -5
- cirq/devices/line_qubit.py +10 -12
- cirq/devices/line_qubit_test.py +9 -2
- cirq/devices/named_topologies.py +1 -1
- cirq/devices/noise_model.py +4 -1
- cirq/devices/superconducting_qubits_noise_properties.py +1 -3
- cirq/experiments/n_qubit_tomography.py +1 -1
- cirq/experiments/qubit_characterizations.py +2 -2
- cirq/experiments/single_qubit_readout_calibration.py +1 -1
- cirq/experiments/t2_decay_experiment.py +1 -1
- cirq/experiments/xeb_simulation_test.py +2 -2
- cirq/interop/quirk/cells/testing.py +1 -1
- cirq/json_resolver_cache.py +1 -0
- cirq/linalg/__init__.py +2 -0
- cirq/linalg/decompositions_test.py +4 -4
- cirq/linalg/diagonalize_test.py +5 -6
- cirq/linalg/transformations.py +72 -9
- cirq/linalg/transformations_test.py +23 -7
- cirq/ops/__init__.py +4 -0
- cirq/ops/arithmetic_operation.py +4 -6
- cirq/ops/classically_controlled_operation.py +10 -3
- cirq/ops/clifford_gate.py +1 -7
- cirq/ops/common_channels.py +21 -15
- cirq/ops/common_gate_families.py +2 -3
- cirq/ops/common_gates.py +48 -11
- cirq/ops/common_gates_test.py +4 -0
- cirq/ops/controlled_gate.py +44 -18
- cirq/ops/controlled_operation.py +13 -5
- cirq/ops/dense_pauli_string.py +14 -19
- cirq/ops/diagonal_gate.py +3 -4
- cirq/ops/eigen_gate.py +8 -10
- cirq/ops/eigen_gate_test.py +6 -0
- cirq/ops/gate_operation.py +11 -6
- cirq/ops/gate_operation_test.py +11 -2
- cirq/ops/gateset.py +2 -1
- cirq/ops/gateset_test.py +38 -5
- cirq/ops/global_phase_op.py +28 -2
- cirq/ops/global_phase_op_test.py +21 -0
- cirq/ops/identity.py +1 -1
- cirq/ops/kraus_channel_test.py +2 -2
- cirq/ops/linear_combinations.py +7 -6
- cirq/ops/linear_combinations_test.py +26 -10
- cirq/ops/matrix_gates.py +8 -4
- cirq/ops/matrix_gates_test.py +25 -3
- cirq/ops/measure_util.py +13 -5
- cirq/ops/measure_util_test.py +8 -2
- cirq/ops/measurement_gate.py +1 -1
- cirq/ops/measurement_gate_test.py +9 -4
- cirq/ops/mixed_unitary_channel_test.py +4 -4
- cirq/ops/named_qubit.py +2 -4
- cirq/ops/parity_gates.py +5 -1
- cirq/ops/parity_gates_test.py +6 -0
- cirq/ops/pauli_gates.py +9 -9
- cirq/ops/pauli_string.py +4 -2
- cirq/ops/pauli_string_raw_types.py +4 -11
- cirq/ops/pauli_string_test.py +13 -13
- cirq/ops/pauli_sum_exponential.py +6 -1
- cirq/ops/qubit_manager.py +97 -0
- cirq/ops/qubit_manager_test.py +66 -0
- cirq/ops/raw_types.py +75 -33
- cirq/ops/raw_types_test.py +34 -0
- cirq/ops/three_qubit_gates.py +16 -10
- cirq/ops/three_qubit_gates_test.py +4 -2
- cirq/ops/two_qubit_diagonal_gate.py +3 -3
- cirq/ops/wait_gate.py +1 -1
- cirq/protocols/__init__.py +1 -0
- cirq/protocols/act_on_protocol.py +3 -3
- cirq/protocols/act_on_protocol_test.py +5 -5
- cirq/protocols/apply_channel_protocol.py +9 -8
- cirq/protocols/apply_mixture_protocol.py +8 -8
- cirq/protocols/apply_mixture_protocol_test.py +1 -1
- cirq/protocols/apply_unitary_protocol.py +66 -19
- cirq/protocols/apply_unitary_protocol_test.py +50 -0
- cirq/protocols/circuit_diagram_info_protocol.py +7 -9
- cirq/protocols/decompose_protocol.py +167 -125
- cirq/protocols/decompose_protocol_test.py +132 -2
- cirq/protocols/has_stabilizer_effect_protocol.py +2 -1
- cirq/protocols/inverse_protocol.py +2 -2
- cirq/protocols/json_serialization_test.py +3 -3
- cirq/protocols/json_test_data/Linspace.json +20 -7
- cirq/protocols/json_test_data/Linspace.repr +4 -1
- cirq/protocols/json_test_data/Points.json +19 -8
- cirq/protocols/json_test_data/Points.repr +4 -1
- cirq/protocols/json_test_data/Result.repr_inward +1 -1
- cirq/protocols/json_test_data/ResultDict.repr +1 -1
- cirq/protocols/json_test_data/ResultDict.repr_inward +1 -1
- cirq/protocols/json_test_data/TrialResult.repr_inward +1 -1
- cirq/protocols/json_test_data/XPowGate.json +13 -5
- cirq/protocols/json_test_data/XPowGate.repr +1 -1
- cirq/protocols/json_test_data/ZPowGate.json +13 -5
- cirq/protocols/json_test_data/ZPowGate.repr +1 -1
- cirq/protocols/json_test_data/ZipLongest.json +19 -0
- cirq/protocols/json_test_data/ZipLongest.repr +1 -0
- cirq/protocols/json_test_data/spec.py +1 -0
- cirq/protocols/kraus_protocol.py +3 -4
- cirq/protocols/measurement_key_protocol.py +3 -1
- cirq/protocols/mixture_protocol.py +3 -2
- cirq/protocols/phase_protocol.py +3 -3
- cirq/protocols/pow_protocol.py +1 -2
- cirq/protocols/qasm.py +4 -4
- cirq/protocols/qid_shape_protocol.py +8 -8
- cirq/protocols/resolve_parameters.py +8 -3
- cirq/protocols/resolve_parameters_test.py +3 -3
- cirq/protocols/unitary_protocol.py +19 -11
- cirq/protocols/unitary_protocol_test.py +37 -0
- cirq/qis/channels.py +1 -1
- cirq/qis/clifford_tableau.py +4 -5
- cirq/qis/quantum_state_representation.py +7 -9
- cirq/qis/states.py +21 -13
- cirq/qis/states_test.py +7 -0
- cirq/sim/clifford/clifford_simulator.py +3 -3
- cirq/sim/density_matrix_simulation_state.py +2 -1
- cirq/sim/density_matrix_simulator.py +1 -1
- cirq/sim/density_matrix_simulator_test.py +9 -5
- cirq/sim/density_matrix_utils.py +7 -32
- cirq/sim/mux.py +2 -2
- cirq/sim/simulation_state.py +58 -18
- cirq/sim/simulation_state_base.py +5 -2
- cirq/sim/simulation_state_test.py +121 -9
- cirq/sim/simulation_utils.py +59 -0
- cirq/sim/simulation_utils_test.py +32 -0
- cirq/sim/simulator.py +2 -1
- cirq/sim/simulator_base_test.py +3 -3
- cirq/sim/sparse_simulator.py +1 -1
- cirq/sim/sparse_simulator_test.py +5 -5
- cirq/sim/state_vector.py +7 -36
- cirq/sim/state_vector_simulation_state.py +18 -1
- cirq/sim/state_vector_simulator.py +3 -2
- cirq/sim/state_vector_simulator_test.py +24 -2
- cirq/sim/state_vector_test.py +46 -15
- cirq/study/__init__.py +1 -0
- cirq/study/flatten_expressions.py +2 -2
- cirq/study/resolver.py +2 -0
- cirq/study/resolver_test.py +1 -1
- cirq/study/result.py +1 -1
- cirq/study/sweeps.py +103 -9
- cirq/study/sweeps_test.py +64 -0
- cirq/testing/__init__.py +4 -0
- cirq/testing/circuit_compare.py +15 -18
- cirq/testing/consistent_act_on.py +4 -4
- cirq/testing/consistent_controlled_gate_op_test.py +1 -1
- cirq/testing/consistent_decomposition.py +11 -2
- cirq/testing/consistent_decomposition_test.py +8 -1
- cirq/testing/consistent_protocols.py +2 -0
- cirq/testing/consistent_protocols_test.py +8 -4
- cirq/testing/consistent_qasm.py +8 -15
- cirq/testing/consistent_specified_has_unitary.py +1 -1
- cirq/testing/consistent_unitary.py +85 -0
- cirq/testing/consistent_unitary_test.py +96 -0
- cirq/testing/equivalent_repr_eval.py +10 -10
- cirq/testing/json.py +3 -3
- cirq/testing/logs.py +1 -1
- cirq/testing/order_tester.py +4 -5
- cirq/testing/random_circuit.py +3 -5
- cirq/testing/sample_gates.py +79 -0
- cirq/testing/sample_gates_test.py +59 -0
- cirq/transformers/__init__.py +2 -0
- cirq/transformers/analytical_decompositions/__init__.py +8 -0
- cirq/transformers/analytical_decompositions/pauli_string_decomposition.py +130 -0
- cirq/transformers/analytical_decompositions/pauli_string_decomposition_test.py +58 -0
- cirq/transformers/analytical_decompositions/quantum_shannon_decomposition.py +230 -0
- cirq/transformers/analytical_decompositions/quantum_shannon_decomposition_test.py +112 -0
- cirq/transformers/analytical_decompositions/three_qubit_decomposition_test.py +1 -3
- cirq/transformers/analytical_decompositions/two_qubit_to_fsim.py +1 -1
- cirq/transformers/expand_composite.py +1 -1
- cirq/transformers/heuristic_decompositions/gate_tabulation_math_utils.py +4 -4
- cirq/transformers/measurement_transformers.py +4 -4
- cirq/transformers/merge_single_qubit_gates.py +17 -4
- cirq/transformers/routing/route_circuit_cqc.py +2 -2
- cirq/transformers/stratify.py +125 -62
- cirq/transformers/stratify_test.py +20 -16
- cirq/transformers/transformer_api.py +1 -1
- cirq/transformers/transformer_primitives.py +3 -2
- cirq/transformers/transformer_primitives_test.py +11 -0
- cirq/value/abc_alt.py +3 -2
- cirq/value/abc_alt_test.py +1 -0
- cirq/value/classical_data.py +10 -10
- cirq/value/digits.py +2 -2
- cirq/value/linear_dict.py +18 -19
- cirq/value/product_state.py +7 -6
- cirq/value/value_equality_attr.py +2 -2
- cirq/vis/heatmap.py +1 -1
- cirq/vis/heatmap_test.py +2 -2
- cirq/work/collector.py +2 -2
- cirq/work/observable_measurement_data.py +5 -5
- cirq/work/observable_readout_calibration.py +3 -1
- cirq/work/observable_settings.py +1 -1
- cirq/work/pauli_sum_collector.py +9 -8
- cirq/work/sampler.py +2 -0
- cirq/work/zeros_sampler.py +2 -2
- {cirq_core-1.1.0.dev20221220224914.dist-info → cirq_core-1.2.0.dist-info}/METADATA +7 -15
- {cirq_core-1.1.0.dev20221220224914.dist-info → cirq_core-1.2.0.dist-info}/RECORD +228 -214
- {cirq_core-1.1.0.dev20221220224914.dist-info → cirq_core-1.2.0.dist-info}/WHEEL +1 -1
- {cirq_core-1.1.0.dev20221220224914.dist-info → cirq_core-1.2.0.dist-info}/LICENSE +0 -0
- {cirq_core-1.1.0.dev20221220224914.dist-info → cirq_core-1.2.0.dist-info}/top_level.txt +0 -0
cirq/linalg/transformations.py
CHANGED
|
@@ -29,6 +29,8 @@ from cirq.linalg import predicates
|
|
|
29
29
|
# user provides a different np.array([]) value.
|
|
30
30
|
RaiseValueErrorIfNotProvided: np.ndarray = np.array([])
|
|
31
31
|
|
|
32
|
+
_NPY_MAXDIMS = 32 # Should be changed once numpy/numpy#5744 is resolved.
|
|
33
|
+
|
|
32
34
|
|
|
33
35
|
def reflection_matrix_pow(reflection_matrix: np.ndarray, exponent: float):
|
|
34
36
|
"""Raises a matrix with two opposing eigenvalues to a power.
|
|
@@ -249,7 +251,7 @@ def targeted_conjugate_about(
|
|
|
249
251
|
tensor: np.ndarray,
|
|
250
252
|
target: np.ndarray,
|
|
251
253
|
indices: Sequence[int],
|
|
252
|
-
conj_indices: Sequence[int] = None,
|
|
254
|
+
conj_indices: Optional[Sequence[int]] = None,
|
|
253
255
|
buffer: Optional[np.ndarray] = None,
|
|
254
256
|
out: Optional[np.ndarray] = None,
|
|
255
257
|
) -> np.ndarray:
|
|
@@ -399,13 +401,13 @@ def partial_trace(tensor: np.ndarray, keep_indices: Sequence[int]) -> np.ndarray
|
|
|
399
401
|
ndim = tensor.ndim // 2
|
|
400
402
|
if not all(tensor.shape[i] == tensor.shape[i + ndim] for i in range(ndim)):
|
|
401
403
|
raise ValueError(
|
|
402
|
-
'Tensors must have shape (d_0,...,d_{{k-1}},d_0,...,'
|
|
403
|
-
'd_{{k-1}}) but had shape ({}).'
|
|
404
|
+
f'Tensors must have shape (d_0,...,d_{{k-1}},d_0,...,'
|
|
405
|
+
f'd_{{k-1}}) but had shape ({tensor.shape}).'
|
|
404
406
|
)
|
|
405
407
|
if not all(i < ndim for i in keep_indices):
|
|
406
408
|
raise ValueError(
|
|
407
|
-
'keep_indices were {} but must be in first half, '
|
|
408
|
-
'i.e. have index less that {}.'
|
|
409
|
+
f'keep_indices were {keep_indices} but must be in first half, '
|
|
410
|
+
f'i.e. have index less that {ndim}.'
|
|
409
411
|
)
|
|
410
412
|
keep_set = set(keep_indices)
|
|
411
413
|
keep_map = dict(zip(keep_indices, sorted(keep_indices)))
|
|
@@ -530,8 +532,8 @@ def sub_state_vector(
|
|
|
530
532
|
|
|
531
533
|
if not np.log2(state_vector.size).is_integer():
|
|
532
534
|
raise ValueError(
|
|
533
|
-
"Input state_vector of size {} does not represent a "
|
|
534
|
-
"state over qubits."
|
|
535
|
+
f"Input state_vector of size {state_vector.size} does not represent a "
|
|
536
|
+
"state over qubits."
|
|
535
537
|
)
|
|
536
538
|
|
|
537
539
|
n_qubits = int(np.log2(state_vector.size))
|
|
@@ -572,8 +574,7 @@ def sub_state_vector(
|
|
|
572
574
|
return default
|
|
573
575
|
|
|
574
576
|
raise EntangledStateError(
|
|
575
|
-
"Input state vector could not be factored into pure state over "
|
|
576
|
-
"indices {}".format(keep_indices)
|
|
577
|
+
f"Input state vector could not be factored into pure state over indices {keep_indices}"
|
|
577
578
|
)
|
|
578
579
|
|
|
579
580
|
|
|
@@ -746,3 +747,65 @@ def transpose_density_matrix_to_axis_order(t: np.ndarray, axes: Sequence[int]):
|
|
|
746
747
|
"""
|
|
747
748
|
axes = list(axes) + [i + len(axes) for i in axes]
|
|
748
749
|
return transpose_state_vector_to_axis_order(t, axes)
|
|
750
|
+
|
|
751
|
+
|
|
752
|
+
def _volumes(shape: Sequence[int]) -> List[int]:
|
|
753
|
+
r"""Returns a list of the volume spanned by each dimension.
|
|
754
|
+
|
|
755
|
+
Given a shape=[d_0, d_1, .., d_n] the volume spanned by each dimension is
|
|
756
|
+
volume[i] = `\prod_{j=i+1}^n d_j`
|
|
757
|
+
|
|
758
|
+
Args:
|
|
759
|
+
shape: Sequence of the size of each dimension.
|
|
760
|
+
|
|
761
|
+
Returns:
|
|
762
|
+
Sequence of the volume spanned of each dimension.
|
|
763
|
+
"""
|
|
764
|
+
volume = [0] * len(shape)
|
|
765
|
+
v = 1
|
|
766
|
+
for i in reversed(range(len(shape))):
|
|
767
|
+
volume[i] = v
|
|
768
|
+
v *= shape[i]
|
|
769
|
+
return volume
|
|
770
|
+
|
|
771
|
+
|
|
772
|
+
def _coordinates_from_index(idx: int, volume: Sequence[int]) -> Sequence[int]:
|
|
773
|
+
ret = []
|
|
774
|
+
for v in volume:
|
|
775
|
+
ret.append(idx // v)
|
|
776
|
+
idx %= v
|
|
777
|
+
return tuple(ret)
|
|
778
|
+
|
|
779
|
+
|
|
780
|
+
def _index_from_coordinates(s: Sequence[int], volume: Sequence[int]) -> int:
|
|
781
|
+
return np.dot(s, volume)
|
|
782
|
+
|
|
783
|
+
|
|
784
|
+
def transpose_flattened_array(t: np.ndarray, shape: Sequence[int], axes: Sequence[int]):
|
|
785
|
+
"""Transposes a flattened array.
|
|
786
|
+
|
|
787
|
+
Equivalent to np.transpose(t.reshape(shape), axes).reshape((-1,)).
|
|
788
|
+
|
|
789
|
+
Args:
|
|
790
|
+
t: flat array.
|
|
791
|
+
shape: the shape of `t` before flattening.
|
|
792
|
+
axes: permutation of range(len(shape)).
|
|
793
|
+
|
|
794
|
+
Returns:
|
|
795
|
+
Flattened transpose of `t`.
|
|
796
|
+
"""
|
|
797
|
+
if len(t.shape) != 1:
|
|
798
|
+
t = t.reshape((-1,))
|
|
799
|
+
cur_volume = _volumes(shape)
|
|
800
|
+
new_volume = _volumes([shape[i] for i in axes])
|
|
801
|
+
ret = np.zeros_like(t)
|
|
802
|
+
for idx in range(t.shape[0]):
|
|
803
|
+
cell = _coordinates_from_index(idx, cur_volume)
|
|
804
|
+
new_cell = [cell[i] for i in axes]
|
|
805
|
+
ret[_index_from_coordinates(new_cell, new_volume)] = t[idx]
|
|
806
|
+
return ret
|
|
807
|
+
|
|
808
|
+
|
|
809
|
+
def can_numpy_support_shape(shape: Sequence[int]) -> bool:
|
|
810
|
+
"""Returns whether numpy supports the given shape or not numpy/numpy#5744."""
|
|
811
|
+
return len(shape) <= _NPY_MAXDIMS
|
|
@@ -17,6 +17,7 @@ import pytest
|
|
|
17
17
|
|
|
18
18
|
import cirq
|
|
19
19
|
import cirq.testing
|
|
20
|
+
from cirq import linalg
|
|
20
21
|
|
|
21
22
|
|
|
22
23
|
def test_reflection_matrix_pow_consistent_results():
|
|
@@ -352,20 +353,20 @@ def test_sub_state_vector():
|
|
|
352
353
|
a = np.arange(4) / np.linalg.norm(np.arange(4))
|
|
353
354
|
b = (np.arange(8) + 3) / np.linalg.norm(np.arange(8) + 3)
|
|
354
355
|
c = (np.arange(16) + 1) / np.linalg.norm(np.arange(16) + 1)
|
|
355
|
-
state = np.kron(np.kron(a, b), c).reshape(2, 2, 2, 2, 2, 2, 2, 2, 2)
|
|
356
|
+
state = np.kron(np.kron(a, b), c).reshape((2, 2, 2, 2, 2, 2, 2, 2, 2))
|
|
356
357
|
|
|
357
358
|
assert cirq.equal_up_to_global_phase(cirq.sub_state_vector(a, [0, 1], atol=1e-8), a)
|
|
358
359
|
assert cirq.equal_up_to_global_phase(cirq.sub_state_vector(b, [0, 1, 2], atol=1e-8), b)
|
|
359
360
|
assert cirq.equal_up_to_global_phase(cirq.sub_state_vector(c, [0, 1, 2, 3], atol=1e-8), c)
|
|
360
361
|
|
|
361
362
|
assert cirq.equal_up_to_global_phase(
|
|
362
|
-
cirq.sub_state_vector(state, [0, 1], atol=1e-15), a.reshape(2, 2)
|
|
363
|
+
cirq.sub_state_vector(state, [0, 1], atol=1e-15), a.reshape((2, 2))
|
|
363
364
|
)
|
|
364
365
|
assert cirq.equal_up_to_global_phase(
|
|
365
|
-
cirq.sub_state_vector(state, [2, 3, 4], atol=1e-15), b.reshape(2, 2, 2)
|
|
366
|
+
cirq.sub_state_vector(state, [2, 3, 4], atol=1e-15), b.reshape((2, 2, 2))
|
|
366
367
|
)
|
|
367
368
|
assert cirq.equal_up_to_global_phase(
|
|
368
|
-
cirq.sub_state_vector(state, [5, 6, 7, 8], atol=1e-15), c.reshape(2, 2, 2, 2)
|
|
369
|
+
cirq.sub_state_vector(state, [5, 6, 7, 8], atol=1e-15), c.reshape((2, 2, 2, 2))
|
|
369
370
|
)
|
|
370
371
|
|
|
371
372
|
# Output state vector conforms to the shape of the input state vector.
|
|
@@ -485,15 +486,15 @@ def test_partial_trace_of_state_vector_as_mixture_pure_result():
|
|
|
485
486
|
|
|
486
487
|
assert mixtures_equal(
|
|
487
488
|
cirq.partial_trace_of_state_vector_as_mixture(state, [0, 1], atol=1e-8),
|
|
488
|
-
((1.0, a.reshape(2, 2)),),
|
|
489
|
+
((1.0, a.reshape((2, 2))),),
|
|
489
490
|
)
|
|
490
491
|
assert mixtures_equal(
|
|
491
492
|
cirq.partial_trace_of_state_vector_as_mixture(state, [2, 3, 4], atol=1e-8),
|
|
492
|
-
((1.0, b.reshape(2, 2, 2)),),
|
|
493
|
+
((1.0, b.reshape((2, 2, 2))),),
|
|
493
494
|
)
|
|
494
495
|
assert mixtures_equal(
|
|
495
496
|
cirq.partial_trace_of_state_vector_as_mixture(state, [5, 6, 7, 8], atol=1e-8),
|
|
496
|
-
((1.0, c.reshape(2, 2, 2, 2)),),
|
|
497
|
+
((1.0, c.reshape((2, 2, 2, 2))),),
|
|
497
498
|
)
|
|
498
499
|
assert mixtures_equal(
|
|
499
500
|
cirq.partial_trace_of_state_vector_as_mixture(state, [0, 1, 2, 3, 4], atol=1e-8),
|
|
@@ -632,3 +633,18 @@ def test_factor_state_vector(state_1: int, state_2: int):
|
|
|
632
633
|
# All phase goes into a1, and b1 is just the dephased state vector
|
|
633
634
|
assert np.allclose(a1, a * phase)
|
|
634
635
|
assert np.allclose(b1, b)
|
|
636
|
+
|
|
637
|
+
|
|
638
|
+
@pytest.mark.parametrize('num_dimensions', [*range(1, 7)])
|
|
639
|
+
def test_transpose_flattened_array(num_dimensions):
|
|
640
|
+
np.random.seed(0)
|
|
641
|
+
for _ in range(10):
|
|
642
|
+
shape = np.random.randint(1, 5, (num_dimensions,)).tolist()
|
|
643
|
+
axes = np.random.permutation(num_dimensions).tolist()
|
|
644
|
+
volume = np.prod(shape)
|
|
645
|
+
A = np.random.permutation(volume)
|
|
646
|
+
want = np.transpose(A.reshape(shape), axes)
|
|
647
|
+
got = linalg.transpose_flattened_array(A, shape, axes).reshape(want.shape)
|
|
648
|
+
assert np.array_equal(want, got)
|
|
649
|
+
got = linalg.transpose_flattened_array(A.reshape(shape), shape, axes).reshape(want.shape)
|
|
650
|
+
assert np.array_equal(want, got)
|
cirq/ops/__init__.py
CHANGED
|
@@ -41,6 +41,7 @@ from cirq.ops.common_channels import (
|
|
|
41
41
|
phase_flip,
|
|
42
42
|
PhaseDampingChannel,
|
|
43
43
|
PhaseFlipChannel,
|
|
44
|
+
R,
|
|
44
45
|
reset,
|
|
45
46
|
reset_each,
|
|
46
47
|
ResetChannel,
|
|
@@ -119,6 +120,8 @@ from cirq.ops.projector import ProjectorString
|
|
|
119
120
|
|
|
120
121
|
from cirq.ops.controlled_operation import ControlledOperation
|
|
121
122
|
|
|
123
|
+
from cirq.ops.qubit_manager import BorrowableQubit, CleanQubit, QubitManager, SimpleQubitManager
|
|
124
|
+
|
|
122
125
|
from cirq.ops.qubit_order import QubitOrder
|
|
123
126
|
|
|
124
127
|
from cirq.ops.qubit_order_or_list import QubitOrderOrList
|
|
@@ -126,6 +129,7 @@ from cirq.ops.qubit_order_or_list import QubitOrderOrList
|
|
|
126
129
|
from cirq.ops.matrix_gates import MatrixGate
|
|
127
130
|
|
|
128
131
|
from cirq.ops.measure_util import (
|
|
132
|
+
M,
|
|
129
133
|
measure,
|
|
130
134
|
measure_each,
|
|
131
135
|
measure_paulistring_terms,
|
cirq/ops/arithmetic_operation.py
CHANGED
|
@@ -15,7 +15,8 @@
|
|
|
15
15
|
|
|
16
16
|
import abc
|
|
17
17
|
import itertools
|
|
18
|
-
from typing import Union, Iterable, List, Sequence, cast, Tuple,
|
|
18
|
+
from typing import Union, Iterable, List, Sequence, cast, Tuple, TYPE_CHECKING
|
|
19
|
+
from typing_extensions import Self
|
|
19
20
|
|
|
20
21
|
import numpy as np
|
|
21
22
|
|
|
@@ -25,9 +26,6 @@ if TYPE_CHECKING:
|
|
|
25
26
|
import cirq
|
|
26
27
|
|
|
27
28
|
|
|
28
|
-
TSelfGate = TypeVar('TSelfGate', bound='ArithmeticGate')
|
|
29
|
-
|
|
30
|
-
|
|
31
29
|
class ArithmeticGate(Gate, metaclass=abc.ABCMeta):
|
|
32
30
|
r"""A helper gate for implementing reversible classical arithmetic.
|
|
33
31
|
|
|
@@ -55,7 +53,7 @@ class ArithmeticGate(Gate, metaclass=abc.ABCMeta):
|
|
|
55
53
|
...
|
|
56
54
|
... def with_registers(
|
|
57
55
|
... self, *new_registers: 'Union[int, Sequence[int]]'
|
|
58
|
-
... ) -> '
|
|
56
|
+
... ) -> 'Add':
|
|
59
57
|
... return Add(*new_registers)
|
|
60
58
|
...
|
|
61
59
|
... def apply(self, *register_values: int) -> 'Union[int, Iterable[int]]':
|
|
@@ -105,7 +103,7 @@ class ArithmeticGate(Gate, metaclass=abc.ABCMeta):
|
|
|
105
103
|
raise NotImplementedError()
|
|
106
104
|
|
|
107
105
|
@abc.abstractmethod
|
|
108
|
-
def with_registers(self
|
|
106
|
+
def with_registers(self, *new_registers: Union[int, Sequence[int]]) -> Self:
|
|
109
107
|
"""Returns the same fate targeting different registers.
|
|
110
108
|
|
|
111
109
|
Args:
|
|
@@ -28,7 +28,7 @@ from typing import (
|
|
|
28
28
|
import sympy
|
|
29
29
|
|
|
30
30
|
from cirq import protocols, value
|
|
31
|
-
from cirq.ops import raw_types
|
|
31
|
+
from cirq.ops import op_tree, raw_types
|
|
32
32
|
|
|
33
33
|
if TYPE_CHECKING:
|
|
34
34
|
import cirq
|
|
@@ -105,11 +105,18 @@ class ClassicallyControlledOperation(raw_types.Operation):
|
|
|
105
105
|
)
|
|
106
106
|
|
|
107
107
|
def _decompose_(self):
|
|
108
|
-
|
|
108
|
+
return self._decompose_with_context_()
|
|
109
|
+
|
|
110
|
+
def _decompose_with_context_(self, context: Optional['cirq.DecompositionContext'] = None):
|
|
111
|
+
result = protocols.decompose_once(
|
|
112
|
+
self._sub_operation, NotImplemented, flatten=False, context=context
|
|
113
|
+
)
|
|
109
114
|
if result is NotImplemented:
|
|
110
115
|
return NotImplemented
|
|
111
116
|
|
|
112
|
-
return
|
|
117
|
+
return op_tree.transform_op_tree(
|
|
118
|
+
result, lambda op: ClassicallyControlledOperation(op, self._conditions)
|
|
119
|
+
)
|
|
113
120
|
|
|
114
121
|
def _value_equality_values_(self):
|
|
115
122
|
return (frozenset(self._conditions), self._sub_operation)
|
cirq/ops/clifford_gate.py
CHANGED
|
@@ -75,12 +75,6 @@ def _to_clifford_tableau(
|
|
|
75
75
|
return clifford_tableau
|
|
76
76
|
|
|
77
77
|
|
|
78
|
-
def _pretend_initialized() -> 'SingleQubitCliffordGate':
|
|
79
|
-
# HACK: This is a workaround to fool mypy and pylint into correctly handling
|
|
80
|
-
# class fields that can't be initialized until after the class is defined.
|
|
81
|
-
pass
|
|
82
|
-
|
|
83
|
-
|
|
84
78
|
def _validate_map_input(
|
|
85
79
|
required_transform_count: int,
|
|
86
80
|
pauli_map_to: Optional[Dict[Pauli, Tuple[Pauli, bool]]],
|
|
@@ -97,6 +91,7 @@ def _validate_map_input(
|
|
|
97
91
|
' of x_to, y_to, and z_to but both were given'
|
|
98
92
|
)
|
|
99
93
|
if len(pauli_map_to) != required_transform_count:
|
|
94
|
+
# pylint: disable=consider-using-f-string
|
|
100
95
|
raise ValueError(
|
|
101
96
|
'Method takes {} transform{} but {} {} given'.format(
|
|
102
97
|
required_transform_count,
|
|
@@ -440,7 +435,6 @@ class CliffordGate(raw_types.Gate, CommonCliffordGates):
|
|
|
440
435
|
def _act_on_(
|
|
441
436
|
self, sim_state: 'cirq.SimulationStateBase', qubits: Sequence['cirq.Qid']
|
|
442
437
|
) -> Union[NotImplementedType, bool]:
|
|
443
|
-
|
|
444
438
|
# Note the computation complexity difference between _decompose_ and _act_on_.
|
|
445
439
|
# Suppose this Gate has `m` qubits, args has `n` qubits, and the decomposition of
|
|
446
440
|
# this operation into `k` operations:
|
cirq/ops/common_channels.py
CHANGED
|
@@ -775,10 +775,16 @@ class ResetChannel(raw_types.Gate):
|
|
|
775
775
|
|
|
776
776
|
|
|
777
777
|
def reset(qubit: 'cirq.Qid') -> raw_types.Operation:
|
|
778
|
-
"""Returns a `cirq.ResetChannel` on the given qubit.
|
|
778
|
+
"""Returns a `cirq.ResetChannel` on the given qubit.
|
|
779
|
+
|
|
780
|
+
This can also be used with the alias `cirq.R`.
|
|
781
|
+
"""
|
|
779
782
|
return ResetChannel(qubit.dimension).on(qubit)
|
|
780
783
|
|
|
781
784
|
|
|
785
|
+
R = reset
|
|
786
|
+
|
|
787
|
+
|
|
782
788
|
def reset_each(*qubits: 'cirq.Qid') -> List[raw_types.Operation]:
|
|
783
789
|
"""Returns a list of `cirq.ResetChannel` instances on the given qubits."""
|
|
784
790
|
return [ResetChannel(q.dimension).on(q) for q in qubits]
|
|
@@ -1010,15 +1016,15 @@ def _phase_flip(p: float) -> PhaseFlipChannel:
|
|
|
1010
1016
|
|
|
1011
1017
|
$$
|
|
1012
1018
|
\begin{aligned}
|
|
1013
|
-
M_0 =& \sqrt{p} \begin{bmatrix}
|
|
1019
|
+
M_0 =& \sqrt{1 - p} \begin{bmatrix}
|
|
1014
1020
|
1 & 0 \\
|
|
1015
1021
|
0 & 1
|
|
1016
|
-
|
|
1022
|
+
\end{bmatrix}
|
|
1017
1023
|
\\
|
|
1018
|
-
M_1 =& \sqrt{
|
|
1024
|
+
M_1 =& \sqrt{p} \begin{bmatrix}
|
|
1019
1025
|
1 & 0 \\
|
|
1020
1026
|
0 & -1
|
|
1021
|
-
|
|
1027
|
+
\end{bmatrix}
|
|
1022
1028
|
\end{aligned}
|
|
1023
1029
|
$$
|
|
1024
1030
|
|
|
@@ -1046,15 +1052,15 @@ def phase_flip(p: Optional[float] = None) -> Union[common_gates.ZPowGate, PhaseF
|
|
|
1046
1052
|
|
|
1047
1053
|
$$
|
|
1048
1054
|
\begin{aligned}
|
|
1049
|
-
M_0 =& \sqrt{p} \begin{bmatrix}
|
|
1055
|
+
M_0 =& \sqrt{1 - p} \begin{bmatrix}
|
|
1050
1056
|
1 & 0 \\
|
|
1051
1057
|
0 & 1
|
|
1052
|
-
|
|
1058
|
+
\end{bmatrix}
|
|
1053
1059
|
\\
|
|
1054
|
-
M_1 =& \sqrt{
|
|
1060
|
+
M_1 =& \sqrt{p} \begin{bmatrix}
|
|
1055
1061
|
1 & 0 \\
|
|
1056
1062
|
0 & -1
|
|
1057
|
-
|
|
1063
|
+
\end{bmatrix}
|
|
1058
1064
|
\end{aligned}
|
|
1059
1065
|
$$
|
|
1060
1066
|
|
|
@@ -1162,14 +1168,14 @@ def _bit_flip(p: float) -> BitFlipChannel:
|
|
|
1162
1168
|
|
|
1163
1169
|
$$
|
|
1164
1170
|
\begin{aligned}
|
|
1165
|
-
M_0 =& \sqrt{p} \begin{bmatrix}
|
|
1171
|
+
M_0 =& \sqrt{1-p} \begin{bmatrix}
|
|
1166
1172
|
1 & 0 \\
|
|
1167
1173
|
0 & 1
|
|
1168
1174
|
\end{bmatrix}
|
|
1169
1175
|
\\
|
|
1170
|
-
M_1 =& \sqrt{
|
|
1176
|
+
M_1 =& \sqrt{p} \begin{bmatrix}
|
|
1171
1177
|
0 & 1 \\
|
|
1172
|
-
1 &
|
|
1178
|
+
1 & 0
|
|
1173
1179
|
\end{bmatrix}
|
|
1174
1180
|
\end{aligned}
|
|
1175
1181
|
$$
|
|
@@ -1198,14 +1204,14 @@ def bit_flip(p: Optional[float] = None) -> Union[common_gates.XPowGate, BitFlipC
|
|
|
1198
1204
|
|
|
1199
1205
|
$$
|
|
1200
1206
|
\begin{aligned}
|
|
1201
|
-
M_0 =& \sqrt{p} \begin{bmatrix}
|
|
1207
|
+
M_0 =& \sqrt{1-p} \begin{bmatrix}
|
|
1202
1208
|
1 & 0 \\
|
|
1203
1209
|
0 & 1
|
|
1204
1210
|
\end{bmatrix}
|
|
1205
1211
|
\\
|
|
1206
|
-
M_1 =& \sqrt{
|
|
1212
|
+
M_1 =& \sqrt{p} \begin{bmatrix}
|
|
1207
1213
|
0 & 1 \\
|
|
1208
|
-
1 &
|
|
1214
|
+
1 & 0
|
|
1209
1215
|
\end{bmatrix}
|
|
1210
1216
|
\end{aligned}
|
|
1211
1217
|
$$
|
cirq/ops/common_gate_families.py
CHANGED
|
@@ -37,9 +37,8 @@ class AnyUnitaryGateFamily(gateset.GateFamily):
|
|
|
37
37
|
|
|
38
38
|
self._num_qubits = num_qubits
|
|
39
39
|
name = f'{str(num_qubits) if num_qubits else "Any"}-Qubit UnitaryGateFamily'
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
)
|
|
40
|
+
kind = f'{num_qubits}-qubit ' if num_qubits else ''
|
|
41
|
+
description = f'Accepts any {kind}unitary gate'
|
|
43
42
|
super().__init__(raw_types.Gate, name=name, description=description)
|
|
44
43
|
|
|
45
44
|
def _predicate(self, g: raw_types.Gate) -> bool:
|
cirq/ops/common_gates.py
CHANGED
|
@@ -11,6 +11,7 @@
|
|
|
11
11
|
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
12
|
# See the License for the specific language governing permissions and
|
|
13
13
|
# limitations under the License.
|
|
14
|
+
|
|
14
15
|
"""Quantum gates that are commonly used in the literature.
|
|
15
16
|
|
|
16
17
|
This module creates Gate instances for the following gates:
|
|
@@ -120,6 +121,10 @@ class XPowGate(eigen_gate.EigenGate):
|
|
|
120
121
|
super().__init__(exponent=exponent, global_shift=global_shift)
|
|
121
122
|
self._dimension = dimension
|
|
122
123
|
|
|
124
|
+
@property
|
|
125
|
+
def dimension(self) -> value.TParamVal:
|
|
126
|
+
return self._dimension
|
|
127
|
+
|
|
123
128
|
def _num_qubits_(self) -> int:
|
|
124
129
|
return 1
|
|
125
130
|
|
|
@@ -183,7 +188,7 @@ class XPowGate(eigen_gate.EigenGate):
|
|
|
183
188
|
|
|
184
189
|
def controlled(
|
|
185
190
|
self,
|
|
186
|
-
num_controls: int = None,
|
|
191
|
+
num_controls: Optional[int] = None,
|
|
187
192
|
control_values: Optional[
|
|
188
193
|
Union[cv.AbstractControlValues, Sequence[Union[int, Collection[int]]]]
|
|
189
194
|
] = None,
|
|
@@ -316,6 +321,18 @@ class XPowGate(eigen_gate.EigenGate):
|
|
|
316
321
|
all_args = ', '.join(args)
|
|
317
322
|
return f'cirq.XPowGate({all_args})'
|
|
318
323
|
|
|
324
|
+
def _json_dict_(self) -> Dict[str, Any]:
|
|
325
|
+
d = protocols.obj_to_dict_helper(self, ['exponent', 'global_shift'])
|
|
326
|
+
if self.dimension != 2:
|
|
327
|
+
d['dimension'] = self.dimension
|
|
328
|
+
return d
|
|
329
|
+
|
|
330
|
+
def _value_equality_values_(self):
|
|
331
|
+
return (*super()._value_equality_values_(), self._dimension)
|
|
332
|
+
|
|
333
|
+
def _value_equality_approximate_values_(self):
|
|
334
|
+
return (*super()._value_equality_approximate_values_(), self._dimension)
|
|
335
|
+
|
|
319
336
|
|
|
320
337
|
class Rx(XPowGate):
|
|
321
338
|
r"""A gate with matrix $e^{-i X t/2}$ that rotates around the X axis of the Bloch sphere by $t$.
|
|
@@ -341,7 +358,7 @@ class Rx(XPowGate):
|
|
|
341
358
|
self._rads = rads
|
|
342
359
|
super().__init__(exponent=rads / _pi(rads), global_shift=-0.5)
|
|
343
360
|
|
|
344
|
-
def _with_exponent(self
|
|
361
|
+
def _with_exponent(self, exponent: value.TParamVal) -> 'Rx':
|
|
345
362
|
return Rx(rads=exponent * _pi(exponent))
|
|
346
363
|
|
|
347
364
|
def _circuit_diagram_info_(
|
|
@@ -496,8 +513,10 @@ class YPowGate(eigen_gate.EigenGate):
|
|
|
496
513
|
if self._exponent == 1:
|
|
497
514
|
return 'cirq.Y'
|
|
498
515
|
return f'(cirq.Y**{proper_repr(self._exponent)})'
|
|
499
|
-
return
|
|
500
|
-
|
|
516
|
+
return (
|
|
517
|
+
'cirq.YPowGate('
|
|
518
|
+
f'exponent={proper_repr(self._exponent)}, '
|
|
519
|
+
f'global_shift={self._global_shift!r})'
|
|
501
520
|
)
|
|
502
521
|
|
|
503
522
|
|
|
@@ -525,7 +544,7 @@ class Ry(YPowGate):
|
|
|
525
544
|
self._rads = rads
|
|
526
545
|
super().__init__(exponent=rads / _pi(rads), global_shift=-0.5)
|
|
527
546
|
|
|
528
|
-
def _with_exponent(self
|
|
547
|
+
def _with_exponent(self, exponent: value.TParamVal) -> 'Ry':
|
|
529
548
|
return Ry(rads=exponent * _pi(exponent))
|
|
530
549
|
|
|
531
550
|
def _circuit_diagram_info_(
|
|
@@ -608,6 +627,10 @@ class ZPowGate(eigen_gate.EigenGate):
|
|
|
608
627
|
super().__init__(exponent=exponent, global_shift=global_shift)
|
|
609
628
|
self._dimension = dimension
|
|
610
629
|
|
|
630
|
+
@property
|
|
631
|
+
def dimension(self) -> value.TParamVal:
|
|
632
|
+
return self._dimension
|
|
633
|
+
|
|
611
634
|
def _num_qubits_(self) -> int:
|
|
612
635
|
return 1
|
|
613
636
|
|
|
@@ -647,7 +670,7 @@ class ZPowGate(eigen_gate.EigenGate):
|
|
|
647
670
|
|
|
648
671
|
def controlled(
|
|
649
672
|
self,
|
|
650
|
-
num_controls: int = None,
|
|
673
|
+
num_controls: Optional[int] = None,
|
|
651
674
|
control_values: Optional[
|
|
652
675
|
Union[cv.AbstractControlValues, Sequence[Union[int, Collection[int]]]]
|
|
653
676
|
] = None,
|
|
@@ -834,6 +857,18 @@ class ZPowGate(eigen_gate.EigenGate):
|
|
|
834
857
|
return NotImplemented
|
|
835
858
|
return True
|
|
836
859
|
|
|
860
|
+
def _json_dict_(self) -> Dict[str, Any]:
|
|
861
|
+
d = protocols.obj_to_dict_helper(self, ['exponent', 'global_shift'])
|
|
862
|
+
if self.dimension != 2:
|
|
863
|
+
d['dimension'] = self.dimension
|
|
864
|
+
return d
|
|
865
|
+
|
|
866
|
+
def _value_equality_values_(self):
|
|
867
|
+
return (*super()._value_equality_values_(), self._dimension)
|
|
868
|
+
|
|
869
|
+
def _value_equality_approximate_values_(self):
|
|
870
|
+
return (*super()._value_equality_approximate_values_(), self._dimension)
|
|
871
|
+
|
|
837
872
|
|
|
838
873
|
class Rz(ZPowGate):
|
|
839
874
|
r"""A gate with matrix $e^{-i Z t/2}$ that rotates around the Z axis of the Bloch sphere by $t$.
|
|
@@ -859,7 +894,7 @@ class Rz(ZPowGate):
|
|
|
859
894
|
self._rads = rads
|
|
860
895
|
super().__init__(exponent=rads / _pi(rads), global_shift=-0.5)
|
|
861
896
|
|
|
862
|
-
def _with_exponent(self
|
|
897
|
+
def _with_exponent(self, exponent: value.TParamVal) -> 'Rz':
|
|
863
898
|
return Rz(rads=exponent * _pi(exponent))
|
|
864
899
|
|
|
865
900
|
def _circuit_diagram_info_(
|
|
@@ -1090,7 +1125,7 @@ class CZPowGate(gate_features.InterchangeableQubitsGate, eigen_gate.EigenGate):
|
|
|
1090
1125
|
|
|
1091
1126
|
def controlled(
|
|
1092
1127
|
self,
|
|
1093
|
-
num_controls: int = None,
|
|
1128
|
+
num_controls: Optional[int] = None,
|
|
1094
1129
|
control_values: Optional[
|
|
1095
1130
|
Union[cv.AbstractControlValues, Sequence[Union[int, Collection[int]]]]
|
|
1096
1131
|
] = None,
|
|
@@ -1189,8 +1224,10 @@ class CZPowGate(gate_features.InterchangeableQubitsGate, eigen_gate.EigenGate):
|
|
|
1189
1224
|
if self._exponent == 1:
|
|
1190
1225
|
return 'cirq.CZ'
|
|
1191
1226
|
return f'(cirq.CZ**{proper_repr(self._exponent)})'
|
|
1192
|
-
return
|
|
1193
|
-
|
|
1227
|
+
return (
|
|
1228
|
+
'cirq.CZPowGate('
|
|
1229
|
+
f'exponent={proper_repr(self._exponent)}, '
|
|
1230
|
+
f'global_shift={self._global_shift!r})'
|
|
1194
1231
|
)
|
|
1195
1232
|
|
|
1196
1233
|
|
|
@@ -1296,7 +1333,7 @@ class CXPowGate(eigen_gate.EigenGate):
|
|
|
1296
1333
|
|
|
1297
1334
|
def controlled(
|
|
1298
1335
|
self,
|
|
1299
|
-
num_controls: int = None,
|
|
1336
|
+
num_controls: Optional[int] = None,
|
|
1300
1337
|
control_values: Optional[
|
|
1301
1338
|
Union[cv.AbstractControlValues, Sequence[Union[int, Collection[int]]]]
|
|
1302
1339
|
] = None,
|
cirq/ops/common_gates_test.py
CHANGED
|
@@ -1100,6 +1100,7 @@ def test_approx_eq():
|
|
|
1100
1100
|
|
|
1101
1101
|
def test_xpow_dim_3():
|
|
1102
1102
|
x = cirq.XPowGate(dimension=3)
|
|
1103
|
+
assert cirq.X != x
|
|
1103
1104
|
# fmt: off
|
|
1104
1105
|
expected = [
|
|
1105
1106
|
[0, 0, 1],
|
|
@@ -1127,6 +1128,7 @@ def test_xpow_dim_3():
|
|
|
1127
1128
|
|
|
1128
1129
|
def test_xpow_dim_4():
|
|
1129
1130
|
x = cirq.XPowGate(dimension=4)
|
|
1131
|
+
assert cirq.X != x
|
|
1130
1132
|
# fmt: off
|
|
1131
1133
|
expected = [
|
|
1132
1134
|
[0, 0, 0, 1],
|
|
@@ -1159,6 +1161,7 @@ def test_zpow_dim_3():
|
|
|
1159
1161
|
L = np.exp(2 * np.pi * 1j / 3)
|
|
1160
1162
|
L2 = L**2
|
|
1161
1163
|
z = cirq.ZPowGate(dimension=3)
|
|
1164
|
+
assert cirq.Z != z
|
|
1162
1165
|
# fmt: off
|
|
1163
1166
|
expected = [
|
|
1164
1167
|
[1, 0, 0],
|
|
@@ -1209,6 +1212,7 @@ def test_zpow_dim_3():
|
|
|
1209
1212
|
|
|
1210
1213
|
def test_zpow_dim_4():
|
|
1211
1214
|
z = cirq.ZPowGate(dimension=4)
|
|
1215
|
+
assert cirq.Z != z
|
|
1212
1216
|
# fmt: off
|
|
1213
1217
|
expected = [
|
|
1214
1218
|
[1, 0, 0, 0],
|