cirq-core 1.5.0.dev20250409225226__py3-none-any.whl → 1.6.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.
Potentially problematic release.
This version of cirq-core might be problematic. Click here for more details.
- cirq/__init__.py +16 -17
- cirq/_compat.py +21 -20
- cirq/_compat_test.py +14 -34
- cirq/_doc.py +4 -2
- cirq/_import.py +8 -6
- cirq/_import_test.py +4 -2
- cirq/_version.py +6 -6
- cirq/_version_test.py +2 -2
- cirq/circuits/_block_diagram_drawer.py +11 -10
- cirq/circuits/_block_diagram_drawer_test.py +8 -6
- cirq/circuits/_box_drawing_character_data.py +8 -8
- cirq/circuits/_box_drawing_character_data_test.py +3 -1
- cirq/circuits/_bucket_priority_queue.py +9 -7
- cirq/circuits/_bucket_priority_queue_test.py +22 -20
- cirq/circuits/circuit.py +248 -172
- cirq/circuits/circuit_operation.py +73 -83
- cirq/circuits/circuit_operation_test.py +128 -90
- cirq/circuits/circuit_test.py +211 -151
- cirq/circuits/frozen_circuit.py +23 -60
- cirq/circuits/frozen_circuit_test.py +31 -8
- cirq/circuits/insert_strategy.py +7 -5
- cirq/circuits/insert_strategy_test.py +4 -2
- cirq/circuits/moment.py +88 -40
- cirq/circuits/moment_test.py +128 -51
- cirq/circuits/optimization_pass.py +5 -5
- cirq/circuits/optimization_pass_test.py +10 -10
- cirq/circuits/qasm_output.py +11 -11
- cirq/circuits/qasm_output_test.py +25 -22
- cirq/circuits/text_diagram_drawer.py +23 -38
- cirq/circuits/text_diagram_drawer_test.py +19 -17
- cirq/conftest.py +4 -3
- cirq/contrib/__init__.py +4 -4
- cirq/contrib/acquaintance/__init__.py +1 -1
- cirq/contrib/acquaintance/bipartite.py +5 -8
- cirq/contrib/acquaintance/bipartite_test.py +18 -13
- cirq/contrib/acquaintance/devices.py +2 -2
- cirq/contrib/acquaintance/devices_test.py +5 -3
- cirq/contrib/acquaintance/executor.py +5 -5
- cirq/contrib/acquaintance/executor_test.py +13 -9
- cirq/contrib/acquaintance/gates.py +18 -28
- cirq/contrib/acquaintance/gates_test.py +24 -20
- cirq/contrib/acquaintance/inspection_utils.py +8 -4
- cirq/contrib/acquaintance/inspection_utils_test.py +4 -2
- cirq/contrib/acquaintance/mutation_utils.py +4 -4
- cirq/contrib/acquaintance/mutation_utils_test.py +4 -2
- cirq/contrib/acquaintance/optimizers.py +4 -4
- cirq/contrib/acquaintance/optimizers_test.py +4 -1
- cirq/contrib/acquaintance/permutation.py +15 -27
- cirq/contrib/acquaintance/permutation_test.py +26 -17
- cirq/contrib/acquaintance/shift.py +4 -4
- cirq/contrib/acquaintance/shift_swap_network.py +4 -4
- cirq/contrib/acquaintance/shift_swap_network_test.py +9 -6
- cirq/contrib/acquaintance/shift_test.py +8 -6
- cirq/contrib/acquaintance/strategies/cubic.py +2 -2
- cirq/contrib/acquaintance/strategies/cubic_test.py +4 -2
- cirq/contrib/acquaintance/strategies/quartic_paired.py +6 -6
- cirq/contrib/acquaintance/strategies/quartic_paired_test.py +10 -6
- cirq/contrib/acquaintance/testing.py +2 -0
- cirq/contrib/acquaintance/topological_sort.py +2 -2
- cirq/contrib/acquaintance/topological_sort_test.py +3 -1
- cirq/contrib/bayesian_network/bayesian_network_gate.py +9 -10
- cirq/contrib/bayesian_network/bayesian_network_gate_test.py +14 -9
- cirq/contrib/circuitdag/circuit_dag.py +4 -4
- cirq/contrib/circuitdag/circuit_dag_test.py +17 -15
- cirq/contrib/custom_simulators/custom_state_simulator.py +5 -5
- cirq/contrib/custom_simulators/custom_state_simulator_test.py +22 -17
- cirq/contrib/graph_device/graph_device.py +12 -11
- cirq/contrib/graph_device/graph_device_test.py +18 -14
- cirq/contrib/graph_device/hypergraph.py +16 -14
- cirq/contrib/graph_device/hypergraph_test.py +13 -11
- cirq/contrib/graph_device/uniform_graph_device.py +6 -4
- cirq/contrib/graph_device/uniform_graph_device_test.py +11 -3
- cirq/contrib/hacks/disable_validation.py +6 -1
- cirq/contrib/hacks/disable_validation_test.py +3 -1
- cirq/contrib/json.py +31 -5
- cirq/contrib/json_test.py +6 -3
- cirq/contrib/json_test_data/DampedReadoutNoiseModel.json +12 -0
- cirq/contrib/json_test_data/DampedReadoutNoiseModel.repr +4 -0
- cirq/contrib/json_test_data/DepolarizingNoiseModel.json +12 -0
- cirq/contrib/json_test_data/DepolarizingNoiseModel.repr +4 -0
- cirq/contrib/json_test_data/DepolarizingWithDampedReadoutNoiseModel.json +6 -0
- cirq/contrib/json_test_data/DepolarizingWithDampedReadoutNoiseModel.repr +1 -0
- cirq/contrib/json_test_data/DepolarizingWithReadoutNoiseModel.json +5 -0
- cirq/contrib/json_test_data/DepolarizingWithReadoutNoiseModel.repr +1 -0
- cirq/contrib/json_test_data/ReadoutNoiseModel.json +12 -0
- cirq/contrib/json_test_data/ReadoutNoiseModel.repr +4 -0
- cirq/contrib/json_test_data/__init__.py +17 -0
- cirq/contrib/json_test_data/spec.py +32 -0
- cirq/contrib/noise_models/noise_models.py +119 -5
- cirq/contrib/noise_models/noise_models_test.py +37 -9
- cirq/contrib/paulistring/clifford_optimize.py +6 -4
- cirq/contrib/paulistring/clifford_optimize_test.py +6 -5
- cirq/contrib/paulistring/clifford_target_gateset.py +10 -10
- cirq/contrib/paulistring/clifford_target_gateset_test.py +13 -11
- cirq/contrib/paulistring/optimize.py +2 -0
- cirq/contrib/paulistring/optimize_test.py +4 -3
- cirq/contrib/paulistring/pauli_string_dag.py +2 -0
- cirq/contrib/paulistring/pauli_string_dag_test.py +3 -1
- cirq/contrib/paulistring/pauli_string_measurement_with_readout_mitigation.py +255 -120
- cirq/contrib/paulistring/pauli_string_measurement_with_readout_mitigation_test.py +398 -19
- cirq/contrib/paulistring/pauli_string_optimize.py +7 -1
- cirq/contrib/paulistring/pauli_string_optimize_test.py +5 -3
- cirq/contrib/paulistring/recombine.py +6 -4
- cirq/contrib/paulistring/recombine_test.py +3 -1
- cirq/contrib/paulistring/separate.py +9 -6
- cirq/contrib/paulistring/separate_test.py +3 -1
- cirq/contrib/qasm_import/_lexer.py +3 -2
- cirq/contrib/qasm_import/_lexer_test.py +49 -13
- cirq/contrib/qasm_import/_parser.py +547 -83
- cirq/contrib/qasm_import/_parser_test.py +988 -97
- cirq/contrib/qasm_import/exception.py +2 -0
- cirq/contrib/qasm_import/qasm.py +8 -2
- cirq/contrib/qasm_import/qasm_test.py +7 -4
- cirq/contrib/qcircuit/qcircuit_diagram_info.py +5 -5
- cirq/contrib/qcircuit/qcircuit_diagram_info_test.py +4 -1
- cirq/contrib/qcircuit/qcircuit_pdf.py +7 -3
- cirq/contrib/qcircuit/qcircuit_pdf_test.py +3 -1
- cirq/contrib/qcircuit/qcircuit_test.py +10 -8
- cirq/contrib/quantum_volume/quantum_volume.py +31 -27
- cirq/contrib/quantum_volume/quantum_volume_test.py +19 -16
- cirq/contrib/quimb/density_matrix.py +15 -14
- cirq/contrib/quimb/density_matrix_test.py +10 -7
- cirq/contrib/quimb/grid_circuits.py +5 -2
- cirq/contrib/quimb/grid_circuits_test.py +3 -0
- cirq/contrib/quimb/mps_simulator.py +20 -20
- cirq/contrib/quimb/mps_simulator_test.py +3 -0
- cirq/contrib/quimb/state_vector.py +12 -11
- cirq/contrib/quimb/state_vector_test.py +3 -0
- cirq/contrib/quirk/export_to_quirk.py +5 -3
- cirq/contrib/quirk/export_to_quirk_test.py +18 -16
- cirq/contrib/quirk/linearize_circuit.py +2 -0
- cirq/contrib/quirk/quirk_gate.py +18 -17
- cirq/contrib/routing/device.py +5 -3
- cirq/contrib/routing/device_test.py +2 -0
- cirq/contrib/routing/greedy.py +10 -21
- cirq/contrib/routing/greedy_test.py +4 -2
- cirq/contrib/routing/initialization.py +2 -2
- cirq/contrib/routing/initialization_test.py +5 -3
- cirq/contrib/routing/router.py +9 -5
- cirq/contrib/routing/router_test.py +2 -0
- cirq/contrib/routing/swap_network.py +3 -3
- cirq/contrib/routing/swap_network_test.py +3 -1
- cirq/contrib/routing/utils.py +2 -2
- cirq/contrib/routing/utils_test.py +3 -0
- cirq/contrib/shuffle_circuits/shuffle_circuits_with_readout_benchmarking.py +15 -9
- cirq/contrib/shuffle_circuits/shuffle_circuits_with_readout_benchmarking_test.py +3 -0
- cirq/contrib/svg/svg.py +3 -3
- cirq/contrib/svg/svg_test.py +8 -5
- cirq/devices/device.py +4 -4
- cirq/devices/device_test.py +7 -4
- cirq/devices/grid_device_metadata.py +10 -10
- cirq/devices/grid_device_metadata_test.py +3 -0
- cirq/devices/grid_qubit.py +29 -21
- cirq/devices/grid_qubit_test.py +3 -0
- cirq/devices/insertion_noise_model.py +7 -7
- cirq/devices/insertion_noise_model_test.py +7 -5
- cirq/devices/line_qubit.py +13 -13
- cirq/devices/line_qubit_test.py +2 -0
- cirq/devices/named_topologies.py +18 -29
- cirq/devices/named_topologies_test.py +13 -10
- cirq/devices/noise_model.py +3 -3
- cirq/devices/noise_model_test.py +19 -15
- cirq/devices/noise_properties.py +15 -6
- cirq/devices/noise_properties_test.py +34 -3
- cirq/devices/noise_utils.py +11 -9
- cirq/devices/noise_utils_test.py +2 -0
- cirq/devices/superconducting_qubits_noise_properties.py +23 -22
- cirq/devices/superconducting_qubits_noise_properties_test.py +6 -6
- cirq/devices/thermal_noise_model.py +107 -37
- cirq/devices/thermal_noise_model_test.py +21 -0
- cirq/devices/unconstrained_device.py +5 -3
- cirq/devices/unconstrained_device_test.py +2 -0
- cirq/experiments/__init__.py +4 -2
- cirq/experiments/benchmarking/__init__.py +17 -0
- cirq/experiments/benchmarking/parallel_xeb.py +677 -0
- cirq/experiments/benchmarking/parallel_xeb_test.py +447 -0
- cirq/experiments/fidelity_estimation.py +14 -8
- cirq/experiments/fidelity_estimation_test.py +3 -0
- cirq/experiments/n_qubit_tomography.py +17 -16
- cirq/experiments/n_qubit_tomography_test.py +8 -5
- cirq/experiments/purity_estimation.py +2 -0
- cirq/experiments/purity_estimation_test.py +2 -0
- cirq/experiments/qubit_characterizations.py +207 -103
- cirq/experiments/qubit_characterizations_test.py +40 -12
- cirq/experiments/random_quantum_circuit_generation.py +56 -70
- cirq/experiments/random_quantum_circuit_generation_test.py +11 -8
- cirq/experiments/readout_confusion_matrix.py +24 -22
- cirq/experiments/readout_confusion_matrix_test.py +2 -0
- cirq/experiments/single_qubit_readout_calibration.py +30 -15
- cirq/experiments/single_qubit_readout_calibration_test.py +5 -2
- cirq/experiments/t1_decay_experiment.py +9 -7
- cirq/experiments/t1_decay_experiment_test.py +13 -11
- cirq/experiments/t2_decay_experiment.py +16 -13
- cirq/experiments/t2_decay_experiment_test.py +2 -0
- cirq/experiments/two_qubit_xeb.py +64 -57
- cirq/experiments/two_qubit_xeb_test.py +10 -6
- cirq/experiments/xeb_fitting.py +39 -35
- cirq/experiments/xeb_sampling.py +37 -44
- cirq/experiments/xeb_sampling_test.py +3 -0
- cirq/experiments/xeb_simulation.py +14 -10
- cirq/experiments/xeb_simulation_test.py +5 -5
- cirq/experiments/z_phase_calibration.py +32 -29
- cirq/experiments/z_phase_calibration_test.py +3 -4
- cirq/interop/quirk/cells/__init__.py +1 -1
- cirq/interop/quirk/cells/all_cells.py +7 -2
- cirq/interop/quirk/cells/arithmetic_cells.py +29 -41
- cirq/interop/quirk/cells/arithmetic_cells_test.py +17 -14
- cirq/interop/quirk/cells/cell.py +19 -28
- cirq/interop/quirk/cells/cell_test.py +3 -0
- cirq/interop/quirk/cells/composite_cell.py +13 -28
- cirq/interop/quirk/cells/composite_cell_test.py +2 -0
- cirq/interop/quirk/cells/control_cells.py +15 -15
- cirq/interop/quirk/cells/control_cells_test.py +7 -5
- cirq/interop/quirk/cells/frequency_space_cells.py +4 -3
- cirq/interop/quirk/cells/frequency_space_cells_test.py +3 -1
- cirq/interop/quirk/cells/ignored_cells.py +3 -0
- cirq/interop/quirk/cells/ignored_cells_test.py +3 -1
- cirq/interop/quirk/cells/input_cells.py +7 -5
- cirq/interop/quirk/cells/input_cells_test.py +7 -5
- cirq/interop/quirk/cells/input_rotation_cells.py +15 -13
- cirq/interop/quirk/cells/input_rotation_cells_test.py +9 -7
- cirq/interop/quirk/cells/measurement_cells.py +5 -2
- cirq/interop/quirk/cells/measurement_cells_test.py +3 -1
- cirq/interop/quirk/cells/parse.py +22 -23
- cirq/interop/quirk/cells/parse_test.py +12 -10
- cirq/interop/quirk/cells/qubit_permutation_cells.py +5 -3
- cirq/interop/quirk/cells/qubit_permutation_cells_test.py +9 -7
- cirq/interop/quirk/cells/scalar_cells.py +4 -1
- cirq/interop/quirk/cells/scalar_cells_test.py +3 -1
- cirq/interop/quirk/cells/single_qubit_rotation_cells.py +5 -2
- cirq/interop/quirk/cells/single_qubit_rotation_cells_test.py +5 -3
- cirq/interop/quirk/cells/swap_cell.py +8 -6
- cirq/interop/quirk/cells/swap_cell_test.py +6 -4
- cirq/interop/quirk/cells/testing.py +6 -6
- cirq/interop/quirk/cells/testing_test.py +8 -6
- cirq/interop/quirk/cells/unsupported_cells.py +3 -0
- cirq/interop/quirk/cells/unsupported_cells_test.py +4 -2
- cirq/interop/quirk/url_to_circuit.py +23 -36
- cirq/interop/quirk/url_to_circuit_test.py +4 -1
- cirq/json_resolver_cache.py +14 -12
- cirq/linalg/__init__.py +4 -6
- cirq/linalg/combinators.py +7 -5
- cirq/linalg/combinators_test.py +10 -7
- cirq/linalg/decompositions.py +24 -35
- cirq/linalg/decompositions_test.py +3 -1
- cirq/linalg/diagonalize.py +6 -4
- cirq/linalg/diagonalize_test.py +15 -14
- cirq/linalg/operator_spaces.py +14 -14
- cirq/linalg/operator_spaces_test.py +13 -11
- cirq/linalg/predicates.py +18 -9
- cirq/linalg/predicates_test.py +5 -0
- cirq/linalg/tolerance.py +6 -3
- cirq/linalg/tolerance_test.py +6 -4
- cirq/linalg/transformations.py +23 -20
- cirq/linalg/transformations_test.py +73 -43
- cirq/neutral_atoms/convert_to_neutral_atom_gates.py +9 -3
- cirq/neutral_atoms/convert_to_neutral_atom_gates_test.py +3 -1
- cirq/neutral_atoms/neutral_atom_devices.py +2 -0
- cirq/ops/__init__.py +2 -0
- cirq/ops/arithmetic_operation.py +21 -21
- cirq/ops/arithmetic_operation_test.py +7 -8
- cirq/ops/boolean_hamiltonian.py +23 -22
- cirq/ops/boolean_hamiltonian_test.py +12 -9
- cirq/ops/classically_controlled_operation.py +31 -36
- cirq/ops/classically_controlled_operation_test.py +121 -117
- cirq/ops/clifford_gate.py +98 -81
- cirq/ops/clifford_gate_test.py +72 -57
- cirq/ops/common_channels.py +44 -44
- cirq/ops/common_channels_test.py +83 -81
- cirq/ops/common_gate_families.py +9 -7
- cirq/ops/common_gate_families_test.py +11 -7
- cirq/ops/common_gates.py +164 -183
- cirq/ops/common_gates_test.py +135 -95
- cirq/ops/control_values.py +23 -26
- cirq/ops/control_values_test.py +22 -20
- cirq/ops/controlled_gate.py +64 -112
- cirq/ops/controlled_gate_test.py +130 -35
- cirq/ops/controlled_operation.py +24 -35
- cirq/ops/controlled_operation_test.py +8 -6
- cirq/ops/dense_pauli_string.py +38 -49
- cirq/ops/dense_pauli_string_test.py +4 -2
- cirq/ops/diagonal_gate.py +18 -31
- cirq/ops/diagonal_gate_test.py +13 -13
- cirq/ops/eigen_gate.py +29 -29
- cirq/ops/eigen_gate_test.py +45 -28
- cirq/ops/fourier_transform.py +14 -20
- cirq/ops/fourier_transform_test.py +15 -12
- cirq/ops/fsim_gate.py +43 -42
- cirq/ops/fsim_gate_test.py +29 -29
- cirq/ops/gate_features.py +2 -0
- cirq/ops/gate_features_test.py +5 -3
- cirq/ops/gate_operation.py +43 -65
- cirq/ops/gate_operation_test.py +46 -42
- cirq/ops/gateset.py +28 -40
- cirq/ops/gateset_test.py +4 -2
- cirq/ops/global_phase_op.py +45 -20
- cirq/ops/global_phase_op_test.py +44 -20
- cirq/ops/greedy_qubit_manager.py +10 -8
- cirq/ops/greedy_qubit_manager_test.py +5 -3
- cirq/ops/identity.py +14 -12
- cirq/ops/identity_test.py +24 -20
- cirq/ops/kraus_channel.py +11 -8
- cirq/ops/kraus_channel_test.py +14 -11
- cirq/ops/linear_combinations.py +65 -77
- cirq/ops/linear_combinations_test.py +14 -9
- cirq/ops/matrix_gates.py +21 -18
- cirq/ops/matrix_gates_test.py +16 -0
- cirq/ops/measure_util.py +15 -20
- cirq/ops/measure_util_test.py +2 -0
- cirq/ops/measurement_gate.py +26 -37
- cirq/ops/measurement_gate_test.py +2 -0
- cirq/ops/mixed_unitary_channel.py +12 -9
- cirq/ops/mixed_unitary_channel_test.py +14 -11
- cirq/ops/named_qubit.py +16 -13
- cirq/ops/named_qubit_test.py +15 -13
- cirq/ops/op_tree.py +9 -7
- cirq/ops/op_tree_test.py +22 -19
- cirq/ops/parallel_gate.py +15 -17
- cirq/ops/parallel_gate_test.py +18 -16
- cirq/ops/parity_gates.py +23 -25
- cirq/ops/parity_gates_test.py +36 -32
- cirq/ops/pauli_gates.py +22 -21
- cirq/ops/pauli_gates_test.py +29 -20
- cirq/ops/pauli_interaction_gate.py +15 -19
- cirq/ops/pauli_interaction_gate_test.py +10 -8
- cirq/ops/pauli_measurement_gate.py +23 -35
- cirq/ops/pauli_measurement_gate_test.py +2 -0
- cirq/ops/pauli_string.py +92 -120
- cirq/ops/pauli_string_phasor.py +52 -45
- cirq/ops/pauli_string_phasor_test.py +4 -5
- cirq/ops/pauli_string_raw_types.py +9 -7
- cirq/ops/pauli_string_raw_types_test.py +2 -0
- cirq/ops/pauli_string_test.py +31 -154
- cirq/ops/pauli_sum_exponential.py +12 -12
- cirq/ops/pauli_sum_exponential_test.py +12 -10
- cirq/ops/permutation_gate.py +8 -6
- cirq/ops/permutation_gate_test.py +10 -8
- cirq/ops/phased_iswap_gate.py +16 -16
- cirq/ops/phased_iswap_gate_test.py +17 -15
- cirq/ops/phased_x_gate.py +16 -17
- cirq/ops/phased_x_gate_test.py +18 -16
- cirq/ops/phased_x_z_gate.py +24 -22
- cirq/ops/phased_x_z_gate_test.py +17 -11
- cirq/ops/projector.py +16 -11
- cirq/ops/projector_test.py +19 -16
- cirq/ops/qid_util.py +7 -5
- cirq/ops/qid_util_test.py +2 -0
- cirq/ops/qubit_manager.py +11 -9
- cirq/ops/qubit_manager_test.py +6 -4
- cirq/ops/qubit_order.py +11 -14
- cirq/ops/qubit_order_or_list.py +4 -2
- cirq/ops/qubit_order_test.py +12 -10
- cirq/ops/random_gate_channel.py +12 -10
- cirq/ops/random_gate_channel_test.py +14 -11
- cirq/ops/raw_types.py +109 -129
- cirq/ops/raw_types_test.py +63 -57
- cirq/ops/state_preparation_channel.py +7 -7
- cirq/ops/state_preparation_channel_test.py +11 -9
- cirq/ops/swap_gates.py +13 -15
- cirq/ops/swap_gates_test.py +19 -17
- cirq/ops/tags.py +5 -3
- cirq/ops/tags_test.py +4 -2
- cirq/ops/three_qubit_gates.py +43 -76
- cirq/ops/three_qubit_gates_test.py +19 -17
- cirq/ops/two_qubit_diagonal_gate.py +13 -13
- cirq/ops/two_qubit_diagonal_gate_test.py +10 -8
- cirq/ops/uniform_superposition_gate.py +5 -3
- cirq/ops/uniform_superposition_gate_test.py +5 -3
- cirq/ops/wait_gate.py +17 -14
- cirq/ops/wait_gate_test.py +9 -6
- cirq/protocols/__init__.py +0 -3
- cirq/protocols/act_on_protocol.py +8 -6
- cirq/protocols/act_on_protocol_test.py +15 -12
- cirq/protocols/apply_channel_protocol.py +10 -14
- cirq/protocols/apply_channel_protocol_test.py +2 -0
- cirq/protocols/apply_mixture_protocol.py +13 -42
- cirq/protocols/apply_mixture_protocol_test.py +7 -5
- cirq/protocols/apply_unitary_protocol.py +39 -34
- cirq/protocols/apply_unitary_protocol_test.py +4 -1
- cirq/protocols/approximate_equality_protocol.py +2 -0
- cirq/protocols/approximate_equality_protocol_test.py +2 -0
- cirq/protocols/circuit_diagram_info_protocol.py +58 -42
- cirq/protocols/circuit_diagram_info_protocol_test.py +70 -12
- cirq/protocols/commutes_protocol.py +8 -7
- cirq/protocols/commutes_protocol_test.py +2 -0
- cirq/protocols/control_key_protocol.py +6 -4
- cirq/protocols/control_key_protocol_test.py +3 -1
- cirq/protocols/decompose_protocol.py +49 -48
- cirq/protocols/decompose_protocol_test.py +27 -16
- cirq/protocols/equal_up_to_global_phase_protocol.py +2 -0
- cirq/protocols/equal_up_to_global_phase_protocol_test.py +9 -6
- cirq/protocols/has_stabilizer_effect_protocol.py +7 -5
- cirq/protocols/has_stabilizer_effect_protocol_test.py +7 -5
- cirq/protocols/has_unitary_protocol.py +10 -6
- cirq/protocols/has_unitary_protocol_test.py +13 -8
- cirq/protocols/hash_from_pickle_test.py +2 -11
- cirq/protocols/inverse_protocol.py +13 -16
- cirq/protocols/inverse_protocol_test.py +5 -3
- cirq/protocols/json_serialization.py +35 -54
- cirq/protocols/json_serialization_test.py +14 -21
- cirq/protocols/json_test_data/CXSWAP.json +46 -0
- cirq/protocols/json_test_data/CXSWAP.repr +13 -0
- cirq/protocols/json_test_data/CZSWAP.json +46 -0
- cirq/protocols/json_test_data/CZSWAP.repr +13 -0
- cirq/protocols/json_test_data/CircuitOperation.json +6 -3
- cirq/protocols/json_test_data/CircuitOperation.repr_inward +4 -2
- cirq/protocols/json_test_data/Moment.json +24 -1
- cirq/protocols/json_test_data/Moment.repr +6 -1
- cirq/protocols/json_test_data/ThermalNoiseModel.json +32 -0
- cirq/protocols/json_test_data/ThermalNoiseModel.repr +1 -0
- cirq/protocols/json_test_data/spec.py +6 -2
- cirq/protocols/kraus_protocol.py +47 -7
- cirq/protocols/kraus_protocol_test.py +86 -12
- cirq/protocols/measurement_key_protocol.py +15 -16
- cirq/protocols/measurement_key_protocol_test.py +13 -11
- cirq/protocols/mixture_protocol.py +7 -5
- cirq/protocols/mixture_protocol_test.py +4 -2
- cirq/protocols/mul_protocol.py +2 -3
- cirq/protocols/mul_protocol_test.py +2 -0
- cirq/protocols/pauli_expansion_protocol.py +6 -3
- cirq/protocols/pauli_expansion_protocol_test.py +5 -3
- cirq/protocols/phase_protocol.py +2 -0
- cirq/protocols/phase_protocol_test.py +3 -1
- cirq/protocols/pow_protocol.py +11 -16
- cirq/protocols/pow_protocol_test.py +2 -0
- cirq/protocols/qasm.py +14 -20
- cirq/protocols/qasm_test.py +6 -3
- cirq/protocols/qid_shape_protocol.py +8 -8
- cirq/protocols/qid_shape_protocol_test.py +3 -1
- cirq/protocols/resolve_parameters.py +5 -3
- cirq/protocols/resolve_parameters_test.py +8 -7
- cirq/protocols/trace_distance_bound.py +6 -4
- cirq/protocols/trace_distance_bound_test.py +3 -1
- cirq/protocols/unitary_protocol.py +17 -7
- cirq/protocols/unitary_protocol_test.py +12 -2
- cirq/qis/channels.py +6 -2
- cirq/qis/channels_test.py +20 -16
- cirq/qis/clifford_tableau.py +21 -19
- cirq/qis/clifford_tableau_test.py +2 -2
- cirq/qis/entropy.py +14 -3
- cirq/qis/entropy_test.py +3 -1
- cirq/qis/measures.py +13 -13
- cirq/qis/measures_test.py +20 -14
- cirq/qis/noise_utils.py +2 -0
- cirq/qis/noise_utils_test.py +9 -7
- cirq/qis/quantum_state_representation.py +7 -8
- cirq/qis/states.py +58 -56
- cirq/qis/states_test.py +2 -0
- cirq/sim/classical_simulator.py +23 -22
- cirq/sim/classical_simulator_test.py +2 -0
- cirq/sim/clifford/clifford_simulator.py +23 -21
- cirq/sim/clifford/clifford_simulator_test.py +7 -4
- cirq/sim/clifford/clifford_tableau_simulation_state.py +10 -7
- cirq/sim/clifford/clifford_tableau_simulation_state_test.py +5 -5
- cirq/sim/clifford/stabilizer_ch_form_simulation_state.py +8 -6
- cirq/sim/clifford/stabilizer_ch_form_simulation_state_test.py +8 -6
- cirq/sim/clifford/stabilizer_sampler.py +9 -7
- cirq/sim/clifford/stabilizer_sampler_test.py +4 -2
- cirq/sim/clifford/stabilizer_simulation_state.py +14 -13
- cirq/sim/clifford/stabilizer_simulation_state_test.py +6 -4
- cirq/sim/clifford/stabilizer_state_ch_form.py +13 -11
- cirq/sim/clifford/stabilizer_state_ch_form_test.py +4 -2
- cirq/sim/density_matrix_simulation_state.py +26 -27
- cirq/sim/density_matrix_simulation_state_test.py +10 -8
- cirq/sim/density_matrix_simulator.py +30 -28
- cirq/sim/density_matrix_simulator_test.py +48 -48
- cirq/sim/density_matrix_utils.py +13 -11
- cirq/sim/density_matrix_utils_test.py +38 -36
- cirq/sim/mux.py +33 -31
- cirq/sim/mux_test.py +3 -0
- cirq/sim/simulation_product_state.py +15 -15
- cirq/sim/simulation_product_state_test.py +29 -26
- cirq/sim/simulation_state.py +29 -38
- cirq/sim/simulation_state_base.py +21 -32
- cirq/sim/simulation_state_test.py +15 -13
- cirq/sim/simulation_utils.py +5 -2
- cirq/sim/simulation_utils_test.py +5 -2
- cirq/sim/simulator.py +90 -106
- cirq/sim/simulator_base.py +33 -45
- cirq/sim/simulator_base_test.py +20 -15
- cirq/sim/simulator_test.py +23 -14
- cirq/sim/sparse_simulator.py +19 -17
- cirq/sim/sparse_simulator_test.py +41 -40
- cirq/sim/state_vector.py +15 -12
- cirq/sim/state_vector_simulation_state.py +31 -31
- cirq/sim/state_vector_simulation_state_test.py +16 -14
- cirq/sim/state_vector_simulator.py +17 -14
- cirq/sim/state_vector_simulator_test.py +2 -0
- cirq/sim/state_vector_test.py +6 -3
- cirq/study/flatten_expressions.py +16 -15
- cirq/study/flatten_expressions_test.py +13 -11
- cirq/study/resolver.py +18 -17
- cirq/study/resolver_test.py +22 -20
- cirq/study/result.py +17 -27
- cirq/study/result_test.py +2 -0
- cirq/study/sweepable.py +12 -10
- cirq/study/sweepable_test.py +3 -0
- cirq/study/sweeps.py +42 -61
- cirq/study/sweeps_test.py +33 -0
- cirq/testing/__init__.py +7 -11
- cirq/testing/_compat_test_data/module_a/__init__.py +1 -0
- cirq/testing/_compat_test_data/module_a/module_b/__init__.py +1 -0
- cirq/testing/_compat_test_data/module_a/sub/__init__.py +1 -0
- cirq/testing/circuit_compare.py +8 -17
- cirq/testing/circuit_compare_test.py +2 -0
- cirq/testing/consistent_act_on.py +13 -11
- cirq/testing/consistent_act_on_test.py +5 -3
- cirq/testing/consistent_channels.py +2 -0
- cirq/testing/consistent_channels_test.py +10 -8
- cirq/testing/consistent_controlled_gate_op.py +5 -5
- cirq/testing/consistent_controlled_gate_op_test.py +18 -18
- cirq/testing/consistent_decomposition.py +2 -2
- cirq/testing/consistent_decomposition_test.py +4 -2
- cirq/testing/consistent_pauli_expansion.py +2 -0
- cirq/testing/consistent_pauli_expansion_test.py +3 -1
- cirq/testing/consistent_phase_by.py +2 -0
- cirq/testing/consistent_phase_by_test.py +3 -1
- cirq/testing/consistent_protocols.py +14 -20
- cirq/testing/consistent_protocols_test.py +13 -11
- cirq/testing/consistent_qasm.py +6 -4
- cirq/testing/consistent_qasm_test.py +7 -7
- cirq/testing/consistent_resolve_parameters.py +2 -0
- cirq/testing/consistent_specified_has_unitary.py +2 -2
- cirq/testing/consistent_specified_has_unitary_test.py +6 -4
- cirq/testing/consistent_unitary.py +1 -0
- cirq/testing/consistent_unitary_test.py +4 -2
- cirq/testing/deprecation.py +5 -2
- cirq/testing/deprecation_test.py +5 -2
- cirq/testing/devices.py +7 -4
- cirq/testing/devices_test.py +7 -4
- cirq/testing/equals_tester.py +4 -2
- cirq/testing/equals_tester_test.py +21 -17
- cirq/testing/equivalent_basis_map.py +6 -4
- cirq/testing/equivalent_basis_map_test.py +6 -4
- cirq/testing/equivalent_repr_eval.py +6 -4
- cirq/testing/equivalent_repr_eval_test.py +5 -3
- cirq/testing/gate_features.py +2 -0
- cirq/testing/gate_features_test.py +7 -5
- cirq/testing/json.py +19 -15
- cirq/testing/json_test.py +5 -3
- cirq/testing/lin_alg_utils.py +10 -11
- cirq/testing/lin_alg_utils_test.py +14 -12
- cirq/testing/logs.py +7 -6
- cirq/testing/logs_test.py +9 -7
- cirq/testing/no_identifier_qubit.py +4 -2
- cirq/testing/no_identifier_qubit_test.py +5 -3
- cirq/testing/op_tree.py +2 -0
- cirq/testing/op_tree_test.py +4 -1
- cirq/testing/order_tester.py +2 -0
- cirq/testing/order_tester_test.py +8 -6
- cirq/testing/pytest_utils.py +2 -0
- cirq/testing/pytest_utils_test.py +4 -2
- cirq/testing/random_circuit.py +21 -20
- cirq/testing/random_circuit_test.py +12 -9
- cirq/testing/repr_pretty_tester.py +1 -0
- cirq/testing/repr_pretty_tester_test.py +5 -3
- cirq/testing/routing_devices.py +4 -1
- cirq/testing/routing_devices_test.py +9 -6
- cirq/testing/sample_circuits.py +4 -1
- cirq/testing/sample_circuits_test.py +3 -1
- cirq/testing/sample_gates.py +3 -0
- cirq/testing/sample_gates_test.py +5 -2
- cirq/transformers/__init__.py +11 -4
- cirq/transformers/align.py +9 -7
- cirq/transformers/align_test.py +2 -0
- cirq/transformers/analytical_decompositions/__init__.py +3 -6
- cirq/transformers/analytical_decompositions/clifford_decomposition.py +18 -16
- cirq/transformers/analytical_decompositions/clifford_decomposition_test.py +2 -0
- cirq/transformers/analytical_decompositions/controlled_gate_decomposition.py +19 -16
- cirq/transformers/analytical_decompositions/controlled_gate_decomposition_test.py +2 -0
- cirq/transformers/analytical_decompositions/cphase_to_fsim.py +11 -9
- cirq/transformers/analytical_decompositions/cphase_to_fsim_test.py +5 -3
- cirq/transformers/analytical_decompositions/pauli_string_decomposition.py +5 -3
- cirq/transformers/analytical_decompositions/pauli_string_decomposition_test.py +5 -3
- cirq/transformers/analytical_decompositions/quantum_shannon_decomposition.py +141 -44
- cirq/transformers/analytical_decompositions/quantum_shannon_decomposition_test.py +35 -1
- cirq/transformers/analytical_decompositions/single_qubit_decompositions.py +8 -7
- cirq/transformers/analytical_decompositions/single_qubit_decompositions_test.py +2 -0
- cirq/transformers/analytical_decompositions/single_to_two_qubit_isometry.py +7 -4
- cirq/transformers/analytical_decompositions/single_to_two_qubit_isometry_test.py +3 -0
- cirq/transformers/analytical_decompositions/three_qubit_decomposition.py +11 -19
- cirq/transformers/analytical_decompositions/three_qubit_decomposition_test.py +8 -33
- cirq/transformers/analytical_decompositions/two_qubit_state_preparation.py +9 -11
- cirq/transformers/analytical_decompositions/two_qubit_state_preparation_test.py +2 -0
- cirq/transformers/analytical_decompositions/two_qubit_to_cz.py +91 -27
- cirq/transformers/analytical_decompositions/two_qubit_to_cz_test.py +36 -7
- cirq/transformers/analytical_decompositions/two_qubit_to_fsim.py +20 -21
- cirq/transformers/analytical_decompositions/two_qubit_to_fsim_test.py +8 -6
- cirq/transformers/analytical_decompositions/two_qubit_to_ms.py +13 -15
- cirq/transformers/analytical_decompositions/two_qubit_to_ms_test.py +3 -1
- cirq/transformers/analytical_decompositions/two_qubit_to_sqrt_iswap.py +39 -41
- cirq/transformers/analytical_decompositions/two_qubit_to_sqrt_iswap_test.py +2 -0
- cirq/transformers/drop_empty_moments.py +5 -3
- cirq/transformers/drop_empty_moments_test.py +4 -2
- cirq/transformers/drop_negligible_operations.py +7 -5
- cirq/transformers/drop_negligible_operations_test.py +2 -0
- cirq/transformers/dynamical_decoupling.py +49 -42
- cirq/transformers/dynamical_decoupling_test.py +223 -205
- cirq/transformers/eject_phased_paulis.py +28 -26
- cirq/transformers/eject_phased_paulis_test.py +12 -9
- cirq/transformers/eject_z.py +12 -12
- cirq/transformers/eject_z_test.py +2 -2
- cirq/transformers/expand_composite.py +6 -4
- cirq/transformers/expand_composite_test.py +3 -1
- cirq/transformers/gauge_compiling/__init__.py +3 -1
- cirq/transformers/gauge_compiling/cphase_gauge.py +2 -0
- cirq/transformers/gauge_compiling/cphase_gauge_test.py +2 -0
- cirq/transformers/gauge_compiling/cz_gauge.py +2 -0
- cirq/transformers/gauge_compiling/cz_gauge_test.py +1 -0
- cirq/transformers/gauge_compiling/gauge_compiling.py +45 -41
- cirq/transformers/gauge_compiling/gauge_compiling_test.py +2 -0
- cirq/transformers/gauge_compiling/gauge_compiling_test_utils.py +1 -0
- cirq/transformers/gauge_compiling/gauge_compiling_test_utils_test.py +5 -1
- cirq/transformers/gauge_compiling/iswap_gauge.py +2 -0
- cirq/transformers/gauge_compiling/iswap_gauge_test.py +1 -0
- cirq/transformers/gauge_compiling/spin_inversion_gauge.py +2 -0
- cirq/transformers/gauge_compiling/spin_inversion_gauge_test.py +2 -0
- cirq/transformers/gauge_compiling/sqrt_cz_gauge.py +7 -6
- cirq/transformers/gauge_compiling/sqrt_cz_gauge_test.py +2 -0
- cirq/transformers/gauge_compiling/sqrt_iswap_gauge.py +2 -0
- cirq/transformers/gauge_compiling/sqrt_iswap_gauge_test.py +2 -0
- cirq/transformers/heuristic_decompositions/gate_tabulation_math_utils.py +6 -3
- cirq/transformers/heuristic_decompositions/gate_tabulation_math_utils_test.py +3 -0
- cirq/transformers/heuristic_decompositions/two_qubit_gate_tabulation.py +12 -9
- cirq/transformers/heuristic_decompositions/two_qubit_gate_tabulation_test.py +9 -7
- cirq/transformers/insertion_sort.py +8 -6
- cirq/transformers/insertion_sort_test.py +3 -1
- cirq/transformers/measurement_transformers.py +29 -29
- cirq/transformers/measurement_transformers_test.py +2 -0
- cirq/transformers/merge_k_qubit_gates.py +12 -10
- cirq/transformers/merge_k_qubit_gates_test.py +18 -18
- cirq/transformers/merge_single_qubit_gates.py +197 -20
- cirq/transformers/merge_single_qubit_gates_test.py +177 -5
- cirq/transformers/noise_adding.py +5 -3
- cirq/transformers/noise_adding_test.py +2 -0
- cirq/transformers/optimize_for_target_gateset.py +19 -17
- cirq/transformers/optimize_for_target_gateset_test.py +11 -8
- cirq/transformers/qubit_management_transformers.py +13 -11
- cirq/transformers/qubit_management_transformers_test.py +5 -3
- cirq/transformers/randomized_measurements.py +16 -14
- cirq/transformers/randomized_measurements_test.py +10 -4
- cirq/transformers/routing/initial_mapper.py +6 -4
- cirq/transformers/routing/initial_mapper_test.py +2 -0
- cirq/transformers/routing/line_initial_mapper.py +16 -14
- cirq/transformers/routing/line_initial_mapper_test.py +9 -7
- cirq/transformers/routing/mapping_manager.py +10 -10
- cirq/transformers/routing/mapping_manager_test.py +2 -0
- cirq/transformers/routing/route_circuit_cqc.py +33 -31
- cirq/transformers/routing/route_circuit_cqc_test.py +15 -13
- cirq/transformers/routing/visualize_routed_circuit.py +8 -7
- cirq/transformers/routing/visualize_routed_circuit_test.py +4 -2
- cirq/transformers/stratify.py +17 -15
- cirq/transformers/stratify_test.py +3 -0
- cirq/transformers/symbolize.py +103 -0
- cirq/transformers/symbolize_test.py +62 -0
- cirq/transformers/synchronize_terminal_measurements.py +10 -10
- cirq/transformers/synchronize_terminal_measurements_test.py +12 -10
- cirq/transformers/tag_transformers.py +97 -0
- cirq/transformers/tag_transformers_test.py +103 -0
- cirq/transformers/target_gatesets/compilation_target_gateset.py +21 -19
- cirq/transformers/target_gatesets/compilation_target_gateset_test.py +20 -16
- cirq/transformers/target_gatesets/cz_gateset.py +7 -5
- cirq/transformers/target_gatesets/cz_gateset_test.py +21 -19
- cirq/transformers/target_gatesets/sqrt_iswap_gateset.py +9 -7
- cirq/transformers/target_gatesets/sqrt_iswap_gateset_test.py +25 -25
- cirq/transformers/transformer_api.py +34 -47
- cirq/transformers/transformer_api_test.py +9 -8
- cirq/transformers/transformer_primitives.py +39 -49
- cirq/transformers/transformer_primitives_test.py +10 -17
- cirq/value/abc_alt.py +6 -4
- cirq/value/abc_alt_test.py +5 -3
- cirq/value/angle.py +11 -12
- cirq/value/angle_test.py +5 -3
- cirq/value/classical_data.py +27 -27
- cirq/value/classical_data_test.py +11 -8
- cirq/value/condition.py +26 -24
- cirq/value/condition_test.py +2 -0
- cirq/value/digits.py +14 -11
- cirq/value/digits_test.py +2 -0
- cirq/value/duration.py +23 -20
- cirq/value/duration_test.py +2 -0
- cirq/value/linear_dict.py +25 -30
- cirq/value/linear_dict_test.py +10 -8
- cirq/value/measurement_key.py +12 -12
- cirq/value/measurement_key_test.py +2 -0
- cirq/value/periodic_value.py +4 -4
- cirq/value/periodic_value_test.py +11 -7
- cirq/value/probability.py +3 -1
- cirq/value/probability_test.py +4 -2
- cirq/value/product_state.py +15 -13
- cirq/value/product_state_test.py +4 -1
- cirq/value/random_state.py +2 -0
- cirq/value/random_state_test.py +5 -3
- cirq/value/timestamp.py +11 -7
- cirq/value/timestamp_test.py +14 -12
- cirq/value/type_alias.py +4 -4
- cirq/value/value_equality_attr.py +8 -9
- cirq/value/value_equality_attr_test.py +14 -11
- cirq/vis/density_matrix.py +3 -3
- cirq/vis/density_matrix_test.py +20 -17
- cirq/vis/heatmap.py +24 -37
- cirq/vis/heatmap_test.py +3 -0
- cirq/vis/histogram.py +9 -6
- cirq/vis/histogram_test.py +5 -2
- cirq/vis/state_histogram.py +10 -8
- cirq/vis/state_histogram_test.py +7 -5
- cirq/vis/vis_utils.py +4 -1
- cirq/vis/vis_utils_test.py +4 -1
- cirq/work/collector.py +12 -18
- cirq/work/collector_test.py +15 -10
- cirq/work/observable_grouping.py +6 -7
- cirq/work/observable_grouping_test.py +10 -9
- cirq/work/observable_measurement.py +47 -45
- cirq/work/observable_measurement_data.py +22 -17
- cirq/work/observable_measurement_data_test.py +4 -1
- cirq/work/observable_measurement_test.py +48 -29
- cirq/work/observable_readout_calibration.py +5 -2
- cirq/work/observable_readout_calibration_test.py +5 -2
- cirq/work/observable_settings.py +13 -22
- cirq/work/observable_settings_test.py +9 -7
- cirq/work/pauli_sum_collector.py +12 -10
- cirq/work/pauli_sum_collector_test.py +9 -9
- cirq/work/sampler.py +42 -43
- cirq/work/sampler_test.py +31 -24
- cirq/work/zeros_sampler.py +6 -4
- cirq/work/zeros_sampler_test.py +7 -5
- {cirq_core-1.5.0.dev20250409225226.dist-info → cirq_core-1.6.0.dist-info}/METADATA +7 -8
- cirq_core-1.6.0.dist-info/RECORD +1241 -0
- {cirq_core-1.5.0.dev20250409225226.dist-info → cirq_core-1.6.0.dist-info}/WHEEL +1 -1
- cirq_core-1.5.0.dev20250409225226.dist-info/RECORD +0 -1216
- {cirq_core-1.5.0.dev20250409225226.dist-info → cirq_core-1.6.0.dist-info}/licenses/LICENSE +0 -0
- {cirq_core-1.5.0.dev20250409225226.dist-info → cirq_core-1.6.0.dist-info}/top_level.txt +0 -0
|
@@ -12,6 +12,8 @@
|
|
|
12
12
|
# See the License for the specific language governing permissions and
|
|
13
13
|
# limitations under the License.
|
|
14
14
|
|
|
15
|
+
from __future__ import annotations
|
|
16
|
+
|
|
15
17
|
import itertools
|
|
16
18
|
|
|
17
19
|
import pytest
|
|
@@ -162,9 +164,11 @@ circuit_diagrams = {
|
|
|
162
164
|
│ │ │ │
|
|
163
165
|
3: ─────────────█───1↦0───────█───1↦0─────────────
|
|
164
166
|
""",
|
|
165
|
-
(
|
|
166
|
-
|
|
167
|
-
|
|
167
|
+
(
|
|
168
|
+
'decomposed',
|
|
169
|
+
cca.BipartiteGraphType.COMPLETE,
|
|
170
|
+
3,
|
|
171
|
+
): """
|
|
168
172
|
0: ───────────────────────█───0↦1───────────────────────────█───0↦1───────────────────────
|
|
169
173
|
│ │ │ │
|
|
170
174
|
1: ─────────────█───0↦1───█───1↦0───█───0↦1───────█───0↦1───█───1↦0───█───0↦1─────────────
|
|
@@ -199,8 +203,7 @@ circuit_diagrams = {
|
|
|
199
203
|
│ │ │ │
|
|
200
204
|
7: ─────────────────────────────────█───1↦0───────────────────────────────────────────────█───1↦0─────────────────────────────────
|
|
201
205
|
|
|
202
|
-
""",
|
|
203
|
-
# pylint: enable=line-too-long
|
|
206
|
+
""", # noqa: E501
|
|
204
207
|
(
|
|
205
208
|
'decomposed',
|
|
206
209
|
cca.BipartiteGraphType.MATCHING,
|
|
@@ -267,7 +270,7 @@ circuit_diagrams = {
|
|
|
267
270
|
@pytest.mark.parametrize(
|
|
268
271
|
'subgraph,part_size', itertools.product(cca.BipartiteGraphType, range(1, 5))
|
|
269
272
|
)
|
|
270
|
-
def test_circuit_diagrams(part_size, subgraph):
|
|
273
|
+
def test_circuit_diagrams(part_size, subgraph) -> None:
|
|
271
274
|
qubits = cirq.LineQubit.range(2 * part_size)
|
|
272
275
|
gate = cca.BipartiteSwapNetworkGate(subgraph, part_size)
|
|
273
276
|
circuit = cirq.Circuit(gate(*qubits))
|
|
@@ -282,10 +285,10 @@ def test_circuit_diagrams(part_size, subgraph):
|
|
|
282
285
|
cirq.testing.assert_has_diagram(circuit, diagram)
|
|
283
286
|
|
|
284
287
|
|
|
285
|
-
def test_bad_args():
|
|
288
|
+
def test_bad_args() -> None:
|
|
286
289
|
gate = cca.BipartiteSwapNetworkGate(cca.BipartiteGraphType.COMPLETE, 2)
|
|
287
290
|
qubits = cirq.LineQubit.range(4)
|
|
288
|
-
gate.subgraph = 'not a subgraph'
|
|
291
|
+
gate.subgraph = 'not a subgraph' # type: ignore[assignment]
|
|
289
292
|
args = cirq.CircuitDiagramInfoArgs(
|
|
290
293
|
known_qubits=None,
|
|
291
294
|
known_qubit_count=None,
|
|
@@ -303,7 +306,7 @@ def test_bad_args():
|
|
|
303
306
|
with pytest.raises(ValueError):
|
|
304
307
|
gate._decompose_(qubits[:3])
|
|
305
308
|
|
|
306
|
-
gate.subgraph = 'unimplemented subgraph'
|
|
309
|
+
gate.subgraph = 'unimplemented subgraph' # type: ignore[assignment]
|
|
307
310
|
with pytest.raises(NotImplementedError):
|
|
308
311
|
gate._decompose_(qubits)
|
|
309
312
|
|
|
@@ -312,7 +315,7 @@ def test_bad_args():
|
|
|
312
315
|
gate._circuit_diagram_info_(args)
|
|
313
316
|
|
|
314
317
|
|
|
315
|
-
def test_bipartite_swap_network_acquaintance_size():
|
|
318
|
+
def test_bipartite_swap_network_acquaintance_size() -> None:
|
|
316
319
|
qubits = cirq.LineQubit.range(4)
|
|
317
320
|
gate = cca.BipartiteSwapNetworkGate(cca.BipartiteGraphType.COMPLETE, 2)
|
|
318
321
|
assert cca.get_acquaintance_size(gate(*qubits)) == 2
|
|
@@ -321,7 +324,7 @@ def test_bipartite_swap_network_acquaintance_size():
|
|
|
321
324
|
@pytest.mark.parametrize(
|
|
322
325
|
'subgraph,part_size', itertools.product(cca.BipartiteGraphType, range(1, 3))
|
|
323
326
|
)
|
|
324
|
-
def test_repr(subgraph, part_size):
|
|
327
|
+
def test_repr(subgraph, part_size) -> None:
|
|
325
328
|
gate = cca.BipartiteSwapNetworkGate(subgraph, part_size)
|
|
326
329
|
cirq.testing.assert_equivalent_repr(gate)
|
|
327
330
|
|
|
@@ -332,18 +335,20 @@ def test_repr(subgraph, part_size):
|
|
|
332
335
|
@pytest.mark.parametrize(
|
|
333
336
|
'subgraph,part_size', itertools.product(cca.BipartiteGraphType, range(1, 6))
|
|
334
337
|
)
|
|
335
|
-
def test_decomposition_permutation_consistency(part_size, subgraph):
|
|
338
|
+
def test_decomposition_permutation_consistency(part_size, subgraph) -> None:
|
|
336
339
|
gate = cca.BipartiteSwapNetworkGate(subgraph, part_size)
|
|
337
340
|
qubits = cirq.LineQubit.range(2 * part_size)
|
|
341
|
+
mapping: dict[cirq.Qid, int]
|
|
338
342
|
mapping = {q: i for i, q in enumerate(qubits)}
|
|
339
343
|
cca.update_mapping(mapping, gate._decompose_(qubits))
|
|
340
344
|
permutation = gate.permutation()
|
|
341
345
|
assert {qubits[i]: j for i, j in permutation.items()} == mapping
|
|
342
346
|
|
|
343
347
|
|
|
344
|
-
def test_bad_number_of_qubits():
|
|
348
|
+
def test_bad_number_of_qubits() -> None:
|
|
345
349
|
gate = cca.BipartiteSwapNetworkGate(cca.BipartiteGraphType.COMPLETE, 6)
|
|
346
350
|
qubits = cirq.LineQubit.range(6)
|
|
351
|
+
mapping: dict[cirq.Qid, int]
|
|
347
352
|
mapping = {q: i for i, q in enumerate(qubits)}
|
|
348
353
|
with pytest.raises(ValueError, match='len'):
|
|
349
354
|
cca.update_mapping(mapping, gate._decompose_(qubits))
|
|
@@ -15,7 +15,7 @@
|
|
|
15
15
|
from __future__ import annotations
|
|
16
16
|
|
|
17
17
|
import abc
|
|
18
|
-
from typing import TYPE_CHECKING
|
|
18
|
+
from typing import TYPE_CHECKING
|
|
19
19
|
|
|
20
20
|
from cirq import circuits, devices, ops
|
|
21
21
|
from cirq.contrib.acquaintance.bipartite import BipartiteSwapNetworkGate
|
|
@@ -42,7 +42,7 @@ class AcquaintanceDevice(devices.Device, metaclass=abc.ABCMeta):
|
|
|
42
42
|
)
|
|
43
43
|
|
|
44
44
|
|
|
45
|
-
def get_acquaintance_size(obj:
|
|
45
|
+
def get_acquaintance_size(obj: circuits.Circuit | ops.Operation) -> int:
|
|
46
46
|
"""The maximum number of qubits to be acquainted with each other."""
|
|
47
47
|
if isinstance(obj, circuits.Circuit):
|
|
48
48
|
return max(tuple(get_acquaintance_size(op) for op in obj.all_operations()) or (0,))
|
|
@@ -12,13 +12,15 @@
|
|
|
12
12
|
# See the License for the specific language governing permissions and
|
|
13
13
|
# limitations under the License.
|
|
14
14
|
|
|
15
|
+
from __future__ import annotations
|
|
16
|
+
|
|
15
17
|
import pytest
|
|
16
18
|
|
|
17
19
|
import cirq
|
|
18
20
|
import cirq.contrib.acquaintance as cca
|
|
19
21
|
|
|
20
22
|
|
|
21
|
-
def test_acquaintance_device():
|
|
23
|
+
def test_acquaintance_device() -> None:
|
|
22
24
|
with pytest.raises(ValueError):
|
|
23
25
|
op = cirq.X(cirq.NamedQubit('q'))
|
|
24
26
|
cca.UnconstrainedAcquaintanceDevice.validate_operation(op)
|
|
@@ -29,6 +31,6 @@ def test_acquaintance_device():
|
|
|
29
31
|
cca.UnconstrainedAcquaintanceDevice.validate_operation(swap_network(*qubits))
|
|
30
32
|
|
|
31
33
|
|
|
32
|
-
def test_not_operation():
|
|
34
|
+
def test_not_operation() -> None:
|
|
33
35
|
with pytest.raises(TypeError):
|
|
34
|
-
_ = cca.get_acquaintance_size(cirq.LineQubit(1))
|
|
36
|
+
_ = cca.get_acquaintance_size(cirq.LineQubit(1)) # type: ignore[arg-type]
|
|
@@ -16,7 +16,7 @@ from __future__ import annotations
|
|
|
16
16
|
|
|
17
17
|
import abc
|
|
18
18
|
from collections import defaultdict
|
|
19
|
-
from typing import
|
|
19
|
+
from typing import Iterator, Sequence, TYPE_CHECKING
|
|
20
20
|
|
|
21
21
|
from cirq import circuits, devices, ops, protocols, transformers
|
|
22
22
|
from cirq.contrib.acquaintance.gates import AcquaintanceOpportunityGate
|
|
@@ -99,7 +99,7 @@ class StrategyExecutorTransformer:
|
|
|
99
99
|
self._mapping = execution_strategy.initial_mapping.copy()
|
|
100
100
|
|
|
101
101
|
def __call__(
|
|
102
|
-
self, circuit: circuits.AbstractCircuit, context:
|
|
102
|
+
self, circuit: circuits.AbstractCircuit, context: cirq.TransformerContext | None = None
|
|
103
103
|
) -> circuits.Circuit:
|
|
104
104
|
"""Executes an acquaintance strategy using cirq.map_operations_and_unroll and
|
|
105
105
|
mutates initial mapping.
|
|
@@ -174,7 +174,7 @@ class GreedyExecutionStrategy(ExecutionStrategy):
|
|
|
174
174
|
self,
|
|
175
175
|
gates: LogicalGates,
|
|
176
176
|
initial_mapping: LogicalMapping,
|
|
177
|
-
device:
|
|
177
|
+
device: cirq.Device | None = None,
|
|
178
178
|
) -> None:
|
|
179
179
|
"""Inits GreedyExecutionStrategy.
|
|
180
180
|
|
|
@@ -214,13 +214,13 @@ class GreedyExecutionStrategy(ExecutionStrategy):
|
|
|
214
214
|
yield gate(*[index_to_qubit[i] for i in gate_indices])
|
|
215
215
|
|
|
216
216
|
@staticmethod
|
|
217
|
-
def canonicalize_gates(gates: LogicalGates) ->
|
|
217
|
+
def canonicalize_gates(gates: LogicalGates) -> dict[frozenset, LogicalGates]:
|
|
218
218
|
"""Canonicalizes a set of gates by the qubits they act on.
|
|
219
219
|
|
|
220
220
|
Takes a set of gates specified by ordered sequences of logical
|
|
221
221
|
indices, and groups those that act on the same qubits regardless of
|
|
222
222
|
order."""
|
|
223
|
-
canonicalized_gates:
|
|
223
|
+
canonicalized_gates: defaultdict[frozenset, LogicalGates] = defaultdict(dict)
|
|
224
224
|
for indices, gate in gates.items():
|
|
225
225
|
indices = tuple(indices)
|
|
226
226
|
canonicalized_gates[frozenset(indices)][indices] = gate
|
|
@@ -12,9 +12,11 @@
|
|
|
12
12
|
# See the License for the specific language governing permissions and
|
|
13
13
|
# limitations under the License.
|
|
14
14
|
|
|
15
|
+
from __future__ import annotations
|
|
16
|
+
|
|
15
17
|
from itertools import combinations
|
|
16
18
|
from string import ascii_lowercase
|
|
17
|
-
from typing import
|
|
19
|
+
from typing import Any, Sequence
|
|
18
20
|
|
|
19
21
|
import numpy as np
|
|
20
22
|
import pytest
|
|
@@ -36,11 +38,12 @@ class ExampleGate(cirq.Gate):
|
|
|
36
38
|
return self._wire_symbols
|
|
37
39
|
|
|
38
40
|
|
|
39
|
-
def test_executor_explicit():
|
|
41
|
+
def test_executor_explicit() -> None:
|
|
40
42
|
num_qubits = 8
|
|
41
43
|
qubits = cirq.LineQubit.range(num_qubits)
|
|
42
44
|
circuit = cca.complete_acquaintance_strategy(qubits, 2)
|
|
43
45
|
|
|
46
|
+
gates: dict[tuple[Any, ...], cirq.Gate]
|
|
44
47
|
gates = {
|
|
45
48
|
(i, j): ExampleGate([str(k) for k in ij])
|
|
46
49
|
for ij in combinations(range(num_qubits), 2)
|
|
@@ -51,10 +54,11 @@ def test_executor_explicit():
|
|
|
51
54
|
assert execution_strategy.device == cirq.UNCONSTRAINED_DEVICE
|
|
52
55
|
|
|
53
56
|
with pytest.raises(ValueError):
|
|
54
|
-
executor = cca.StrategyExecutorTransformer(None)
|
|
57
|
+
executor = cca.StrategyExecutorTransformer(None) # type: ignore[arg-type]
|
|
55
58
|
executor = cca.StrategyExecutorTransformer(execution_strategy)
|
|
56
59
|
|
|
57
60
|
with pytest.raises(NotImplementedError):
|
|
61
|
+
bad_gates: dict[tuple[Any, ...], cirq.Gate]
|
|
58
62
|
bad_gates = {(0,): ExampleGate(['0']), (0, 1): ExampleGate(['0', '1'])}
|
|
59
63
|
cca.GreedyExecutionStrategy(bad_gates, initial_mapping)
|
|
60
64
|
|
|
@@ -79,13 +83,13 @@ def test_executor_explicit():
|
|
|
79
83
|
6: ───6───7───╲0╱───7───4───╱1╲───4───6───╲0╱───6───2───╱1╲───2───4───╲0╱───4───0───╱1╲───0───2───╲0╱───2───1───╱1╲───
|
|
80
84
|
│ │ │ │ │ │ │ │ │ │ │ │
|
|
81
85
|
7: ───7───6───╱1╲─────────────────6───4───╱1╲─────────────────4───2───╱1╲─────────────────2───0───╱1╲─────────────────
|
|
82
|
-
""".strip()
|
|
86
|
+
""".strip() # noqa: E501
|
|
83
87
|
ct.assert_has_diagram(circuit, expected_text_diagram)
|
|
84
88
|
|
|
85
89
|
|
|
86
90
|
def random_diagonal_gates(
|
|
87
91
|
num_qubits: int, acquaintance_size: int
|
|
88
|
-
) ->
|
|
92
|
+
) -> dict[tuple[cirq.Qid, ...], cirq.Gate]:
|
|
89
93
|
|
|
90
94
|
return {
|
|
91
95
|
Q: cirq.DiagonalGate(np.random.random(2**acquaintance_size))
|
|
@@ -104,8 +108,8 @@ def random_diagonal_gates(
|
|
|
104
108
|
],
|
|
105
109
|
)
|
|
106
110
|
def test_executor_random(
|
|
107
|
-
num_qubits: int, acquaintance_size: int, gates:
|
|
108
|
-
):
|
|
111
|
+
num_qubits: int, acquaintance_size: int, gates: dict[tuple[cirq.Qid, ...], cirq.Gate]
|
|
112
|
+
) -> None:
|
|
109
113
|
qubits = cirq.LineQubit.range(num_qubits)
|
|
110
114
|
circuit = cca.complete_acquaintance_strategy(qubits, acquaintance_size)
|
|
111
115
|
|
|
@@ -124,7 +128,7 @@ def test_executor_random(
|
|
|
124
128
|
np.testing.assert_allclose(actual=actual_unitary, desired=expected_unitary, verbose=True)
|
|
125
129
|
|
|
126
130
|
|
|
127
|
-
def test_acquaintance_operation():
|
|
131
|
+
def test_acquaintance_operation() -> None:
|
|
128
132
|
n = 5
|
|
129
133
|
physical_qubits = tuple(cirq.LineQubit.range(n))
|
|
130
134
|
logical_qubits = tuple(cirq.NamedQubit(s) for s in ascii_lowercase[:n])
|
|
@@ -132,7 +136,7 @@ def test_acquaintance_operation():
|
|
|
132
136
|
with pytest.raises(ValueError):
|
|
133
137
|
cca.AcquaintanceOperation(physical_qubits[:3], int_indices[:4])
|
|
134
138
|
for logical_indices in (logical_qubits, int_indices):
|
|
135
|
-
op = cca.AcquaintanceOperation(physical_qubits, logical_indices)
|
|
139
|
+
op = cca.AcquaintanceOperation(physical_qubits, logical_indices) # type: ignore[type-var]
|
|
136
140
|
assert op.logical_indices == logical_indices
|
|
137
141
|
assert op.qubits == physical_qubits
|
|
138
142
|
wire_symbols = tuple(f'({i})' for i in logical_indices)
|
|
@@ -18,17 +18,7 @@ import functools
|
|
|
18
18
|
import itertools
|
|
19
19
|
import math
|
|
20
20
|
import operator
|
|
21
|
-
from typing import
|
|
22
|
-
Dict,
|
|
23
|
-
Iterable,
|
|
24
|
-
Iterator,
|
|
25
|
-
List,
|
|
26
|
-
NamedTuple,
|
|
27
|
-
Optional,
|
|
28
|
-
Sequence,
|
|
29
|
-
Tuple,
|
|
30
|
-
TYPE_CHECKING,
|
|
31
|
-
)
|
|
21
|
+
from typing import Iterable, Iterator, NamedTuple, Sequence, TYPE_CHECKING
|
|
32
22
|
|
|
33
23
|
from cirq import ops, protocols, value
|
|
34
24
|
from cirq.contrib.acquaintance.permutation import (
|
|
@@ -44,14 +34,14 @@ if TYPE_CHECKING:
|
|
|
44
34
|
|
|
45
35
|
def operations_to_part_lens(
|
|
46
36
|
qubit_order: Sequence[cirq.Qid], op_tree: cirq.OP_TREE
|
|
47
|
-
) ->
|
|
37
|
+
) -> tuple[int, ...]:
|
|
48
38
|
qubit_sort_key = functools.partial(operator.indexOf, qubit_order)
|
|
49
39
|
op_parts = [tuple(sorted(op.qubits, key=qubit_sort_key)) for op in ops.flatten_op_tree(op_tree)]
|
|
50
|
-
singletons:
|
|
40
|
+
singletons: list[tuple[cirq.Qid, ...]] = [(q,) for q in set(qubit_order).difference(*op_parts)]
|
|
51
41
|
part_sort_key = lambda p: min(qubit_sort_key(q) for q in p)
|
|
52
42
|
parts = tuple(tuple(part) for part in sorted(singletons + op_parts, key=part_sort_key))
|
|
53
43
|
|
|
54
|
-
if
|
|
44
|
+
if tuple(itertools.chain.from_iterable(parts)) != tuple(qubit_order):
|
|
55
45
|
raise ValueError('sum(parts, ()) != tuple(qubit_order)')
|
|
56
46
|
|
|
57
47
|
return tuple(len(part) for part in parts)
|
|
@@ -87,16 +77,16 @@ def acquaint(*qubits) -> cirq.Operation:
|
|
|
87
77
|
Layers = NamedTuple(
|
|
88
78
|
'Layers',
|
|
89
79
|
[
|
|
90
|
-
('prior_interstitial',
|
|
91
|
-
('pre',
|
|
92
|
-
('intra',
|
|
93
|
-
('post',
|
|
94
|
-
('posterior_interstitial',
|
|
80
|
+
('prior_interstitial', list['cirq.Operation']),
|
|
81
|
+
('pre', list['cirq.Operation']),
|
|
82
|
+
('intra', list['cirq.Operation']),
|
|
83
|
+
('post', list['cirq.Operation']),
|
|
84
|
+
('posterior_interstitial', list['cirq.Operation']),
|
|
95
85
|
],
|
|
96
86
|
)
|
|
97
87
|
|
|
98
88
|
|
|
99
|
-
def new_layers(**kwargs:
|
|
89
|
+
def new_layers(**kwargs: list[cirq.Operation]) -> Layers:
|
|
100
90
|
return Layers._make(kwargs.get(field, []) for field in Layers._fields)
|
|
101
91
|
|
|
102
92
|
|
|
@@ -106,7 +96,7 @@ def acquaint_insides(
|
|
|
106
96
|
qubits: Sequence[cirq.Qid],
|
|
107
97
|
before: bool,
|
|
108
98
|
layers: Layers,
|
|
109
|
-
mapping:
|
|
99
|
+
mapping: dict[ops.Qid, int],
|
|
110
100
|
) -> None:
|
|
111
101
|
"""Acquaints each of the qubits with another set specified by an
|
|
112
102
|
acquaintance gate.
|
|
@@ -153,12 +143,12 @@ def _get_max_reach(size: int, round_up: bool = True) -> int:
|
|
|
153
143
|
|
|
154
144
|
|
|
155
145
|
def acquaint_and_shift(
|
|
156
|
-
parts:
|
|
146
|
+
parts: tuple[list[cirq.Qid], list[cirq.Qid]],
|
|
157
147
|
layers: Layers,
|
|
158
|
-
acquaintance_size:
|
|
148
|
+
acquaintance_size: int | None,
|
|
159
149
|
swap_gate: cirq.Gate,
|
|
160
|
-
mapping:
|
|
161
|
-
):
|
|
150
|
+
mapping: dict[ops.Qid, int],
|
|
151
|
+
) -> None:
|
|
162
152
|
"""Acquaints and shifts a pair of lists of qubits. The first part is
|
|
163
153
|
acquainted with every qubit individually in the second part, and vice
|
|
164
154
|
versa. Operations are grouped into several layers:
|
|
@@ -276,7 +266,7 @@ class SwapNetworkGate(PermutationGate):
|
|
|
276
266
|
def __init__(
|
|
277
267
|
self,
|
|
278
268
|
part_lens: Sequence[int],
|
|
279
|
-
acquaintance_size:
|
|
269
|
+
acquaintance_size: int | None = 0,
|
|
280
270
|
swap_gate: cirq.Gate = ops.SWAP,
|
|
281
271
|
) -> None:
|
|
282
272
|
super().__init__(sum(part_lens), swap_gate)
|
|
@@ -346,13 +336,13 @@ class SwapNetworkGate(PermutationGate):
|
|
|
346
336
|
def from_operations(
|
|
347
337
|
qubit_order: Sequence[cirq.Qid],
|
|
348
338
|
operations: Sequence[cirq.Operation],
|
|
349
|
-
acquaintance_size:
|
|
339
|
+
acquaintance_size: int | None = 0,
|
|
350
340
|
swap_gate: cirq.Gate = ops.SWAP,
|
|
351
341
|
) -> SwapNetworkGate:
|
|
352
342
|
part_sizes = operations_to_part_lens(qubit_order, operations)
|
|
353
343
|
return SwapNetworkGate(part_sizes, acquaintance_size, swap_gate)
|
|
354
344
|
|
|
355
|
-
def permutation(self) ->
|
|
345
|
+
def permutation(self) -> dict[int, int]:
|
|
356
346
|
return {i: j for i, j in enumerate(reversed(range(sum(self.part_lens))))}
|
|
357
347
|
|
|
358
348
|
def __repr__(self) -> str:
|
|
@@ -12,10 +12,12 @@
|
|
|
12
12
|
# See the License for the specific language governing permissions and
|
|
13
13
|
# limitations under the License.
|
|
14
14
|
|
|
15
|
+
from __future__ import annotations
|
|
16
|
+
|
|
15
17
|
from itertools import combinations, product
|
|
16
18
|
from random import randint
|
|
17
19
|
from string import ascii_lowercase as alphabet
|
|
18
|
-
from typing import
|
|
20
|
+
from typing import Sequence
|
|
19
21
|
|
|
20
22
|
import numpy
|
|
21
23
|
import pytest
|
|
@@ -25,7 +27,7 @@ import cirq.contrib.acquaintance as cca
|
|
|
25
27
|
import cirq.testing as ct
|
|
26
28
|
|
|
27
29
|
|
|
28
|
-
def test_acquaintance_gate_repr():
|
|
30
|
+
def test_acquaintance_gate_repr() -> None:
|
|
29
31
|
assert (
|
|
30
32
|
repr(cca.AcquaintanceOpportunityGate(2))
|
|
31
33
|
== 'cirq.contrib.acquaintance.AcquaintanceOpportunityGate'
|
|
@@ -33,7 +35,7 @@ def test_acquaintance_gate_repr():
|
|
|
33
35
|
)
|
|
34
36
|
|
|
35
37
|
|
|
36
|
-
def test_acquaintance_gate_text_diagram_info():
|
|
38
|
+
def test_acquaintance_gate_text_diagram_info() -> None:
|
|
37
39
|
qubits = [cirq.NamedQubit(s) for s in 'xyz']
|
|
38
40
|
circuit = cirq.Circuit([cirq.Moment([cca.acquaint(*qubits)])])
|
|
39
41
|
actual_text_diagram = circuit.to_text_diagram().strip()
|
|
@@ -47,11 +49,11 @@ z: ───█───
|
|
|
47
49
|
assert actual_text_diagram == expected_text_diagram
|
|
48
50
|
|
|
49
51
|
|
|
50
|
-
def test_acquaintance_gate_unknown_qubit_count():
|
|
52
|
+
def test_acquaintance_gate_unknown_qubit_count() -> None:
|
|
51
53
|
assert cirq.circuit_diagram_info(cca.acquaint, default=None) is None
|
|
52
54
|
|
|
53
55
|
|
|
54
|
-
def test_swap_network_gate():
|
|
56
|
+
def test_swap_network_gate() -> None:
|
|
55
57
|
qubits = tuple(cirq.NamedQubit(s) for s in alphabet)
|
|
56
58
|
|
|
57
59
|
acquaintance_size = 3
|
|
@@ -123,7 +125,7 @@ f: ───╱1╲─────────╱1╲─────────
|
|
|
123
125
|
@pytest.mark.parametrize(
|
|
124
126
|
'part_lens', [tuple(randint(1, 3) for _ in range(randint(2, 10))) for _ in range(3)]
|
|
125
127
|
)
|
|
126
|
-
def test_acquaint_part_pairs(part_lens):
|
|
128
|
+
def test_acquaint_part_pairs(part_lens) -> None:
|
|
127
129
|
parts = []
|
|
128
130
|
n_qubits = 0
|
|
129
131
|
for part_len in part_lens:
|
|
@@ -139,7 +141,7 @@ def test_acquaint_part_pairs(part_lens):
|
|
|
139
141
|
assert expected_opps == actual_opps
|
|
140
142
|
|
|
141
143
|
|
|
142
|
-
acquaintance_sizes:
|
|
144
|
+
acquaintance_sizes: tuple[int | None, ...] = (None,)
|
|
143
145
|
acquaintance_sizes += tuple(range(5))
|
|
144
146
|
|
|
145
147
|
|
|
@@ -152,13 +154,13 @@ acquaintance_sizes += tuple(range(5))
|
|
|
152
154
|
)
|
|
153
155
|
),
|
|
154
156
|
)
|
|
155
|
-
def test_swap_network_gate_permutation(part_lens, acquaintance_size):
|
|
157
|
+
def test_swap_network_gate_permutation(part_lens, acquaintance_size) -> None:
|
|
156
158
|
n_qubits = sum(part_lens)
|
|
157
159
|
swap_network_gate = cca.SwapNetworkGate(part_lens, acquaintance_size)
|
|
158
160
|
cca.testing.assert_permutation_decomposition_equivalence(swap_network_gate, n_qubits)
|
|
159
161
|
|
|
160
162
|
|
|
161
|
-
def test_swap_network_gate_from_ops():
|
|
163
|
+
def test_swap_network_gate_from_ops() -> None:
|
|
162
164
|
n_qubits = 10
|
|
163
165
|
qubits = cirq.LineQubit.range(n_qubits)
|
|
164
166
|
part_lens = (1, 2, 1, 3, 3)
|
|
@@ -196,7 +198,7 @@ def test_swap_network_gate_from_ops():
|
|
|
196
198
|
cirq.testing.assert_has_diagram(circuit, expected_diagram)
|
|
197
199
|
|
|
198
200
|
|
|
199
|
-
def test_swap_network_decomposition():
|
|
201
|
+
def test_swap_network_decomposition() -> None:
|
|
200
202
|
qubits = cirq.LineQubit.range(8)
|
|
201
203
|
swap_network_gate = cca.SwapNetworkGate((4, 4), 5)
|
|
202
204
|
operations = cirq.decompose_once_with_qubits(swap_network_gate, qubits)
|
|
@@ -221,7 +223,7 @@ def test_swap_network_decomposition():
|
|
|
221
223
|
ct.assert_has_diagram(circuit, expected_text_diagram)
|
|
222
224
|
|
|
223
225
|
|
|
224
|
-
def test_swap_network_init_error():
|
|
226
|
+
def test_swap_network_init_error() -> None:
|
|
225
227
|
with pytest.raises(ValueError):
|
|
226
228
|
cca.SwapNetworkGate(())
|
|
227
229
|
with pytest.raises(ValueError):
|
|
@@ -235,7 +237,7 @@ part_lens_and_acquaintance_sizes = [
|
|
|
235
237
|
|
|
236
238
|
|
|
237
239
|
@pytest.mark.parametrize('part_lens, acquaintance_size', part_lens_and_acquaintance_sizes)
|
|
238
|
-
def test_swap_network_permutation(part_lens, acquaintance_size):
|
|
240
|
+
def test_swap_network_permutation(part_lens, acquaintance_size) -> None:
|
|
239
241
|
n_qubits = sum(part_lens)
|
|
240
242
|
gate = cca.SwapNetworkGate(part_lens, acquaintance_size)
|
|
241
243
|
|
|
@@ -244,7 +246,7 @@ def test_swap_network_permutation(part_lens, acquaintance_size):
|
|
|
244
246
|
|
|
245
247
|
|
|
246
248
|
@pytest.mark.parametrize('part_lens, acquaintance_size', part_lens_and_acquaintance_sizes)
|
|
247
|
-
def test_swap_network_repr(part_lens, acquaintance_size):
|
|
249
|
+
def test_swap_network_repr(part_lens, acquaintance_size) -> None:
|
|
248
250
|
gate = cca.SwapNetworkGate(part_lens, acquaintance_size)
|
|
249
251
|
ct.assert_equivalent_repr(gate)
|
|
250
252
|
|
|
@@ -254,20 +256,22 @@ class OtherOperation(cirq.Operation):
|
|
|
254
256
|
self._qubits = tuple(qubits)
|
|
255
257
|
|
|
256
258
|
@property
|
|
257
|
-
def qubits(self) ->
|
|
259
|
+
def qubits(self) -> tuple[cirq.Qid, ...]:
|
|
258
260
|
return self._qubits
|
|
259
261
|
|
|
260
|
-
def with_qubits(self, *new_qubits: cirq.Qid) ->
|
|
261
|
-
return type(self)(
|
|
262
|
+
def with_qubits(self, *new_qubits: cirq.Qid) -> OtherOperation:
|
|
263
|
+
return type(self)(new_qubits)
|
|
262
264
|
|
|
263
265
|
def __eq__(self, other):
|
|
264
266
|
return isinstance(other, type(self)) and self.qubits == other.qubits
|
|
265
267
|
|
|
266
268
|
|
|
267
|
-
def test_get_acquaintance_size():
|
|
269
|
+
def test_get_acquaintance_size() -> None:
|
|
270
|
+
qubits: Sequence[cirq.Qid]
|
|
268
271
|
qubits = cirq.LineQubit.range(8)
|
|
272
|
+
op: cirq.Operation
|
|
269
273
|
op = OtherOperation(qubits)
|
|
270
|
-
assert op.with_qubits(qubits) == op
|
|
274
|
+
assert op.with_qubits(*qubits) == op
|
|
271
275
|
assert cca.get_acquaintance_size(op) == 0
|
|
272
276
|
|
|
273
277
|
for s, _ in enumerate(qubits):
|
|
@@ -299,7 +303,7 @@ def test_get_acquaintance_size():
|
|
|
299
303
|
assert cca.get_acquaintance_size(op) == 0
|
|
300
304
|
|
|
301
305
|
|
|
302
|
-
def test_operations_to_part_lens():
|
|
306
|
+
def test_operations_to_part_lens() -> None:
|
|
303
307
|
qubits = cirq.LineQubit.range(6)
|
|
304
308
|
ops = [cirq.CZ(*qubits[1:3]), cirq.XX(*qubits[3:5])]
|
|
305
309
|
part_lens = cca.gates.operations_to_part_lens(qubits, ops)
|
|
@@ -317,7 +321,7 @@ def test_operations_to_part_lens():
|
|
|
317
321
|
@pytest.mark.parametrize(
|
|
318
322
|
'part_len_sets', [set(tuple(randint(1, 5) for _ in range(randint(2, 7))) for _ in range(5))]
|
|
319
323
|
)
|
|
320
|
-
def test_swap_network_gate_equality(part_len_sets):
|
|
324
|
+
def test_swap_network_gate_equality(part_len_sets) -> None:
|
|
321
325
|
acquaintance_sizes = [None, 0, 1, 2, 3]
|
|
322
326
|
swap_gates = [cirq.SWAP, cirq.CNOT]
|
|
323
327
|
equals_tester = ct.EqualsTester()
|
|
@@ -14,7 +14,7 @@
|
|
|
14
14
|
|
|
15
15
|
from __future__ import annotations
|
|
16
16
|
|
|
17
|
-
from typing import
|
|
17
|
+
from typing import Iterator, Sequence, TYPE_CHECKING
|
|
18
18
|
|
|
19
19
|
from cirq import devices
|
|
20
20
|
from cirq.contrib import circuitdag
|
|
@@ -51,7 +51,9 @@ class LogicalAnnotator(ExecutionStrategy):
|
|
|
51
51
|
yield AcquaintanceOperation(qubits, indices)
|
|
52
52
|
|
|
53
53
|
|
|
54
|
-
def get_acquaintance_dag(
|
|
54
|
+
def get_acquaintance_dag(
|
|
55
|
+
strategy: cirq.Circuit, initial_mapping: LogicalMapping
|
|
56
|
+
) -> circuitdag.CircuitDag:
|
|
55
57
|
strategy = strategy.copy()
|
|
56
58
|
expose_acquaintance_gates(strategy)
|
|
57
59
|
LogicalAnnotator(initial_mapping)(strategy)
|
|
@@ -66,9 +68,11 @@ def get_acquaintance_dag(strategy: cirq.Circuit, initial_mapping: LogicalMapping
|
|
|
66
68
|
|
|
67
69
|
def get_logical_acquaintance_opportunities(
|
|
68
70
|
strategy: cirq.Circuit, initial_mapping: LogicalMapping
|
|
69
|
-
) ->
|
|
71
|
+
) -> set[frozenset[int]] | set[frozenset[cirq.Qid]]:
|
|
70
72
|
acquaintance_dag = get_acquaintance_dag(strategy, initial_mapping)
|
|
71
73
|
logical_acquaintance_opportunities = set()
|
|
72
74
|
for op in acquaintance_dag.all_operations():
|
|
73
|
-
logical_acquaintance_opportunities.add(
|
|
75
|
+
logical_acquaintance_opportunities.add(
|
|
76
|
+
frozenset(op.logical_indices) # type: ignore[attr-defined]
|
|
77
|
+
)
|
|
74
78
|
return logical_acquaintance_opportunities
|
|
@@ -12,6 +12,8 @@
|
|
|
12
12
|
# See the License for the specific language governing permissions and
|
|
13
13
|
# limitations under the License.
|
|
14
14
|
|
|
15
|
+
from __future__ import annotations
|
|
16
|
+
|
|
15
17
|
from itertools import combinations, product
|
|
16
18
|
|
|
17
19
|
import pytest
|
|
@@ -22,7 +24,7 @@ import cirq.contrib.acquaintance.inspection_utils as inspection_utils
|
|
|
22
24
|
|
|
23
25
|
|
|
24
26
|
@pytest.mark.parametrize('n_qubits, acquaintance_size', product(range(2, 6), range(2, 5)))
|
|
25
|
-
def test_get_logical_acquaintance_opportunities(n_qubits, acquaintance_size):
|
|
27
|
+
def test_get_logical_acquaintance_opportunities(n_qubits, acquaintance_size) -> None:
|
|
26
28
|
qubits = cirq.LineQubit.range(n_qubits)
|
|
27
29
|
acquaintance_strategy = cca.complete_acquaintance_strategy(qubits, acquaintance_size)
|
|
28
30
|
initial_mapping = {q: i for i, q in enumerate(qubits)}
|
|
@@ -30,5 +32,5 @@ def test_get_logical_acquaintance_opportunities(n_qubits, acquaintance_size):
|
|
|
30
32
|
assert opps == set(frozenset(s) for s in combinations(range(n_qubits), acquaintance_size))
|
|
31
33
|
|
|
32
34
|
|
|
33
|
-
def test_device():
|
|
35
|
+
def test_device() -> None:
|
|
34
36
|
assert inspection_utils.LogicalAnnotator({}).device == cirq.UNCONSTRAINED_DEVICE
|
|
@@ -15,7 +15,7 @@
|
|
|
15
15
|
from __future__ import annotations
|
|
16
16
|
|
|
17
17
|
import collections
|
|
18
|
-
from typing import cast,
|
|
18
|
+
from typing import cast, Sequence, TYPE_CHECKING
|
|
19
19
|
|
|
20
20
|
from cirq import circuits, ops, transformers
|
|
21
21
|
from cirq.contrib.acquaintance.devices import get_acquaintance_size
|
|
@@ -25,7 +25,7 @@ from cirq.contrib.acquaintance.permutation import PermutationGate
|
|
|
25
25
|
if TYPE_CHECKING:
|
|
26
26
|
import cirq
|
|
27
27
|
|
|
28
|
-
STRATEGY_GATE =
|
|
28
|
+
STRATEGY_GATE = AcquaintanceOpportunityGate | PermutationGate
|
|
29
29
|
|
|
30
30
|
|
|
31
31
|
def rectify_acquaintance_strategy(circuit: cirq.Circuit, acquaint_first: bool = True) -> None:
|
|
@@ -43,7 +43,7 @@ def rectify_acquaintance_strategy(circuit: cirq.Circuit, acquaint_first: bool =
|
|
|
43
43
|
"""
|
|
44
44
|
rectified_moments = []
|
|
45
45
|
for moment in circuit:
|
|
46
|
-
gate_type_to_ops:
|
|
46
|
+
gate_type_to_ops: dict[bool, list[ops.GateOperation]] = collections.defaultdict(list)
|
|
47
47
|
for op in moment.operations:
|
|
48
48
|
gate_op = cast(ops.GateOperation, op)
|
|
49
49
|
is_acquaintance = isinstance(gate_op.gate, AcquaintanceOpportunityGate)
|
|
@@ -59,7 +59,7 @@ def rectify_acquaintance_strategy(circuit: cirq.Circuit, acquaint_first: bool =
|
|
|
59
59
|
def replace_acquaintance_with_swap_network(
|
|
60
60
|
circuit: cirq.Circuit,
|
|
61
61
|
qubit_order: Sequence[cirq.Qid],
|
|
62
|
-
acquaintance_size:
|
|
62
|
+
acquaintance_size: int | None = 0,
|
|
63
63
|
swap_gate: cirq.Gate = ops.SWAP,
|
|
64
64
|
) -> bool:
|
|
65
65
|
"""Replace every rectified moment with acquaintance gates with a generalized swap network.
|
|
@@ -12,6 +12,8 @@
|
|
|
12
12
|
# See the License for the specific language governing permissions and
|
|
13
13
|
# limitations under the License.
|
|
14
14
|
|
|
15
|
+
from __future__ import annotations
|
|
16
|
+
|
|
15
17
|
from string import ascii_lowercase as alphabet
|
|
16
18
|
|
|
17
19
|
import pytest
|
|
@@ -20,7 +22,7 @@ import cirq
|
|
|
20
22
|
import cirq.contrib.acquaintance as cca
|
|
21
23
|
|
|
22
24
|
|
|
23
|
-
def test_complete_acquaintance_strategy():
|
|
25
|
+
def test_complete_acquaintance_strategy() -> None:
|
|
24
26
|
qubits = [cirq.NamedQubit(s) for s in alphabet]
|
|
25
27
|
|
|
26
28
|
with pytest.raises(ValueError):
|
|
@@ -136,7 +138,7 @@ a b c d
|
|
|
136
138
|
assert cca.get_acquaintance_size(cubic_strategy) == 3
|
|
137
139
|
|
|
138
140
|
|
|
139
|
-
def test_rectification():
|
|
141
|
+
def test_rectification() -> None:
|
|
140
142
|
qubits = cirq.LineQubit.range(4)
|
|
141
143
|
|
|
142
144
|
perm_gate = cca.SwapPermutationGate()
|