qiskit 1.3.0b1__cp39-abi3-win32.whl → 1.3.0rc2__cp39-abi3-win32.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.
- qiskit/VERSION.txt +1 -1
- qiskit/__init__.py +20 -1
- qiskit/_accelerate.pyd +0 -0
- qiskit/assembler/assemble_schedules.py +2 -0
- qiskit/circuit/__init__.py +44 -1
- qiskit/circuit/_standard_gates_commutations.py +585 -0
- qiskit/circuit/barrier.py +2 -0
- qiskit/circuit/controlflow/builder.py +3 -3
- qiskit/circuit/controlflow/if_else.py +13 -5
- qiskit/circuit/controlflow/while_loop.py +10 -2
- qiskit/circuit/delay.py +20 -3
- qiskit/circuit/equivalence.py +13 -214
- qiskit/circuit/gate.py +3 -1
- qiskit/circuit/instruction.py +32 -11
- qiskit/circuit/instructionset.py +2 -0
- qiskit/circuit/library/__init__.py +110 -14
- qiskit/circuit/library/arithmetic/__init__.py +9 -2
- qiskit/circuit/library/arithmetic/adders/__init__.py +1 -0
- qiskit/circuit/library/arithmetic/adders/adder.py +154 -2
- qiskit/circuit/library/arithmetic/adders/cdkm_ripple_carry_adder.py +20 -56
- qiskit/circuit/library/arithmetic/adders/draper_qft_adder.py +14 -1
- qiskit/circuit/library/arithmetic/adders/vbe_ripple_carry_adder.py +21 -91
- qiskit/circuit/library/arithmetic/linear_pauli_rotations.py +1 -1
- qiskit/circuit/library/arithmetic/multipliers/__init__.py +1 -0
- qiskit/circuit/library/arithmetic/multipliers/hrs_cumulative_multiplier.py +8 -1
- qiskit/circuit/library/arithmetic/multipliers/multiplier.py +94 -3
- qiskit/circuit/library/arithmetic/multipliers/rg_qft_multiplier.py +8 -1
- qiskit/circuit/library/arithmetic/weighted_adder.py +1 -1
- qiskit/circuit/library/basis_change/qft.py +20 -38
- qiskit/circuit/library/blueprintcircuit.py +64 -0
- qiskit/circuit/library/boolean_logic/__init__.py +4 -4
- qiskit/circuit/library/boolean_logic/inner_product.py +81 -4
- qiskit/circuit/library/boolean_logic/quantum_and.py +107 -4
- qiskit/circuit/library/boolean_logic/quantum_or.py +107 -3
- qiskit/circuit/library/boolean_logic/quantum_xor.py +97 -3
- qiskit/circuit/library/data_preparation/__init__.py +6 -3
- qiskit/circuit/library/data_preparation/{z_feature_map.py → _z_feature_map.py} +45 -34
- qiskit/circuit/library/data_preparation/_zz_feature_map.py +150 -0
- qiskit/circuit/library/data_preparation/pauli_feature_map.py +342 -29
- qiskit/circuit/library/fourier_checking.py +72 -11
- qiskit/circuit/library/generalized_gates/__init__.py +1 -1
- qiskit/circuit/library/generalized_gates/diagonal.py +45 -51
- qiskit/circuit/library/generalized_gates/gms.py +67 -14
- qiskit/circuit/library/generalized_gates/gr.py +4 -4
- qiskit/circuit/library/generalized_gates/isometry.py +2 -2
- qiskit/circuit/library/generalized_gates/linear_function.py +12 -6
- qiskit/circuit/library/generalized_gates/mcmt.py +167 -107
- qiskit/circuit/library/generalized_gates/permutation.py +8 -6
- qiskit/circuit/library/generalized_gates/rv.py +8 -9
- qiskit/circuit/library/graph_state.py +93 -10
- qiskit/circuit/library/grover_operator.py +270 -2
- qiskit/circuit/library/hidden_linear_function.py +83 -20
- qiskit/circuit/library/iqp.py +99 -20
- qiskit/circuit/library/n_local/__init__.py +19 -7
- qiskit/circuit/library/n_local/efficient_su2.py +118 -5
- qiskit/circuit/library/n_local/evolved_operator_ansatz.py +259 -0
- qiskit/circuit/library/n_local/excitation_preserving.py +130 -6
- qiskit/circuit/library/n_local/n_local.py +406 -5
- qiskit/circuit/library/n_local/pauli_two_design.py +106 -4
- qiskit/circuit/library/n_local/qaoa_ansatz.py +80 -1
- qiskit/circuit/library/n_local/real_amplitudes.py +127 -7
- qiskit/circuit/library/n_local/two_local.py +14 -7
- qiskit/circuit/library/overlap.py +91 -26
- qiskit/circuit/library/pauli_evolution.py +17 -15
- qiskit/circuit/library/phase_estimation.py +80 -4
- qiskit/circuit/library/quantum_volume.py +72 -20
- qiskit/circuit/library/standard_gates/__init__.py +20 -1
- qiskit/circuit/library/standard_gates/dcx.py +2 -1
- qiskit/circuit/library/standard_gates/ecr.py +2 -2
- qiskit/circuit/library/standard_gates/h.py +4 -3
- qiskit/circuit/library/standard_gates/i.py +2 -1
- qiskit/circuit/library/standard_gates/iswap.py +2 -2
- qiskit/circuit/library/standard_gates/p.py +20 -12
- qiskit/circuit/library/standard_gates/r.py +1 -1
- qiskit/circuit/library/standard_gates/rx.py +4 -3
- qiskit/circuit/library/standard_gates/rxx.py +2 -2
- qiskit/circuit/library/standard_gates/ry.py +4 -3
- qiskit/circuit/library/standard_gates/ryy.py +2 -2
- qiskit/circuit/library/standard_gates/rz.py +13 -12
- qiskit/circuit/library/standard_gates/rzx.py +6 -6
- qiskit/circuit/library/standard_gates/rzz.py +1 -1
- qiskit/circuit/library/standard_gates/s.py +4 -4
- qiskit/circuit/library/standard_gates/swap.py +3 -3
- qiskit/circuit/library/standard_gates/sx.py +4 -3
- qiskit/circuit/library/standard_gates/t.py +2 -2
- qiskit/circuit/library/standard_gates/u.py +11 -3
- qiskit/circuit/library/standard_gates/u1.py +65 -15
- qiskit/circuit/library/standard_gates/u2.py +4 -1
- qiskit/circuit/library/standard_gates/u3.py +31 -3
- qiskit/circuit/library/standard_gates/x.py +7 -5
- qiskit/circuit/library/standard_gates/xx_minus_yy.py +2 -2
- qiskit/circuit/library/standard_gates/xx_plus_yy.py +2 -2
- qiskit/circuit/library/standard_gates/y.py +4 -3
- qiskit/circuit/library/standard_gates/z.py +3 -3
- qiskit/circuit/library/templates/clifford/clifford_2_1.py +9 -8
- qiskit/circuit/library/templates/clifford/clifford_2_2.py +10 -9
- qiskit/circuit/library/templates/clifford/clifford_2_3.py +9 -7
- qiskit/circuit/library/templates/clifford/clifford_2_4.py +9 -8
- qiskit/circuit/library/templates/clifford/clifford_3_1.py +9 -8
- qiskit/circuit/library/templates/clifford/clifford_4_1.py +10 -9
- qiskit/circuit/library/templates/clifford/clifford_4_2.py +10 -9
- qiskit/circuit/library/templates/clifford/clifford_4_3.py +10 -9
- qiskit/circuit/library/templates/clifford/clifford_4_4.py +10 -9
- qiskit/circuit/library/templates/clifford/clifford_5_1.py +10 -9
- qiskit/circuit/library/templates/clifford/clifford_6_1.py +10 -9
- qiskit/circuit/library/templates/clifford/clifford_6_2.py +10 -9
- qiskit/circuit/library/templates/clifford/clifford_6_3.py +10 -9
- qiskit/circuit/library/templates/clifford/clifford_6_4.py +9 -8
- qiskit/circuit/library/templates/clifford/clifford_6_5.py +10 -9
- qiskit/circuit/library/templates/clifford/clifford_8_1.py +10 -9
- qiskit/circuit/library/templates/clifford/clifford_8_2.py +10 -9
- qiskit/circuit/library/templates/clifford/clifford_8_3.py +10 -9
- qiskit/circuit/library/templates/nct/template_nct_2a_1.py +9 -7
- qiskit/circuit/library/templates/nct/template_nct_2a_2.py +10 -8
- qiskit/circuit/library/templates/nct/template_nct_2a_3.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_4a_1.py +16 -14
- qiskit/circuit/library/templates/nct/template_nct_4a_2.py +14 -12
- qiskit/circuit/library/templates/nct/template_nct_4a_3.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_4b_1.py +14 -12
- qiskit/circuit/library/templates/nct/template_nct_4b_2.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_5a_1.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_5a_2.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_5a_3.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_5a_4.py +11 -9
- qiskit/circuit/library/templates/nct/template_nct_6a_1.py +11 -9
- qiskit/circuit/library/templates/nct/template_nct_6a_2.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_6a_3.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_6a_4.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_6b_1.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_6b_2.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_6c_1.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_7a_1.py +13 -11
- qiskit/circuit/library/templates/nct/template_nct_7b_1.py +13 -11
- qiskit/circuit/library/templates/nct/template_nct_7c_1.py +13 -11
- qiskit/circuit/library/templates/nct/template_nct_7d_1.py +13 -11
- qiskit/circuit/library/templates/nct/template_nct_7e_1.py +13 -11
- qiskit/circuit/library/templates/nct/template_nct_9a_1.py +13 -11
- qiskit/circuit/library/templates/nct/template_nct_9c_1.py +11 -9
- qiskit/circuit/library/templates/nct/template_nct_9c_10.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_9c_11.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_9c_12.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_9c_2.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_9c_3.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_9c_4.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_9c_5.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_9c_6.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_9c_7.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_9c_8.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_9c_9.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_9d_1.py +11 -9
- qiskit/circuit/library/templates/nct/template_nct_9d_10.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_9d_2.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_9d_3.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_9d_4.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_9d_5.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_9d_6.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_9d_7.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_9d_8.py +12 -10
- qiskit/circuit/library/templates/nct/template_nct_9d_9.py +12 -10
- qiskit/circuit/library/templates/rzx/rzx_cy.py +11 -10
- qiskit/circuit/library/templates/rzx/rzx_xz.py +16 -15
- qiskit/circuit/library/templates/rzx/rzx_yz.py +12 -10
- qiskit/circuit/library/templates/rzx/rzx_zz1.py +22 -20
- qiskit/circuit/library/templates/rzx/rzx_zz2.py +16 -15
- qiskit/circuit/library/templates/rzx/rzx_zz3.py +17 -15
- qiskit/circuit/parameter.py +4 -0
- qiskit/circuit/parameterexpression.py +167 -34
- qiskit/circuit/quantumcircuit.py +162 -126
- qiskit/circuit/singleton.py +2 -0
- qiskit/circuit/store.py +2 -0
- qiskit/circuit/twirling.py +145 -0
- qiskit/compiler/assembler.py +17 -4
- qiskit/compiler/scheduler.py +2 -0
- qiskit/compiler/sequencer.py +2 -0
- qiskit/compiler/transpiler.py +81 -26
- qiskit/converters/circuit_to_dag.py +2 -2
- qiskit/converters/circuit_to_dagdependency.py +1 -1
- qiskit/converters/circuit_to_dagdependency_v2.py +1 -1
- qiskit/converters/circuit_to_instruction.py +1 -1
- qiskit/converters/dag_to_circuit.py +7 -5
- qiskit/converters/dag_to_dagdependency.py +1 -1
- qiskit/converters/dag_to_dagdependency_v2.py +1 -1
- qiskit/converters/dagdependency_to_circuit.py +5 -1
- qiskit/converters/dagdependency_to_dag.py +6 -1
- qiskit/dagcircuit/collect_blocks.py +3 -3
- qiskit/dagcircuit/dagdependency.py +18 -5
- qiskit/dagcircuit/dagdependency_v2.py +1 -1
- qiskit/dagcircuit/dagnode.py +2 -2
- qiskit/passmanager/__init__.py +2 -2
- qiskit/primitives/backend_estimator.py +5 -2
- qiskit/primitives/backend_sampler_v2.py +61 -18
- qiskit/primitives/base/base_estimator.py +2 -2
- qiskit/primitives/containers/data_bin.py +9 -1
- qiskit/primitives/statevector_sampler.py +1 -1
- qiskit/primitives/utils.py +1 -1
- qiskit/providers/__init__.py +3 -3
- qiskit/providers/backend.py +12 -1
- qiskit/providers/backend_compat.py +23 -3
- qiskit/providers/basic_provider/basic_simulator.py +12 -2
- qiskit/providers/fake_provider/fake_pulse_backend.py +6 -1
- qiskit/providers/fake_provider/generic_backend_v2.py +46 -30
- qiskit/providers/models/pulsedefaults.py +2 -0
- qiskit/pulse/builder.py +59 -18
- qiskit/pulse/calibration_entries.py +4 -1
- qiskit/pulse/channels.py +2 -0
- qiskit/pulse/exceptions.py +2 -0
- qiskit/pulse/instruction_schedule_map.py +21 -6
- qiskit/pulse/instructions/acquire.py +2 -0
- qiskit/pulse/instructions/delay.py +2 -0
- qiskit/pulse/instructions/directives.py +8 -0
- qiskit/pulse/instructions/frequency.py +3 -0
- qiskit/pulse/instructions/instruction.py +2 -0
- qiskit/pulse/instructions/phase.py +3 -0
- qiskit/pulse/instructions/play.py +2 -0
- qiskit/pulse/instructions/reference.py +2 -0
- qiskit/pulse/instructions/snapshot.py +2 -0
- qiskit/pulse/library/pulse.py +2 -0
- qiskit/pulse/library/symbolic_pulses.py +28 -0
- qiskit/pulse/library/waveform.py +2 -0
- qiskit/pulse/macros.py +1 -1
- qiskit/pulse/schedule.py +12 -13
- qiskit/pulse/transforms/alignments.py +5 -3
- qiskit/pulse/transforms/dag.py +7 -0
- qiskit/qasm2/export.py +5 -3
- qiskit/qasm2/parse.py +46 -2
- qiskit/qasm3/__init__.py +1 -0
- qiskit/qasm3/ast.py +123 -15
- qiskit/qasm3/exporter.py +103 -77
- qiskit/qobj/converters/pulse_instruction.py +6 -4
- qiskit/qpy/__init__.py +181 -0
- qiskit/qpy/binary_io/circuits.py +20 -5
- qiskit/qpy/binary_io/schedules.py +3 -4
- qiskit/qpy/binary_io/value.py +310 -13
- qiskit/qpy/common.py +46 -2
- qiskit/qpy/formats.py +7 -0
- qiskit/qpy/interface.py +40 -4
- qiskit/quantum_info/__init__.py +4 -0
- qiskit/quantum_info/operators/channel/transformations.py +28 -21
- qiskit/quantum_info/operators/dihedral/dihedral.py +1 -1
- qiskit/quantum_info/operators/operator.py +54 -8
- qiskit/quantum_info/operators/symplectic/base_pauli.py +11 -19
- qiskit/quantum_info/operators/symplectic/clifford.py +1 -1
- qiskit/quantum_info/operators/symplectic/clifford_circuits.py +1 -1
- qiskit/quantum_info/operators/symplectic/pauli.py +2 -0
- qiskit/quantum_info/operators/symplectic/pauli_list.py +4 -4
- qiskit/quantum_info/operators/symplectic/sparse_pauli_op.py +23 -2
- qiskit/quantum_info/states/densitymatrix.py +5 -5
- qiskit/quantum_info/states/stabilizerstate.py +1 -1
- qiskit/quantum_info/states/statevector.py +6 -6
- qiskit/result/mitigation/base_readout_mitigator.py +1 -1
- qiskit/result/mitigation/correlated_readout_mitigator.py +9 -1
- qiskit/result/mitigation/local_readout_mitigator.py +9 -1
- qiskit/result/mitigation/utils.py +57 -0
- qiskit/scheduler/config.py +2 -0
- qiskit/scheduler/methods/basic.py +3 -0
- qiskit/scheduler/schedule_circuit.py +2 -0
- qiskit/scheduler/sequence.py +2 -0
- qiskit/synthesis/__init__.py +25 -0
- qiskit/synthesis/arithmetic/__init__.py +16 -0
- qiskit/synthesis/arithmetic/adders/__init__.py +17 -0
- qiskit/synthesis/arithmetic/adders/cdkm_ripple_carry_adder.py +154 -0
- qiskit/synthesis/arithmetic/adders/draper_qft_adder.py +103 -0
- qiskit/synthesis/arithmetic/adders/vbe_ripple_carry_adder.py +161 -0
- qiskit/synthesis/arithmetic/multipliers/__init__.py +16 -0
- qiskit/synthesis/arithmetic/multipliers/hrs_cumulative_multiplier.py +102 -0
- qiskit/synthesis/arithmetic/multipliers/rg_qft_multiplier.py +99 -0
- qiskit/synthesis/clifford/clifford_decompose_bm.py +1 -2
- qiskit/synthesis/clifford/clifford_decompose_greedy.py +3 -2
- qiskit/synthesis/clifford/clifford_decompose_layers.py +2 -1
- qiskit/synthesis/evolution/__init__.py +1 -0
- qiskit/synthesis/evolution/lie_trotter.py +16 -42
- qiskit/synthesis/evolution/pauli_network.py +80 -0
- qiskit/synthesis/evolution/product_formula.py +165 -238
- qiskit/synthesis/evolution/qdrift.py +36 -29
- qiskit/synthesis/evolution/suzuki_trotter.py +87 -27
- qiskit/synthesis/multi_controlled/__init__.py +1 -0
- qiskit/synthesis/multi_controlled/mcmt_vchain.py +52 -0
- qiskit/synthesis/qft/qft_decompose_full.py +19 -1
- qiskit/synthesis/qft/qft_decompose_lnn.py +2 -1
- qiskit/synthesis/stabilizer/stabilizer_decompose.py +2 -1
- qiskit/synthesis/two_qubit/two_qubit_decompose.py +4 -63
- qiskit/synthesis/unitary/qsd.py +5 -5
- qiskit/transpiler/__init__.py +21 -14
- qiskit/transpiler/basepasses.py +1 -1
- qiskit/transpiler/passes/__init__.py +2 -0
- qiskit/transpiler/passes/basis/basis_translator.py +9 -565
- qiskit/transpiler/passes/basis/decompose.py +45 -12
- qiskit/transpiler/passes/basis/unroll_3q_or_more.py +1 -1
- qiskit/transpiler/passes/basis/unroll_custom_definitions.py +1 -1
- qiskit/transpiler/passes/calibration/pulse_gate.py +4 -2
- qiskit/transpiler/passes/calibration/rx_builder.py +11 -7
- qiskit/transpiler/passes/calibration/rzx_builder.py +46 -30
- qiskit/transpiler/passes/layout/disjoint_utils.py +15 -13
- qiskit/transpiler/passes/layout/sabre_layout.py +7 -2
- qiskit/transpiler/passes/layout/sabre_pre_layout.py +5 -0
- qiskit/transpiler/passes/optimization/__init__.py +1 -0
- qiskit/transpiler/passes/optimization/collect_cliffords.py +19 -3
- qiskit/transpiler/passes/optimization/collect_linear_functions.py +1 -1
- qiskit/transpiler/passes/optimization/collect_multiqubit_blocks.py +2 -2
- qiskit/transpiler/passes/optimization/commutative_inverse_cancellation.py +1 -1
- qiskit/transpiler/passes/optimization/consolidate_blocks.py +48 -131
- qiskit/transpiler/passes/optimization/echo_rzx_weyl_decomposition.py +4 -2
- qiskit/transpiler/passes/optimization/elide_permutations.py +9 -32
- qiskit/transpiler/passes/optimization/optimize_1q_decomposition.py +5 -11
- qiskit/transpiler/passes/optimization/optimize_1q_gates.py +1 -1
- qiskit/transpiler/passes/optimization/optimize_swap_before_measure.py +1 -1
- qiskit/transpiler/passes/optimization/remove_identity_equiv.py +69 -0
- qiskit/transpiler/passes/optimization/template_matching/backward_match.py +5 -5
- qiskit/transpiler/passes/optimization/template_matching/forward_match.py +4 -4
- qiskit/transpiler/passes/optimization/template_matching/template_substitution.py +2 -2
- qiskit/transpiler/passes/routing/commuting_2q_gate_routing/commuting_2q_gate_router.py +1 -1
- qiskit/transpiler/passes/routing/commuting_2q_gate_routing/swap_strategy.py +1 -1
- qiskit/transpiler/passes/routing/sabre_swap.py +7 -3
- qiskit/transpiler/passes/routing/star_prerouting.py +2 -2
- qiskit/transpiler/passes/scheduling/alap.py +1 -1
- qiskit/transpiler/passes/scheduling/alignments/align_measures.py +2 -2
- qiskit/transpiler/passes/scheduling/alignments/check_durations.py +1 -1
- qiskit/transpiler/passes/scheduling/alignments/pulse_gate_validation.py +2 -0
- qiskit/transpiler/passes/scheduling/alignments/reschedule.py +2 -2
- qiskit/transpiler/passes/scheduling/asap.py +1 -1
- qiskit/transpiler/passes/scheduling/base_scheduler.py +14 -12
- qiskit/transpiler/passes/scheduling/dynamical_decoupling.py +9 -4
- qiskit/transpiler/passes/scheduling/padding/base_padding.py +1 -1
- qiskit/transpiler/passes/scheduling/padding/dynamical_decoupling.py +16 -5
- qiskit/transpiler/passes/scheduling/padding/pad_delay.py +4 -1
- qiskit/transpiler/passes/scheduling/scheduling/base_scheduler.py +6 -2
- qiskit/transpiler/passes/scheduling/time_unit_conversion.py +9 -4
- qiskit/transpiler/passes/synthesis/high_level_synthesis.py +262 -99
- qiskit/transpiler/passes/synthesis/hls_plugins.py +637 -7
- qiskit/transpiler/passes/synthesis/solovay_kitaev_synthesis.py +3 -3
- qiskit/transpiler/passes/synthesis/unitary_synthesis.py +55 -34
- qiskit/transpiler/passes/utils/barrier_before_final_measurements.py +2 -56
- qiskit/transpiler/passes/utils/convert_conditions_to_if_ops.py +5 -0
- qiskit/transpiler/passes/utils/gate_direction.py +12 -275
- qiskit/transpiler/passes/utils/gates_basis.py +7 -30
- qiskit/transpiler/passes/utils/merge_adjacent_barriers.py +2 -1
- qiskit/transpiler/passmanager_config.py +22 -4
- qiskit/transpiler/preset_passmanagers/builtin_plugins.py +40 -14
- qiskit/transpiler/preset_passmanagers/common.py +5 -3
- qiskit/transpiler/preset_passmanagers/generate_preset_pass_manager.py +125 -42
- qiskit/transpiler/preset_passmanagers/plugin.py +1 -1
- qiskit/transpiler/target.py +74 -16
- qiskit/utils/deprecate_pulse.py +119 -0
- qiskit/visualization/circuit/_utils.py +2 -2
- qiskit/visualization/circuit/circuit_visualization.py +3 -2
- qiskit/visualization/circuit/matplotlib.py +1 -1
- qiskit/visualization/dag_visualization.py +1 -1
- qiskit/visualization/pass_manager_visualization.py +3 -14
- qiskit/visualization/pulse_v2/interface.py +3 -1
- qiskit/visualization/timeline/core.py +25 -2
- qiskit/visualization/timeline/interface.py +12 -0
- {qiskit-1.3.0b1.dist-info → qiskit-1.3.0rc2.dist-info}/METADATA +9 -8
- {qiskit-1.3.0b1.dist-info → qiskit-1.3.0rc2.dist-info}/RECORD +357 -346
- {qiskit-1.3.0b1.dist-info → qiskit-1.3.0rc2.dist-info}/WHEEL +1 -1
- {qiskit-1.3.0b1.dist-info → qiskit-1.3.0rc2.dist-info}/entry_points.txt +19 -0
- qiskit/circuit/library/data_preparation/zz_feature_map.py +0 -118
- qiskit/synthesis/two_qubit/weyl.py +0 -97
- qiskit/transpiler/passes/synthesis/qubit_tracker.py +0 -132
- {qiskit-1.3.0b1.dist-info → qiskit-1.3.0rc2.dist-info}/LICENSE.txt +0 -0
- {qiskit-1.3.0b1.dist-info → qiskit-1.3.0rc2.dist-info}/top_level.txt +0 -0
@@ -214,13 +214,201 @@ not sufficient, the corresponding synthesis method will return `None`.
|
|
214
214
|
MCXSynthesisNDirtyI15
|
215
215
|
MCXSynthesis1CleanB95
|
216
216
|
MCXSynthesisDefault
|
217
|
+
|
218
|
+
|
219
|
+
MCMT Synthesis
|
220
|
+
''''''''''''''
|
221
|
+
|
222
|
+
.. list-table:: Plugins for :class:`.MCMTGate` (key = ``"mcmt"``)
|
223
|
+
:header-rows: 1
|
224
|
+
|
225
|
+
* - Plugin name
|
226
|
+
- Plugin class
|
227
|
+
- Number of clean ancillas
|
228
|
+
- Number of dirty ancillas
|
229
|
+
- Description
|
230
|
+
* - ``"vchain"``
|
231
|
+
- :class:`.MCMTSynthesisVChain`
|
232
|
+
- `k-1`
|
233
|
+
- `0`
|
234
|
+
- uses a linear number of Toffoli gates
|
235
|
+
* - ``"noaux"``
|
236
|
+
- :class:`~.MCMTSynthesisNoAux`
|
237
|
+
- `0`
|
238
|
+
- `0`
|
239
|
+
- uses Qiskit's standard control mechanism
|
240
|
+
* - ``"default"``
|
241
|
+
- :class:`~.MCMTSynthesisDefault`
|
242
|
+
- any
|
243
|
+
- any
|
244
|
+
- chooses the best algorithm based on the ancillas available
|
245
|
+
|
246
|
+
.. autosummary::
|
247
|
+
:toctree: ../stubs/
|
248
|
+
|
249
|
+
MCMTSynthesisVChain
|
250
|
+
MCMTSynthesisNoAux
|
251
|
+
MCMTSynthesisDefault
|
252
|
+
|
253
|
+
|
254
|
+
Pauli Evolution Synthesis
|
255
|
+
'''''''''''''''''''''''''
|
256
|
+
|
257
|
+
.. list-table:: Plugins for :class:`.PauliEvolutionGate` (key = ``"PauliEvolution"``)
|
258
|
+
:header-rows: 1
|
259
|
+
|
260
|
+
* - Plugin name
|
261
|
+
- Plugin class
|
262
|
+
- Description
|
263
|
+
- Targeted connectivity
|
264
|
+
* - ``"rustiq"``
|
265
|
+
- :class:`~.PauliEvolutionSynthesisRustiq`
|
266
|
+
- use a diagonalizing Clifford per Pauli term
|
267
|
+
- all-to-all
|
268
|
+
* - ``"default"``
|
269
|
+
- :class:`~.PauliEvolutionSynthesisDefault`
|
270
|
+
- use ``rustiq_core`` synthesis library
|
271
|
+
- all-to-all
|
272
|
+
|
273
|
+
.. autosummary::
|
274
|
+
:toctree: ../stubs/
|
275
|
+
|
276
|
+
PauliEvolutionSynthesisDefault
|
277
|
+
PauliEvolutionSynthesisRustiq
|
278
|
+
|
279
|
+
|
280
|
+
Modular Adder Synthesis
|
281
|
+
'''''''''''''''''''''''
|
282
|
+
|
283
|
+
.. list-table:: Plugins for :class:`.ModularAdderGate` (key = ``"ModularAdder"``)
|
284
|
+
:header-rows: 1
|
285
|
+
|
286
|
+
* - Plugin name
|
287
|
+
- Plugin class
|
288
|
+
- Number of clean ancillas
|
289
|
+
- Description
|
290
|
+
* - ``"ripple_cdkm"``
|
291
|
+
- :class:`.ModularAdderSynthesisC04`
|
292
|
+
- 1
|
293
|
+
- a ripple-carry adder
|
294
|
+
* - ``"ripple_vbe"``
|
295
|
+
- :class:`.ModularAdderSynthesisV95`
|
296
|
+
- :math:`n-1`, for :math:`n`-bit numbers
|
297
|
+
- a ripple-carry adder
|
298
|
+
* - ``"qft"``
|
299
|
+
- :class:`.ModularAdderSynthesisD00`
|
300
|
+
- 0
|
301
|
+
- a QFT-based adder
|
302
|
+
|
303
|
+
.. autosummary::
|
304
|
+
:toctree: ../stubs/
|
305
|
+
|
306
|
+
ModularAdderSynthesisC04
|
307
|
+
ModularAdderSynthesisD00
|
308
|
+
ModularAdderSynthesisV95
|
309
|
+
|
310
|
+
Half Adder Synthesis
|
311
|
+
''''''''''''''''''''
|
312
|
+
|
313
|
+
.. list-table:: Plugins for :class:`.HalfAdderGate` (key = ``"HalfAdder"``)
|
314
|
+
:header-rows: 1
|
315
|
+
|
316
|
+
* - Plugin name
|
317
|
+
- Plugin class
|
318
|
+
- Number of clean ancillas
|
319
|
+
- Description
|
320
|
+
* - ``"ripple_cdkm"``
|
321
|
+
- :class:`.HalfAdderSynthesisC04`
|
322
|
+
- 1
|
323
|
+
- a ripple-carry adder
|
324
|
+
* - ``"ripple_vbe"``
|
325
|
+
- :class:`.HalfAdderSynthesisV95`
|
326
|
+
- :math:`n-1`, for :math:`n`-bit numbers
|
327
|
+
- a ripple-carry adder
|
328
|
+
* - ``"qft"``
|
329
|
+
- :class:`.HalfAdderSynthesisD00`
|
330
|
+
- 0
|
331
|
+
- a QFT-based adder
|
332
|
+
|
333
|
+
.. autosummary::
|
334
|
+
:toctree: ../stubs/
|
335
|
+
|
336
|
+
HalfAdderSynthesisC04
|
337
|
+
HalfAdderSynthesisD00
|
338
|
+
HalfAdderSynthesisV95
|
339
|
+
|
340
|
+
Full Adder Synthesis
|
341
|
+
''''''''''''''''''''
|
342
|
+
|
343
|
+
.. list-table:: Plugins for :class:`.FullAdderGate` (key = ``"FullAdder"``)
|
344
|
+
:header-rows: 1
|
345
|
+
|
346
|
+
* - Plugin name
|
347
|
+
- Plugin class
|
348
|
+
- Number of clean ancillas
|
349
|
+
- Description
|
350
|
+
* - ``"ripple_cdkm"``
|
351
|
+
- :class:`.FullAdderSynthesisC04`
|
352
|
+
- 0
|
353
|
+
- a ripple-carry adder
|
354
|
+
* - ``"ripple_vbe"``
|
355
|
+
- :class:`.FullAdderSynthesisV95`
|
356
|
+
- :math:`n-1`, for :math:`n`-bit numbers
|
357
|
+
- a ripple-carry adder
|
358
|
+
|
359
|
+
.. autosummary::
|
360
|
+
:toctree: ../stubs/
|
361
|
+
|
362
|
+
FullAdderSynthesisC04
|
363
|
+
FullAdderSynthesisV95
|
364
|
+
|
365
|
+
|
366
|
+
Multiplier Synthesis
|
367
|
+
''''''''''''''''''''
|
368
|
+
|
369
|
+
.. list-table:: Plugins for :class:`.MultiplierGate` (key = ``"Multiplier"``)
|
370
|
+
:header-rows: 1
|
371
|
+
|
372
|
+
* - Plugin name
|
373
|
+
- Plugin class
|
374
|
+
- Number of clean ancillas
|
375
|
+
- Description
|
376
|
+
* - ``"cumulative"``
|
377
|
+
- :class:`.MultiplierSynthesisH18`
|
378
|
+
- depending on the :class:`.AdderGate` used
|
379
|
+
- a cumulative adder based on controlled adders
|
380
|
+
* - ``"qft"``
|
381
|
+
- :class:`.MultiplierSynthesisR17`
|
382
|
+
- 0
|
383
|
+
- a QFT-based multiplier
|
384
|
+
|
385
|
+
.. autosummary::
|
386
|
+
:toctree: ../stubs/
|
387
|
+
|
388
|
+
MultiplierSynthesisH18
|
389
|
+
MultiplierSynthesisR17
|
390
|
+
|
217
391
|
"""
|
218
392
|
|
393
|
+
from __future__ import annotations
|
394
|
+
|
395
|
+
import warnings
|
219
396
|
import numpy as np
|
220
397
|
import rustworkx as rx
|
221
398
|
|
222
399
|
from qiskit.circuit.quantumcircuit import QuantumCircuit
|
223
|
-
from qiskit.circuit.library import
|
400
|
+
from qiskit.circuit.library import (
|
401
|
+
LinearFunction,
|
402
|
+
QFTGate,
|
403
|
+
MCXGate,
|
404
|
+
C3XGate,
|
405
|
+
C4XGate,
|
406
|
+
PauliEvolutionGate,
|
407
|
+
ModularAdderGate,
|
408
|
+
HalfAdderGate,
|
409
|
+
FullAdderGate,
|
410
|
+
MultiplierGate,
|
411
|
+
)
|
224
412
|
from qiskit.transpiler.exceptions import TranspilerError
|
225
413
|
from qiskit.transpiler.coupling import CouplingMap
|
226
414
|
|
@@ -253,6 +441,15 @@ from qiskit.synthesis.multi_controlled import (
|
|
253
441
|
synth_mcx_1_clean_b95,
|
254
442
|
synth_mcx_gray_code,
|
255
443
|
synth_mcx_noaux_v24,
|
444
|
+
synth_mcmt_vchain,
|
445
|
+
)
|
446
|
+
from qiskit.synthesis.evolution import ProductFormula, synth_pauli_network_rustiq
|
447
|
+
from qiskit.synthesis.arithmetic import (
|
448
|
+
adder_ripple_c04,
|
449
|
+
adder_qft_d00,
|
450
|
+
adder_ripple_v95,
|
451
|
+
multiplier_qft_r17,
|
452
|
+
multiplier_cumulative_h18,
|
256
453
|
)
|
257
454
|
from qiskit.transpiler.passes.routing.algorithms import ApproximateTokenSwapper
|
258
455
|
from .plugin import HighLevelSynthesisPlugin
|
@@ -505,6 +702,10 @@ class QFTSynthesisFull(HighLevelSynthesisPlugin):
|
|
505
702
|
This plugin name is :``qft.full`` which can be used as the key on
|
506
703
|
an :class:`~.HLSConfig` object to use this method with :class:`~.HighLevelSynthesis`.
|
507
704
|
|
705
|
+
Note that the plugin mechanism is not applied if the gate is called ``qft`` but
|
706
|
+
is not an instance of ``QFTGate``. This allows users to create custom gates with
|
707
|
+
name ``qft``.
|
708
|
+
|
508
709
|
The plugin supports the following additional options:
|
509
710
|
|
510
711
|
* reverse_qubits (bool): Whether to synthesize the "QFT" operation (if ``False``,
|
@@ -532,10 +733,11 @@ class QFTSynthesisFull(HighLevelSynthesisPlugin):
|
|
532
733
|
|
533
734
|
def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
|
534
735
|
"""Run synthesis for the given QFTGate."""
|
736
|
+
|
737
|
+
# Even though the gate is called "qft", it's not a QFTGate,
|
738
|
+
# and we should not synthesize it using the plugin.
|
535
739
|
if not isinstance(high_level_object, QFTGate):
|
536
|
-
|
537
|
-
"The synthesis plugin 'qft.full` only applies to objects of type QFTGate."
|
538
|
-
)
|
740
|
+
return None
|
539
741
|
|
540
742
|
reverse_qubits = options.get("reverse_qubits", False)
|
541
743
|
approximation_degree = options.get("approximation_degree", 0)
|
@@ -560,6 +762,10 @@ class QFTSynthesisLine(HighLevelSynthesisPlugin):
|
|
560
762
|
This plugin name is :``qft.line`` which can be used as the key on
|
561
763
|
an :class:`~.HLSConfig` object to use this method with :class:`~.HighLevelSynthesis`.
|
562
764
|
|
765
|
+
Note that the plugin mechanism is not applied if the gate is called ``qft`` but
|
766
|
+
is not an instance of ``QFTGate``. This allows users to create custom gates with
|
767
|
+
name ``qft``.
|
768
|
+
|
563
769
|
The plugin supports the following additional options:
|
564
770
|
|
565
771
|
* reverse_qubits (bool): Whether to synthesize the "QFT" operation (if ``False``,
|
@@ -584,10 +790,11 @@ class QFTSynthesisLine(HighLevelSynthesisPlugin):
|
|
584
790
|
|
585
791
|
def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
|
586
792
|
"""Run synthesis for the given QFTGate."""
|
793
|
+
|
794
|
+
# Even though the gate is called "qft", it's not a QFTGate,
|
795
|
+
# and we should not synthesize it using the plugin.
|
587
796
|
if not isinstance(high_level_object, QFTGate):
|
588
|
-
|
589
|
-
"The synthesis plugin 'qft.line` only applies to objects of type QFTGate."
|
590
|
-
)
|
797
|
+
return None
|
591
798
|
|
592
799
|
reverse_qubits = options.get("reverse_qubits", False)
|
593
800
|
approximation_degree = options.get("approximation_degree", 0)
|
@@ -926,3 +1133,426 @@ class MCXSynthesisDefault(HighLevelSynthesisPlugin):
|
|
926
1133
|
return MCXSynthesisNoAuxV24().run(
|
927
1134
|
high_level_object, coupling_map, target, qubits, **options
|
928
1135
|
)
|
1136
|
+
|
1137
|
+
|
1138
|
+
class MCMTSynthesisDefault(HighLevelSynthesisPlugin):
|
1139
|
+
"""A default decomposition for MCMT gates."""
|
1140
|
+
|
1141
|
+
def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
|
1142
|
+
# first try to use the V-chain synthesis if enough auxiliary qubits are available
|
1143
|
+
if (
|
1144
|
+
decomposition := MCMTSynthesisVChain().run(
|
1145
|
+
high_level_object, coupling_map, target, qubits, **options
|
1146
|
+
)
|
1147
|
+
) is not None:
|
1148
|
+
return decomposition
|
1149
|
+
|
1150
|
+
return MCMTSynthesisNoAux().run(high_level_object, coupling_map, target, qubits, **options)
|
1151
|
+
|
1152
|
+
|
1153
|
+
class MCMTSynthesisNoAux(HighLevelSynthesisPlugin):
|
1154
|
+
"""A V-chain based synthesis for ``MCMTGate``."""
|
1155
|
+
|
1156
|
+
def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
|
1157
|
+
base_gate = high_level_object.base_gate
|
1158
|
+
ctrl_state = options.get("ctrl_state", None)
|
1159
|
+
|
1160
|
+
if high_level_object.num_target_qubits == 1:
|
1161
|
+
# no broadcasting needed (makes for better circuit diagrams)
|
1162
|
+
circuit = QuantumCircuit(high_level_object.num_qubits)
|
1163
|
+
circuit.append(
|
1164
|
+
base_gate.control(high_level_object.num_ctrl_qubits, ctrl_state=ctrl_state),
|
1165
|
+
circuit.qubits,
|
1166
|
+
)
|
1167
|
+
|
1168
|
+
else:
|
1169
|
+
base = QuantumCircuit(high_level_object.num_target_qubits, name=high_level_object.label)
|
1170
|
+
for i in range(high_level_object.num_target_qubits):
|
1171
|
+
base.append(base_gate, [i], [])
|
1172
|
+
|
1173
|
+
circuit = base.control(high_level_object.num_ctrl_qubits, ctrl_state=ctrl_state)
|
1174
|
+
|
1175
|
+
return circuit.decompose()
|
1176
|
+
|
1177
|
+
|
1178
|
+
class MCMTSynthesisVChain(HighLevelSynthesisPlugin):
|
1179
|
+
"""A V-chain based synthesis for ``MCMTGate``."""
|
1180
|
+
|
1181
|
+
def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
|
1182
|
+
if options.get("num_clean_ancillas", 0) < high_level_object.num_ctrl_qubits - 1:
|
1183
|
+
return None # insufficient number of auxiliary qubits
|
1184
|
+
|
1185
|
+
ctrl_state = options.get("ctrl_state", None)
|
1186
|
+
|
1187
|
+
return synth_mcmt_vchain(
|
1188
|
+
high_level_object.base_gate,
|
1189
|
+
high_level_object.num_ctrl_qubits,
|
1190
|
+
high_level_object.num_target_qubits,
|
1191
|
+
ctrl_state,
|
1192
|
+
)
|
1193
|
+
|
1194
|
+
|
1195
|
+
class ModularAdderSynthesisDefault(HighLevelSynthesisPlugin):
|
1196
|
+
"""The default modular adder (no carry in, no carry out qubit) synthesis.
|
1197
|
+
|
1198
|
+
This plugin name is:``ModularAdder.default`` which can be used as the key on
|
1199
|
+
an :class:`~.HLSConfig` object to use this method with :class:`~.HighLevelSynthesis`.
|
1200
|
+
|
1201
|
+
If at least one clean auxiliary qubit is available, the :class:`ModularAdderSynthesisC04`
|
1202
|
+
is used, otherwise :class:`ModularAdderSynthesisD00`.
|
1203
|
+
|
1204
|
+
The plugin supports the following plugin-specific options:
|
1205
|
+
|
1206
|
+
* ``num_clean_ancillas``: The number of clean auxiliary qubits available.
|
1207
|
+
|
1208
|
+
"""
|
1209
|
+
|
1210
|
+
def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
|
1211
|
+
if not isinstance(high_level_object, ModularAdderGate):
|
1212
|
+
return None
|
1213
|
+
|
1214
|
+
if options.get("num_clean_ancillas", 0) >= 1:
|
1215
|
+
return adder_ripple_c04(high_level_object.num_state_qubits, kind="fixed")
|
1216
|
+
|
1217
|
+
return adder_qft_d00(high_level_object.num_state_qubits, kind="fixed")
|
1218
|
+
|
1219
|
+
|
1220
|
+
class ModularAdderSynthesisC04(HighLevelSynthesisPlugin):
|
1221
|
+
r"""A ripple-carry adder, modulo :math:`2^n`.
|
1222
|
+
|
1223
|
+
This plugin name is:``ModularAdder.ripple_c04`` which can be used as the key on
|
1224
|
+
an :class:`~.HLSConfig` object to use this method with :class:`~.HighLevelSynthesis`.
|
1225
|
+
|
1226
|
+
This plugin requires at least one clean auxiliary qubit.
|
1227
|
+
|
1228
|
+
The plugin supports the following plugin-specific options:
|
1229
|
+
|
1230
|
+
* ``num_clean_ancillas``: The number of clean auxiliary qubits available.
|
1231
|
+
|
1232
|
+
"""
|
1233
|
+
|
1234
|
+
def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
|
1235
|
+
if not isinstance(high_level_object, ModularAdderGate):
|
1236
|
+
return None
|
1237
|
+
|
1238
|
+
# unless we implement the full adder, this implementation needs an ancilla qubit
|
1239
|
+
if options.get("num_clean_ancillas", 0) < 1:
|
1240
|
+
return None
|
1241
|
+
|
1242
|
+
return adder_ripple_c04(high_level_object.num_state_qubits, kind="fixed")
|
1243
|
+
|
1244
|
+
|
1245
|
+
class ModularAdderSynthesisV95(HighLevelSynthesisPlugin):
|
1246
|
+
r"""A ripple-carry adder, modulo :math:`2^n`.
|
1247
|
+
|
1248
|
+
This plugin name is:``ModularAdder.ripple_v95`` which can be used as the key on
|
1249
|
+
an :class:`~.HLSConfig` object to use this method with :class:`~.HighLevelSynthesis`.
|
1250
|
+
|
1251
|
+
For an adder on 2 registers with :math:`n` qubits each, this plugin requires at
|
1252
|
+
least :math:`n-1` clean auxiliary qubit.
|
1253
|
+
|
1254
|
+
The plugin supports the following plugin-specific options:
|
1255
|
+
|
1256
|
+
* ``num_clean_ancillas``: The number of clean auxiliary qubits available.
|
1257
|
+
|
1258
|
+
"""
|
1259
|
+
|
1260
|
+
def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
|
1261
|
+
if not isinstance(high_level_object, ModularAdderGate):
|
1262
|
+
return None
|
1263
|
+
|
1264
|
+
num_state_qubits = high_level_object.num_state_qubits
|
1265
|
+
|
1266
|
+
# for more than 1 state qubit, we need an ancilla
|
1267
|
+
if num_state_qubits > 1 > options.get("num_clean_ancillas", 1):
|
1268
|
+
return None
|
1269
|
+
|
1270
|
+
return adder_ripple_v95(num_state_qubits, kind="fixed")
|
1271
|
+
|
1272
|
+
|
1273
|
+
class ModularAdderSynthesisD00(HighLevelSynthesisPlugin):
|
1274
|
+
r"""A QFT-based adder, modulo :math:`2^n`.
|
1275
|
+
|
1276
|
+
This plugin name is:``ModularAdder.qft_d00`` which can be used as the key on
|
1277
|
+
an :class:`~.HLSConfig` object to use this method with :class:`~.HighLevelSynthesis`.
|
1278
|
+
"""
|
1279
|
+
|
1280
|
+
def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
|
1281
|
+
if not isinstance(high_level_object, ModularAdderGate):
|
1282
|
+
return None
|
1283
|
+
|
1284
|
+
return adder_qft_d00(high_level_object.num_state_qubits, kind="fixed")
|
1285
|
+
|
1286
|
+
|
1287
|
+
class HalfAdderSynthesisDefault(HighLevelSynthesisPlugin):
|
1288
|
+
r"""The default half-adder (no carry in, but a carry out qubit) synthesis.
|
1289
|
+
|
1290
|
+
If we have an auxiliary qubit available, the Cuccaro ripple-carry adder uses
|
1291
|
+
:math:`O(n)` CX gates and 1 auxiliary qubit, whereas the Vedral ripple-carry uses more CX
|
1292
|
+
and :math:`n-1` auxiliary qubits. The QFT-based adder uses no auxiliary qubits, but
|
1293
|
+
:math:`O(n^2)`, hence it is only used if no auxiliary qubits are available.
|
1294
|
+
|
1295
|
+
This plugin name is:``HalfAdder.default`` which can be used as the key on
|
1296
|
+
an :class:`~.HLSConfig` object to use this method with :class:`~.HighLevelSynthesis`.
|
1297
|
+
|
1298
|
+
If at least one clean auxiliary qubit is available, the :class:`HalfAdderSynthesisC04`
|
1299
|
+
is used, otherwise :class:`HalfAdderSynthesisD00`.
|
1300
|
+
|
1301
|
+
The plugin supports the following plugin-specific options:
|
1302
|
+
|
1303
|
+
* ``num_clean_ancillas``: The number of clean auxiliary qubits available.
|
1304
|
+
|
1305
|
+
"""
|
1306
|
+
|
1307
|
+
def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
|
1308
|
+
if not isinstance(high_level_object, HalfAdderGate):
|
1309
|
+
return None
|
1310
|
+
|
1311
|
+
if options.get("num_clean_ancillas", 0) >= 1:
|
1312
|
+
return adder_ripple_c04(high_level_object.num_state_qubits, kind="half")
|
1313
|
+
|
1314
|
+
return adder_qft_d00(high_level_object.num_state_qubits, kind="half")
|
1315
|
+
|
1316
|
+
|
1317
|
+
class HalfAdderSynthesisC04(HighLevelSynthesisPlugin):
|
1318
|
+
"""A ripple-carry adder with a carry-out bit.
|
1319
|
+
|
1320
|
+
This plugin name is:``HalfAdder.ripple_c04`` which can be used as the key on
|
1321
|
+
an :class:`~.HLSConfig` object to use this method with :class:`~.HighLevelSynthesis`.
|
1322
|
+
|
1323
|
+
This plugin requires at least one clean auxiliary qubit.
|
1324
|
+
|
1325
|
+
The plugin supports the following plugin-specific options:
|
1326
|
+
|
1327
|
+
* ``num_clean_ancillas``: The number of clean auxiliary qubits available.
|
1328
|
+
|
1329
|
+
"""
|
1330
|
+
|
1331
|
+
def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
|
1332
|
+
if not isinstance(high_level_object, HalfAdderGate):
|
1333
|
+
return None
|
1334
|
+
|
1335
|
+
# unless we implement the full adder, this implementation needs an ancilla qubit
|
1336
|
+
if options.get("num_clean_ancillas", 0) < 1:
|
1337
|
+
return None
|
1338
|
+
|
1339
|
+
return adder_ripple_c04(high_level_object.num_state_qubits, kind="half")
|
1340
|
+
|
1341
|
+
|
1342
|
+
class HalfAdderSynthesisV95(HighLevelSynthesisPlugin):
|
1343
|
+
"""A ripple-carry adder with a carry-out bit.
|
1344
|
+
|
1345
|
+
This plugin name is:``HalfAdder.ripple_v95`` which can be used as the key on
|
1346
|
+
an :class:`~.HLSConfig` object to use this method with :class:`~.HighLevelSynthesis`.
|
1347
|
+
|
1348
|
+
For an adder on 2 registers with :math:`n` qubits each, this plugin requires at
|
1349
|
+
least :math:`n-1` clean auxiliary qubit.
|
1350
|
+
|
1351
|
+
The plugin supports the following plugin-specific options:
|
1352
|
+
|
1353
|
+
* ``num_clean_ancillas``: The number of clean auxiliary qubits available.
|
1354
|
+
"""
|
1355
|
+
|
1356
|
+
def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
|
1357
|
+
if not isinstance(high_level_object, HalfAdderGate):
|
1358
|
+
return None
|
1359
|
+
|
1360
|
+
num_state_qubits = high_level_object.num_state_qubits
|
1361
|
+
|
1362
|
+
# for more than 1 state qubit, we need an ancilla
|
1363
|
+
if num_state_qubits > 1 > options.get("num_clean_ancillas", 1):
|
1364
|
+
return None
|
1365
|
+
|
1366
|
+
return adder_ripple_v95(num_state_qubits, kind="half")
|
1367
|
+
|
1368
|
+
|
1369
|
+
class HalfAdderSynthesisD00(HighLevelSynthesisPlugin):
|
1370
|
+
"""A QFT-based adder with a carry-in and a carry-out bit.
|
1371
|
+
|
1372
|
+
This plugin name is:``HalfAdder.qft_d00`` which can be used as the key on
|
1373
|
+
an :class:`~.HLSConfig` object to use this method with :class:`~.HighLevelSynthesis`.
|
1374
|
+
"""
|
1375
|
+
|
1376
|
+
def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
|
1377
|
+
if not isinstance(high_level_object, HalfAdderGate):
|
1378
|
+
return None
|
1379
|
+
|
1380
|
+
return adder_qft_d00(high_level_object.num_state_qubits, kind="half")
|
1381
|
+
|
1382
|
+
|
1383
|
+
class FullAdderSynthesisC04(HighLevelSynthesisPlugin):
|
1384
|
+
"""A ripple-carry adder with a carry-in and a carry-out bit.
|
1385
|
+
|
1386
|
+
This plugin name is:``FullAdder.ripple_c04`` which can be used as the key on
|
1387
|
+
an :class:`~.HLSConfig` object to use this method with :class:`~.HighLevelSynthesis`.
|
1388
|
+
|
1389
|
+
This plugin requires at least one clean auxiliary qubit.
|
1390
|
+
|
1391
|
+
The plugin supports the following plugin-specific options:
|
1392
|
+
|
1393
|
+
* ``num_clean_ancillas``: The number of clean auxiliary qubits available.
|
1394
|
+
|
1395
|
+
"""
|
1396
|
+
|
1397
|
+
def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
|
1398
|
+
if not isinstance(high_level_object, FullAdderGate):
|
1399
|
+
return None
|
1400
|
+
|
1401
|
+
return adder_ripple_c04(high_level_object.num_state_qubits, kind="full")
|
1402
|
+
|
1403
|
+
|
1404
|
+
class FullAdderSynthesisV95(HighLevelSynthesisPlugin):
|
1405
|
+
"""A ripple-carry adder with a carry-in and a carry-out bit.
|
1406
|
+
|
1407
|
+
This plugin name is:``FullAdder.ripple_v95`` which can be used as the key on
|
1408
|
+
an :class:`~.HLSConfig` object to use this method with :class:`~.HighLevelSynthesis`.
|
1409
|
+
|
1410
|
+
For an adder on 2 registers with :math:`n` qubits each, this plugin requires at
|
1411
|
+
least :math:`n-1` clean auxiliary qubit.
|
1412
|
+
|
1413
|
+
The plugin supports the following plugin-specific options:
|
1414
|
+
|
1415
|
+
* ``num_clean_ancillas``: The number of clean auxiliary qubits available.
|
1416
|
+
"""
|
1417
|
+
|
1418
|
+
def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
|
1419
|
+
if not isinstance(high_level_object, FullAdderGate):
|
1420
|
+
return None
|
1421
|
+
|
1422
|
+
num_state_qubits = high_level_object.num_state_qubits
|
1423
|
+
|
1424
|
+
# for more than 1 state qubit, we need an ancilla
|
1425
|
+
if num_state_qubits > 1 > options.get("num_clean_ancillas", 1):
|
1426
|
+
return None
|
1427
|
+
|
1428
|
+
return adder_ripple_v95(num_state_qubits, kind="full")
|
1429
|
+
|
1430
|
+
|
1431
|
+
class MultiplierSynthesisH18(HighLevelSynthesisPlugin):
|
1432
|
+
"""A cumulative multiplier based on controlled adders.
|
1433
|
+
|
1434
|
+
This plugin name is:``Multiplier.cumulative_h18`` which can be used as the key on
|
1435
|
+
an :class:`~.HLSConfig` object to use this method with :class:`~.HighLevelSynthesis`.
|
1436
|
+
"""
|
1437
|
+
|
1438
|
+
def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
|
1439
|
+
if not isinstance(high_level_object, MultiplierGate):
|
1440
|
+
return None
|
1441
|
+
|
1442
|
+
return multiplier_cumulative_h18(
|
1443
|
+
high_level_object.num_state_qubits, high_level_object.num_result_qubits
|
1444
|
+
)
|
1445
|
+
|
1446
|
+
|
1447
|
+
class MultiplierSynthesisR17(HighLevelSynthesisPlugin):
|
1448
|
+
"""A QFT-based multiplier.
|
1449
|
+
|
1450
|
+
This plugin name is:``Multiplier.qft_r17`` which can be used as the key on
|
1451
|
+
an :class:`~.HLSConfig` object to use this method with :class:`~.HighLevelSynthesis`.
|
1452
|
+
"""
|
1453
|
+
|
1454
|
+
def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
|
1455
|
+
if not isinstance(high_level_object, MultiplierGate):
|
1456
|
+
return None
|
1457
|
+
|
1458
|
+
return multiplier_qft_r17(
|
1459
|
+
high_level_object.num_state_qubits, high_level_object.num_result_qubits
|
1460
|
+
)
|
1461
|
+
|
1462
|
+
|
1463
|
+
class PauliEvolutionSynthesisDefault(HighLevelSynthesisPlugin):
|
1464
|
+
"""Synthesize a :class:`.PauliEvolutionGate` using the default synthesis algorithm.
|
1465
|
+
|
1466
|
+
This plugin name is:``PauliEvolution.default`` which can be used as the key on
|
1467
|
+
an :class:`~.HLSConfig` object to use this method with :class:`~.HighLevelSynthesis`.
|
1468
|
+
|
1469
|
+
The following plugin option can be set:
|
1470
|
+
|
1471
|
+
* preserve_order: If ``False``, allow re-ordering the Pauli terms in the Hamiltonian to
|
1472
|
+
reduce the circuit depth of the decomposition.
|
1473
|
+
|
1474
|
+
"""
|
1475
|
+
|
1476
|
+
def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
|
1477
|
+
if not isinstance(high_level_object, PauliEvolutionGate):
|
1478
|
+
# Don't do anything if a gate is called "evolution" but is not an
|
1479
|
+
# actual PauliEvolutionGate
|
1480
|
+
return None
|
1481
|
+
|
1482
|
+
algo = high_level_object.synthesis
|
1483
|
+
|
1484
|
+
if "preserve_order" in options and isinstance(algo, ProductFormula):
|
1485
|
+
algo.preserve_order = options["preserve_order"]
|
1486
|
+
|
1487
|
+
return algo.synthesize(high_level_object)
|
1488
|
+
|
1489
|
+
|
1490
|
+
class PauliEvolutionSynthesisRustiq(HighLevelSynthesisPlugin):
|
1491
|
+
"""Synthesize a :class:`.PauliEvolutionGate` using Rustiq.
|
1492
|
+
|
1493
|
+
This plugin name is :``PauliEvolution.rustiq`` which can be used as the key on
|
1494
|
+
an :class:`~.HLSConfig` object to use this method with :class:`~.HighLevelSynthesis`.
|
1495
|
+
|
1496
|
+
The Rustiq synthesis algorithm is described in [1], and is implemented in
|
1497
|
+
Rust-based quantum circuit synthesis library available at
|
1498
|
+
https://github.com/smartiel/rustiq-core.
|
1499
|
+
|
1500
|
+
On large circuits the plugin may take a significant runtime.
|
1501
|
+
|
1502
|
+
The plugin supports the following additional options:
|
1503
|
+
|
1504
|
+
* optimize_count (bool): if `True` the synthesis algorithm will try to optimize
|
1505
|
+
the 2-qubit gate count; and if `False` then the 2-qubit depth.
|
1506
|
+
* preserve_order (bool): whether the order of paulis should be preserved, up to
|
1507
|
+
commutativity.
|
1508
|
+
* upto_clifford (bool): if `True`, the final Clifford operator is not synthesized.
|
1509
|
+
* upto_phase (bool): if `True`, the global phase of the returned circuit may
|
1510
|
+
differ from the global phase of the given pauli network.
|
1511
|
+
* resynth_clifford_method (int): describes the strategy to synthesize the final
|
1512
|
+
Clifford operator. Allowed values are `0` (naive approach), `1` (qiskit
|
1513
|
+
greedy synthesis), `2` (rustiq isometry synthesis).
|
1514
|
+
|
1515
|
+
References:
|
1516
|
+
1. Timothée Goubault de Brugière and Simon Martiel,
|
1517
|
+
*Faster and shorter synthesis of Hamiltonian simulation circuits*,
|
1518
|
+
`arXiv:2404.03280 [quant-ph] <https://arxiv.org/abs/2404.03280>`_
|
1519
|
+
|
1520
|
+
"""
|
1521
|
+
|
1522
|
+
def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
|
1523
|
+
if not isinstance(high_level_object, PauliEvolutionGate):
|
1524
|
+
# Don't do anything if a gate is called "evolution" but is not an
|
1525
|
+
# actual PauliEvolutionGate
|
1526
|
+
return None
|
1527
|
+
|
1528
|
+
algo = high_level_object.synthesis
|
1529
|
+
|
1530
|
+
if not isinstance(algo, ProductFormula):
|
1531
|
+
warnings.warn(
|
1532
|
+
"Cannot apply Rustiq if the evolution synthesis does not implement ``expand``. ",
|
1533
|
+
stacklevel=2,
|
1534
|
+
category=RuntimeWarning,
|
1535
|
+
)
|
1536
|
+
return None
|
1537
|
+
|
1538
|
+
if "preserve_order" in options:
|
1539
|
+
algo.preserve_order = options["preserve_order"]
|
1540
|
+
|
1541
|
+
num_qubits = high_level_object.num_qubits
|
1542
|
+
pauli_network = algo.expand(high_level_object)
|
1543
|
+
|
1544
|
+
optimize_count = options.get("optimize_count", True)
|
1545
|
+
preserve_order = options.get("preserve_order", True)
|
1546
|
+
upto_clifford = options.get("upto_clifford", False)
|
1547
|
+
upto_phase = options.get("upto_phase", False)
|
1548
|
+
resynth_clifford_method = options.get("resynth_clifford_method", 1)
|
1549
|
+
|
1550
|
+
return synth_pauli_network_rustiq(
|
1551
|
+
num_qubits=num_qubits,
|
1552
|
+
pauli_network=pauli_network,
|
1553
|
+
optimize_count=optimize_count,
|
1554
|
+
preserve_order=preserve_order,
|
1555
|
+
upto_clifford=upto_clifford,
|
1556
|
+
upto_phase=upto_phase,
|
1557
|
+
resynth_clifford_method=resynth_clifford_method,
|
1558
|
+
)
|