qiskit 2.0.3__cp39-abi3-manylinux2014_aarch64.manylinux_2_17_aarch64.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 -0
- qiskit/__init__.py +141 -0
- qiskit/_accelerate.abi3.so +0 -0
- qiskit/_numpy_compat.py +73 -0
- qiskit/circuit/__init__.py +1343 -0
- qiskit/circuit/_add_control.py +312 -0
- qiskit/circuit/_classical_resource_map.py +150 -0
- qiskit/circuit/_standard_gates_commutations.py +3849 -0
- qiskit/circuit/_utils.py +167 -0
- qiskit/circuit/annotated_operation.py +279 -0
- qiskit/circuit/barrier.py +46 -0
- qiskit/circuit/classical/__init__.py +41 -0
- qiskit/circuit/classical/expr/__init__.py +266 -0
- qiskit/circuit/classical/expr/constructors.py +764 -0
- qiskit/circuit/classical/expr/expr.py +498 -0
- qiskit/circuit/classical/expr/visitors.py +375 -0
- qiskit/circuit/classical/types/__init__.py +113 -0
- qiskit/circuit/classical/types/ordering.py +229 -0
- qiskit/circuit/classical/types/types.py +153 -0
- qiskit/circuit/commutation_checker.py +133 -0
- qiskit/circuit/commutation_library.py +20 -0
- qiskit/circuit/controlflow/__init__.py +59 -0
- qiskit/circuit/controlflow/_builder_utils.py +211 -0
- qiskit/circuit/controlflow/box.py +163 -0
- qiskit/circuit/controlflow/break_loop.py +56 -0
- qiskit/circuit/controlflow/builder.py +791 -0
- qiskit/circuit/controlflow/continue_loop.py +56 -0
- qiskit/circuit/controlflow/control_flow.py +94 -0
- qiskit/circuit/controlflow/for_loop.py +218 -0
- qiskit/circuit/controlflow/if_else.py +498 -0
- qiskit/circuit/controlflow/switch_case.py +411 -0
- qiskit/circuit/controlflow/while_loop.py +166 -0
- qiskit/circuit/controlledgate.py +274 -0
- qiskit/circuit/delay.py +157 -0
- qiskit/circuit/duration.py +80 -0
- qiskit/circuit/equivalence.py +94 -0
- qiskit/circuit/equivalence_library.py +18 -0
- qiskit/circuit/exceptions.py +19 -0
- qiskit/circuit/gate.py +261 -0
- qiskit/circuit/instruction.py +564 -0
- qiskit/circuit/instructionset.py +132 -0
- qiskit/circuit/library/__init__.py +984 -0
- qiskit/circuit/library/arithmetic/__init__.py +40 -0
- qiskit/circuit/library/arithmetic/adders/__init__.py +18 -0
- qiskit/circuit/library/arithmetic/adders/adder.py +235 -0
- qiskit/circuit/library/arithmetic/adders/cdkm_ripple_carry_adder.py +123 -0
- qiskit/circuit/library/arithmetic/adders/draper_qft_adder.py +129 -0
- qiskit/circuit/library/arithmetic/adders/vbe_ripple_carry_adder.py +95 -0
- qiskit/circuit/library/arithmetic/exact_reciprocal.py +131 -0
- qiskit/circuit/library/arithmetic/functional_pauli_rotations.py +114 -0
- qiskit/circuit/library/arithmetic/integer_comparator.py +200 -0
- qiskit/circuit/library/arithmetic/linear_amplitude_function.py +363 -0
- qiskit/circuit/library/arithmetic/linear_pauli_rotations.py +243 -0
- qiskit/circuit/library/arithmetic/multipliers/__init__.py +17 -0
- qiskit/circuit/library/arithmetic/multipliers/hrs_cumulative_multiplier.py +145 -0
- qiskit/circuit/library/arithmetic/multipliers/multiplier.py +201 -0
- qiskit/circuit/library/arithmetic/multipliers/rg_qft_multiplier.py +108 -0
- qiskit/circuit/library/arithmetic/piecewise_chebyshev.py +502 -0
- qiskit/circuit/library/arithmetic/piecewise_linear_pauli_rotations.py +387 -0
- qiskit/circuit/library/arithmetic/piecewise_polynomial_pauli_rotations.py +493 -0
- qiskit/circuit/library/arithmetic/polynomial_pauli_rotations.py +389 -0
- qiskit/circuit/library/arithmetic/quadratic_form.py +364 -0
- qiskit/circuit/library/arithmetic/weighted_adder.py +409 -0
- qiskit/circuit/library/basis_change/__init__.py +15 -0
- qiskit/circuit/library/basis_change/qft.py +316 -0
- qiskit/circuit/library/bit_flip_oracle.py +130 -0
- qiskit/circuit/library/blueprintcircuit.py +316 -0
- qiskit/circuit/library/boolean_logic/__init__.py +18 -0
- qiskit/circuit/library/boolean_logic/inner_product.py +157 -0
- qiskit/circuit/library/boolean_logic/quantum_and.py +204 -0
- qiskit/circuit/library/boolean_logic/quantum_or.py +206 -0
- qiskit/circuit/library/boolean_logic/quantum_xor.py +167 -0
- qiskit/circuit/library/data_preparation/__init__.py +57 -0
- qiskit/circuit/library/data_preparation/_z_feature_map.py +115 -0
- qiskit/circuit/library/data_preparation/_zz_feature_map.py +150 -0
- qiskit/circuit/library/data_preparation/initializer.py +107 -0
- qiskit/circuit/library/data_preparation/pauli_feature_map.py +656 -0
- qiskit/circuit/library/data_preparation/state_preparation.py +336 -0
- qiskit/circuit/library/fourier_checking.py +160 -0
- qiskit/circuit/library/generalized_gates/__init__.py +30 -0
- qiskit/circuit/library/generalized_gates/diagonal.py +159 -0
- qiskit/circuit/library/generalized_gates/gms.py +175 -0
- qiskit/circuit/library/generalized_gates/gr.py +219 -0
- qiskit/circuit/library/generalized_gates/isometry.py +370 -0
- qiskit/circuit/library/generalized_gates/linear_function.py +318 -0
- qiskit/circuit/library/generalized_gates/mcg_up_to_diagonal.py +143 -0
- qiskit/circuit/library/generalized_gates/mcmt.py +316 -0
- qiskit/circuit/library/generalized_gates/pauli.py +84 -0
- qiskit/circuit/library/generalized_gates/permutation.py +198 -0
- qiskit/circuit/library/generalized_gates/rv.py +96 -0
- qiskit/circuit/library/generalized_gates/uc.py +303 -0
- qiskit/circuit/library/generalized_gates/uc_pauli_rot.py +164 -0
- qiskit/circuit/library/generalized_gates/ucrx.py +32 -0
- qiskit/circuit/library/generalized_gates/ucry.py +32 -0
- qiskit/circuit/library/generalized_gates/ucrz.py +32 -0
- qiskit/circuit/library/generalized_gates/unitary.py +217 -0
- qiskit/circuit/library/graph_state.py +172 -0
- qiskit/circuit/library/grover_operator.py +583 -0
- qiskit/circuit/library/hamiltonian_gate.py +142 -0
- qiskit/circuit/library/hidden_linear_function.py +163 -0
- qiskit/circuit/library/iqp.py +180 -0
- qiskit/circuit/library/n_local/__init__.py +45 -0
- qiskit/circuit/library/n_local/efficient_su2.py +282 -0
- qiskit/circuit/library/n_local/evolved_operator_ansatz.py +520 -0
- qiskit/circuit/library/n_local/excitation_preserving.py +303 -0
- qiskit/circuit/library/n_local/n_local.py +1477 -0
- qiskit/circuit/library/n_local/pauli_two_design.py +246 -0
- qiskit/circuit/library/n_local/qaoa_ansatz.py +367 -0
- qiskit/circuit/library/n_local/real_amplitudes.py +312 -0
- qiskit/circuit/library/n_local/two_local.py +289 -0
- qiskit/circuit/library/overlap.py +183 -0
- qiskit/circuit/library/pauli_evolution.py +201 -0
- qiskit/circuit/library/phase_estimation.py +177 -0
- qiskit/circuit/library/phase_oracle.py +239 -0
- qiskit/circuit/library/quantum_volume.py +180 -0
- qiskit/circuit/library/standard_gates/__init__.py +141 -0
- qiskit/circuit/library/standard_gates/dcx.py +77 -0
- qiskit/circuit/library/standard_gates/ecr.py +129 -0
- qiskit/circuit/library/standard_gates/equivalence_library.py +1800 -0
- qiskit/circuit/library/standard_gates/global_phase.py +84 -0
- qiskit/circuit/library/standard_gates/h.py +253 -0
- qiskit/circuit/library/standard_gates/i.py +76 -0
- qiskit/circuit/library/standard_gates/iswap.py +133 -0
- qiskit/circuit/library/standard_gates/p.py +422 -0
- qiskit/circuit/library/standard_gates/r.py +114 -0
- qiskit/circuit/library/standard_gates/rx.py +293 -0
- qiskit/circuit/library/standard_gates/rxx.py +180 -0
- qiskit/circuit/library/standard_gates/ry.py +286 -0
- qiskit/circuit/library/standard_gates/ryy.py +180 -0
- qiskit/circuit/library/standard_gates/rz.py +307 -0
- qiskit/circuit/library/standard_gates/rzx.py +226 -0
- qiskit/circuit/library/standard_gates/rzz.py +193 -0
- qiskit/circuit/library/standard_gates/s.py +419 -0
- qiskit/circuit/library/standard_gates/swap.py +281 -0
- qiskit/circuit/library/standard_gates/sx.py +310 -0
- qiskit/circuit/library/standard_gates/t.py +178 -0
- qiskit/circuit/library/standard_gates/u.py +395 -0
- qiskit/circuit/library/standard_gates/u1.py +490 -0
- qiskit/circuit/library/standard_gates/u2.py +145 -0
- qiskit/circuit/library/standard_gates/u3.py +428 -0
- qiskit/circuit/library/standard_gates/x.py +1481 -0
- qiskit/circuit/library/standard_gates/xx_minus_yy.py +202 -0
- qiskit/circuit/library/standard_gates/xx_plus_yy.py +236 -0
- qiskit/circuit/library/standard_gates/y.py +257 -0
- qiskit/circuit/library/standard_gates/z.py +338 -0
- qiskit/circuit/library/templates/__init__.py +92 -0
- qiskit/circuit/library/templates/clifford/__init__.py +33 -0
- qiskit/circuit/library/templates/clifford/clifford_2_1.py +34 -0
- qiskit/circuit/library/templates/clifford/clifford_2_2.py +35 -0
- qiskit/circuit/library/templates/clifford/clifford_2_3.py +34 -0
- qiskit/circuit/library/templates/clifford/clifford_2_4.py +34 -0
- qiskit/circuit/library/templates/clifford/clifford_3_1.py +35 -0
- qiskit/circuit/library/templates/clifford/clifford_4_1.py +38 -0
- qiskit/circuit/library/templates/clifford/clifford_4_2.py +37 -0
- qiskit/circuit/library/templates/clifford/clifford_4_3.py +38 -0
- qiskit/circuit/library/templates/clifford/clifford_4_4.py +37 -0
- qiskit/circuit/library/templates/clifford/clifford_5_1.py +40 -0
- qiskit/circuit/library/templates/clifford/clifford_6_1.py +40 -0
- qiskit/circuit/library/templates/clifford/clifford_6_2.py +40 -0
- qiskit/circuit/library/templates/clifford/clifford_6_3.py +40 -0
- qiskit/circuit/library/templates/clifford/clifford_6_4.py +38 -0
- qiskit/circuit/library/templates/clifford/clifford_6_5.py +40 -0
- qiskit/circuit/library/templates/clifford/clifford_8_1.py +42 -0
- qiskit/circuit/library/templates/clifford/clifford_8_2.py +42 -0
- qiskit/circuit/library/templates/clifford/clifford_8_3.py +41 -0
- qiskit/circuit/library/templates/nct/__init__.py +67 -0
- qiskit/circuit/library/templates/nct/template_nct_2a_1.py +34 -0
- qiskit/circuit/library/templates/nct/template_nct_2a_2.py +35 -0
- qiskit/circuit/library/templates/nct/template_nct_2a_3.py +37 -0
- qiskit/circuit/library/templates/nct/template_nct_4a_1.py +43 -0
- qiskit/circuit/library/templates/nct/template_nct_4a_2.py +41 -0
- qiskit/circuit/library/templates/nct/template_nct_4a_3.py +39 -0
- qiskit/circuit/library/templates/nct/template_nct_4b_1.py +41 -0
- qiskit/circuit/library/templates/nct/template_nct_4b_2.py +39 -0
- qiskit/circuit/library/templates/nct/template_nct_5a_1.py +40 -0
- qiskit/circuit/library/templates/nct/template_nct_5a_2.py +40 -0
- qiskit/circuit/library/templates/nct/template_nct_5a_3.py +40 -0
- qiskit/circuit/library/templates/nct/template_nct_5a_4.py +39 -0
- qiskit/circuit/library/templates/nct/template_nct_6a_1.py +40 -0
- qiskit/circuit/library/templates/nct/template_nct_6a_2.py +41 -0
- qiskit/circuit/library/templates/nct/template_nct_6a_3.py +41 -0
- qiskit/circuit/library/templates/nct/template_nct_6a_4.py +41 -0
- qiskit/circuit/library/templates/nct/template_nct_6b_1.py +41 -0
- qiskit/circuit/library/templates/nct/template_nct_6b_2.py +41 -0
- qiskit/circuit/library/templates/nct/template_nct_6c_1.py +41 -0
- qiskit/circuit/library/templates/nct/template_nct_7a_1.py +43 -0
- qiskit/circuit/library/templates/nct/template_nct_7b_1.py +43 -0
- qiskit/circuit/library/templates/nct/template_nct_7c_1.py +43 -0
- qiskit/circuit/library/templates/nct/template_nct_7d_1.py +43 -0
- qiskit/circuit/library/templates/nct/template_nct_7e_1.py +43 -0
- qiskit/circuit/library/templates/nct/template_nct_9a_1.py +45 -0
- qiskit/circuit/library/templates/nct/template_nct_9c_1.py +43 -0
- qiskit/circuit/library/templates/nct/template_nct_9c_10.py +44 -0
- qiskit/circuit/library/templates/nct/template_nct_9c_11.py +44 -0
- qiskit/circuit/library/templates/nct/template_nct_9c_12.py +44 -0
- qiskit/circuit/library/templates/nct/template_nct_9c_2.py +44 -0
- qiskit/circuit/library/templates/nct/template_nct_9c_3.py +44 -0
- qiskit/circuit/library/templates/nct/template_nct_9c_4.py +44 -0
- qiskit/circuit/library/templates/nct/template_nct_9c_5.py +44 -0
- qiskit/circuit/library/templates/nct/template_nct_9c_6.py +44 -0
- qiskit/circuit/library/templates/nct/template_nct_9c_7.py +44 -0
- qiskit/circuit/library/templates/nct/template_nct_9c_8.py +44 -0
- qiskit/circuit/library/templates/nct/template_nct_9c_9.py +44 -0
- qiskit/circuit/library/templates/nct/template_nct_9d_1.py +43 -0
- qiskit/circuit/library/templates/nct/template_nct_9d_10.py +44 -0
- qiskit/circuit/library/templates/nct/template_nct_9d_2.py +44 -0
- qiskit/circuit/library/templates/nct/template_nct_9d_3.py +44 -0
- qiskit/circuit/library/templates/nct/template_nct_9d_4.py +44 -0
- qiskit/circuit/library/templates/nct/template_nct_9d_5.py +44 -0
- qiskit/circuit/library/templates/nct/template_nct_9d_6.py +44 -0
- qiskit/circuit/library/templates/nct/template_nct_9d_7.py +44 -0
- qiskit/circuit/library/templates/nct/template_nct_9d_8.py +44 -0
- qiskit/circuit/library/templates/nct/template_nct_9d_9.py +44 -0
- qiskit/circuit/library/templates/rzx/__init__.py +25 -0
- qiskit/circuit/library/templates/rzx/rzx_cy.py +47 -0
- qiskit/circuit/library/templates/rzx/rzx_xz.py +54 -0
- qiskit/circuit/library/templates/rzx/rzx_yz.py +45 -0
- qiskit/circuit/library/templates/rzx/rzx_zz1.py +69 -0
- qiskit/circuit/library/templates/rzx/rzx_zz2.py +59 -0
- qiskit/circuit/library/templates/rzx/rzx_zz3.py +59 -0
- qiskit/circuit/measure.py +53 -0
- qiskit/circuit/operation.py +68 -0
- qiskit/circuit/parameter.py +179 -0
- qiskit/circuit/parameterexpression.py +703 -0
- qiskit/circuit/parametertable.py +119 -0
- qiskit/circuit/parametervector.py +140 -0
- qiskit/circuit/quantumcircuit.py +7540 -0
- qiskit/circuit/quantumcircuitdata.py +136 -0
- qiskit/circuit/random/__init__.py +15 -0
- qiskit/circuit/random/utils.py +366 -0
- qiskit/circuit/reset.py +37 -0
- qiskit/circuit/singleton.py +600 -0
- qiskit/circuit/store.py +89 -0
- qiskit/circuit/tools/__init__.py +16 -0
- qiskit/circuit/tools/pi_check.py +193 -0
- qiskit/circuit/twirling.py +145 -0
- qiskit/compiler/__init__.py +27 -0
- qiskit/compiler/transpiler.py +375 -0
- qiskit/converters/__init__.py +74 -0
- qiskit/converters/circuit_to_dag.py +80 -0
- qiskit/converters/circuit_to_dagdependency.py +49 -0
- qiskit/converters/circuit_to_dagdependency_v2.py +46 -0
- qiskit/converters/circuit_to_gate.py +107 -0
- qiskit/converters/circuit_to_instruction.py +142 -0
- qiskit/converters/dag_to_circuit.py +79 -0
- qiskit/converters/dag_to_dagdependency.py +54 -0
- qiskit/converters/dag_to_dagdependency_v2.py +43 -0
- qiskit/converters/dagdependency_to_circuit.py +40 -0
- qiskit/converters/dagdependency_to_dag.py +48 -0
- qiskit/dagcircuit/__init__.py +55 -0
- qiskit/dagcircuit/collect_blocks.py +407 -0
- qiskit/dagcircuit/dagcircuit.py +24 -0
- qiskit/dagcircuit/dagdependency.py +612 -0
- qiskit/dagcircuit/dagdependency_v2.py +566 -0
- qiskit/dagcircuit/dagdepnode.py +160 -0
- qiskit/dagcircuit/dagnode.py +188 -0
- qiskit/dagcircuit/exceptions.py +42 -0
- qiskit/exceptions.py +153 -0
- qiskit/passmanager/__init__.py +258 -0
- qiskit/passmanager/base_tasks.py +230 -0
- qiskit/passmanager/compilation_status.py +74 -0
- qiskit/passmanager/exceptions.py +19 -0
- qiskit/passmanager/flow_controllers.py +116 -0
- qiskit/passmanager/passmanager.py +353 -0
- qiskit/primitives/__init__.py +490 -0
- qiskit/primitives/backend_estimator_v2.py +530 -0
- qiskit/primitives/backend_sampler_v2.py +339 -0
- qiskit/primitives/base/__init__.py +20 -0
- qiskit/primitives/base/base_estimator.py +247 -0
- qiskit/primitives/base/base_primitive_job.py +78 -0
- qiskit/primitives/base/base_primitive_v1.py +45 -0
- qiskit/primitives/base/base_result_v1.py +65 -0
- qiskit/primitives/base/base_sampler.py +196 -0
- qiskit/primitives/base/estimator_result_v1.py +46 -0
- qiskit/primitives/base/sampler_result_v1.py +45 -0
- qiskit/primitives/base/validation_v1.py +250 -0
- qiskit/primitives/containers/__init__.py +26 -0
- qiskit/primitives/containers/bindings_array.py +391 -0
- qiskit/primitives/containers/bit_array.py +764 -0
- qiskit/primitives/containers/data_bin.py +175 -0
- qiskit/primitives/containers/estimator_pub.py +222 -0
- qiskit/primitives/containers/object_array.py +94 -0
- qiskit/primitives/containers/observables_array.py +296 -0
- qiskit/primitives/containers/primitive_result.py +53 -0
- qiskit/primitives/containers/pub_result.py +51 -0
- qiskit/primitives/containers/sampler_pub.py +193 -0
- qiskit/primitives/containers/sampler_pub_result.py +74 -0
- qiskit/primitives/containers/shape.py +129 -0
- qiskit/primitives/primitive_job.py +81 -0
- qiskit/primitives/statevector_estimator.py +175 -0
- qiskit/primitives/statevector_sampler.py +290 -0
- qiskit/primitives/utils.py +72 -0
- qiskit/providers/__init__.py +677 -0
- qiskit/providers/backend.py +364 -0
- qiskit/providers/basic_provider/__init__.py +47 -0
- qiskit/providers/basic_provider/basic_provider.py +121 -0
- qiskit/providers/basic_provider/basic_provider_job.py +65 -0
- qiskit/providers/basic_provider/basic_provider_tools.py +218 -0
- qiskit/providers/basic_provider/basic_simulator.py +693 -0
- qiskit/providers/basic_provider/exceptions.py +30 -0
- qiskit/providers/exceptions.py +33 -0
- qiskit/providers/fake_provider/__init__.py +69 -0
- qiskit/providers/fake_provider/generic_backend_v2.py +374 -0
- qiskit/providers/fake_provider/utils/__init__.py +15 -0
- qiskit/providers/job.py +147 -0
- qiskit/providers/jobstatus.py +30 -0
- qiskit/providers/options.py +273 -0
- qiskit/providers/providerutils.py +110 -0
- qiskit/qasm/libs/dummy/stdgates.inc +75 -0
- qiskit/qasm/libs/qelib1.inc +266 -0
- qiskit/qasm/libs/stdgates.inc +82 -0
- qiskit/qasm2/__init__.py +669 -0
- qiskit/qasm2/exceptions.py +27 -0
- qiskit/qasm2/export.py +364 -0
- qiskit/qasm2/parse.py +438 -0
- qiskit/qasm3/__init__.py +372 -0
- qiskit/qasm3/ast.py +782 -0
- qiskit/qasm3/exceptions.py +27 -0
- qiskit/qasm3/experimental.py +70 -0
- qiskit/qasm3/exporter.py +1340 -0
- qiskit/qasm3/printer.py +608 -0
- qiskit/qpy/__init__.py +1965 -0
- qiskit/qpy/binary_io/__init__.py +35 -0
- qiskit/qpy/binary_io/circuits.py +1455 -0
- qiskit/qpy/binary_io/parse_sympy_repr.py +121 -0
- qiskit/qpy/binary_io/schedules.py +308 -0
- qiskit/qpy/binary_io/value.py +1165 -0
- qiskit/qpy/common.py +353 -0
- qiskit/qpy/exceptions.py +53 -0
- qiskit/qpy/formats.py +442 -0
- qiskit/qpy/interface.py +344 -0
- qiskit/qpy/type_keys.py +409 -0
- qiskit/quantum_info/__init__.py +162 -0
- qiskit/quantum_info/analysis/__init__.py +17 -0
- qiskit/quantum_info/analysis/average.py +47 -0
- qiskit/quantum_info/analysis/distance.py +104 -0
- qiskit/quantum_info/analysis/make_observable.py +44 -0
- qiskit/quantum_info/analysis/z2_symmetries.py +484 -0
- qiskit/quantum_info/operators/__init__.py +28 -0
- qiskit/quantum_info/operators/base_operator.py +145 -0
- qiskit/quantum_info/operators/channel/__init__.py +29 -0
- qiskit/quantum_info/operators/channel/chi.py +191 -0
- qiskit/quantum_info/operators/channel/choi.py +218 -0
- qiskit/quantum_info/operators/channel/kraus.py +337 -0
- qiskit/quantum_info/operators/channel/ptm.py +204 -0
- qiskit/quantum_info/operators/channel/quantum_channel.py +348 -0
- qiskit/quantum_info/operators/channel/stinespring.py +296 -0
- qiskit/quantum_info/operators/channel/superop.py +373 -0
- qiskit/quantum_info/operators/channel/transformations.py +490 -0
- qiskit/quantum_info/operators/custom_iterator.py +48 -0
- qiskit/quantum_info/operators/dihedral/__init__.py +18 -0
- qiskit/quantum_info/operators/dihedral/dihedral.py +511 -0
- qiskit/quantum_info/operators/dihedral/dihedral_circuits.py +216 -0
- qiskit/quantum_info/operators/dihedral/polynomial.py +313 -0
- qiskit/quantum_info/operators/dihedral/random.py +64 -0
- qiskit/quantum_info/operators/linear_op.py +25 -0
- qiskit/quantum_info/operators/measures.py +418 -0
- qiskit/quantum_info/operators/mixins/__init__.py +52 -0
- qiskit/quantum_info/operators/mixins/adjoint.py +52 -0
- qiskit/quantum_info/operators/mixins/group.py +171 -0
- qiskit/quantum_info/operators/mixins/linear.py +84 -0
- qiskit/quantum_info/operators/mixins/multiply.py +62 -0
- qiskit/quantum_info/operators/mixins/tolerances.py +72 -0
- qiskit/quantum_info/operators/op_shape.py +525 -0
- qiskit/quantum_info/operators/operator.py +869 -0
- qiskit/quantum_info/operators/operator_utils.py +76 -0
- qiskit/quantum_info/operators/predicates.py +183 -0
- qiskit/quantum_info/operators/random.py +154 -0
- qiskit/quantum_info/operators/scalar_op.py +254 -0
- qiskit/quantum_info/operators/symplectic/__init__.py +23 -0
- qiskit/quantum_info/operators/symplectic/base_pauli.py +719 -0
- qiskit/quantum_info/operators/symplectic/clifford.py +1032 -0
- qiskit/quantum_info/operators/symplectic/clifford_circuits.py +558 -0
- qiskit/quantum_info/operators/symplectic/pauli.py +755 -0
- qiskit/quantum_info/operators/symplectic/pauli_list.py +1242 -0
- qiskit/quantum_info/operators/symplectic/pauli_utils.py +40 -0
- qiskit/quantum_info/operators/symplectic/random.py +117 -0
- qiskit/quantum_info/operators/symplectic/sparse_pauli_op.py +1239 -0
- qiskit/quantum_info/operators/utils/__init__.py +20 -0
- qiskit/quantum_info/operators/utils/anti_commutator.py +36 -0
- qiskit/quantum_info/operators/utils/commutator.py +36 -0
- qiskit/quantum_info/operators/utils/double_commutator.py +76 -0
- qiskit/quantum_info/quaternion.py +156 -0
- qiskit/quantum_info/random.py +26 -0
- qiskit/quantum_info/states/__init__.py +28 -0
- qiskit/quantum_info/states/densitymatrix.py +857 -0
- qiskit/quantum_info/states/measures.py +288 -0
- qiskit/quantum_info/states/quantum_state.py +503 -0
- qiskit/quantum_info/states/random.py +157 -0
- qiskit/quantum_info/states/stabilizerstate.py +805 -0
- qiskit/quantum_info/states/statevector.py +977 -0
- qiskit/quantum_info/states/utils.py +247 -0
- qiskit/result/__init__.py +61 -0
- qiskit/result/counts.py +189 -0
- qiskit/result/distributions/__init__.py +17 -0
- qiskit/result/distributions/probability.py +100 -0
- qiskit/result/distributions/quasi.py +154 -0
- qiskit/result/exceptions.py +40 -0
- qiskit/result/models.py +241 -0
- qiskit/result/postprocess.py +239 -0
- qiskit/result/result.py +385 -0
- qiskit/result/sampled_expval.py +74 -0
- qiskit/result/utils.py +294 -0
- qiskit/synthesis/__init__.py +240 -0
- qiskit/synthesis/arithmetic/__init__.py +18 -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/comparators/__init__.py +16 -0
- qiskit/synthesis/arithmetic/comparators/compare_2s.py +112 -0
- qiskit/synthesis/arithmetic/comparators/compare_greedy.py +66 -0
- qiskit/synthesis/arithmetic/multipliers/__init__.py +16 -0
- qiskit/synthesis/arithmetic/multipliers/hrs_cumulative_multiplier.py +103 -0
- qiskit/synthesis/arithmetic/multipliers/rg_qft_multiplier.py +100 -0
- qiskit/synthesis/arithmetic/weighted_sum.py +155 -0
- qiskit/synthesis/boolean/__init__.py +13 -0
- qiskit/synthesis/boolean/boolean_expression.py +231 -0
- qiskit/synthesis/boolean/boolean_expression_synth.py +124 -0
- qiskit/synthesis/boolean/boolean_expression_visitor.py +96 -0
- qiskit/synthesis/clifford/__init__.py +19 -0
- qiskit/synthesis/clifford/clifford_decompose_ag.py +178 -0
- qiskit/synthesis/clifford/clifford_decompose_bm.py +46 -0
- qiskit/synthesis/clifford/clifford_decompose_full.py +64 -0
- qiskit/synthesis/clifford/clifford_decompose_greedy.py +58 -0
- qiskit/synthesis/clifford/clifford_decompose_layers.py +447 -0
- qiskit/synthesis/cnotdihedral/__init__.py +17 -0
- qiskit/synthesis/cnotdihedral/cnotdihedral_decompose_full.py +52 -0
- qiskit/synthesis/cnotdihedral/cnotdihedral_decompose_general.py +141 -0
- qiskit/synthesis/cnotdihedral/cnotdihedral_decompose_two_qubits.py +266 -0
- qiskit/synthesis/discrete_basis/__init__.py +16 -0
- qiskit/synthesis/discrete_basis/commutator_decompose.py +265 -0
- qiskit/synthesis/discrete_basis/gate_sequence.py +421 -0
- qiskit/synthesis/discrete_basis/generate_basis_approximations.py +165 -0
- qiskit/synthesis/discrete_basis/solovay_kitaev.py +240 -0
- qiskit/synthesis/evolution/__init__.py +21 -0
- qiskit/synthesis/evolution/evolution_synthesis.py +48 -0
- qiskit/synthesis/evolution/lie_trotter.py +120 -0
- qiskit/synthesis/evolution/matrix_synthesis.py +47 -0
- qiskit/synthesis/evolution/pauli_network.py +80 -0
- qiskit/synthesis/evolution/product_formula.py +313 -0
- qiskit/synthesis/evolution/qdrift.py +130 -0
- qiskit/synthesis/evolution/suzuki_trotter.py +224 -0
- qiskit/synthesis/linear/__init__.py +26 -0
- qiskit/synthesis/linear/cnot_synth.py +69 -0
- qiskit/synthesis/linear/linear_circuits_utils.py +128 -0
- qiskit/synthesis/linear/linear_depth_lnn.py +61 -0
- qiskit/synthesis/linear/linear_matrix_utils.py +27 -0
- qiskit/synthesis/linear_phase/__init__.py +17 -0
- qiskit/synthesis/linear_phase/cnot_phase_synth.py +206 -0
- qiskit/synthesis/linear_phase/cx_cz_depth_lnn.py +61 -0
- qiskit/synthesis/linear_phase/cz_depth_lnn.py +58 -0
- qiskit/synthesis/multi_controlled/__init__.py +25 -0
- qiskit/synthesis/multi_controlled/mcmt_vchain.py +52 -0
- qiskit/synthesis/multi_controlled/mcx_synthesis.py +359 -0
- qiskit/synthesis/multi_controlled/multi_control_rotation_gates.py +206 -0
- qiskit/synthesis/one_qubit/__init__.py +15 -0
- qiskit/synthesis/one_qubit/one_qubit_decompose.py +288 -0
- qiskit/synthesis/permutation/__init__.py +18 -0
- qiskit/synthesis/permutation/permutation_full.py +78 -0
- qiskit/synthesis/permutation/permutation_lnn.py +54 -0
- qiskit/synthesis/permutation/permutation_reverse_lnn.py +93 -0
- qiskit/synthesis/permutation/permutation_utils.py +16 -0
- qiskit/synthesis/qft/__init__.py +16 -0
- qiskit/synthesis/qft/qft_decompose_full.py +97 -0
- qiskit/synthesis/qft/qft_decompose_lnn.py +79 -0
- qiskit/synthesis/stabilizer/__init__.py +16 -0
- qiskit/synthesis/stabilizer/stabilizer_circuit.py +149 -0
- qiskit/synthesis/stabilizer/stabilizer_decompose.py +194 -0
- qiskit/synthesis/two_qubit/__init__.py +20 -0
- qiskit/synthesis/two_qubit/local_invariance.py +63 -0
- qiskit/synthesis/two_qubit/two_qubit_decompose.py +583 -0
- qiskit/synthesis/two_qubit/xx_decompose/__init__.py +19 -0
- qiskit/synthesis/two_qubit/xx_decompose/circuits.py +300 -0
- qiskit/synthesis/two_qubit/xx_decompose/decomposer.py +324 -0
- qiskit/synthesis/two_qubit/xx_decompose/embodiments.py +163 -0
- qiskit/synthesis/two_qubit/xx_decompose/paths.py +412 -0
- qiskit/synthesis/two_qubit/xx_decompose/polytopes.py +262 -0
- qiskit/synthesis/two_qubit/xx_decompose/utilities.py +40 -0
- qiskit/synthesis/two_qubit/xx_decompose/weyl.py +133 -0
- qiskit/synthesis/unitary/__init__.py +13 -0
- qiskit/synthesis/unitary/aqc/__init__.py +177 -0
- qiskit/synthesis/unitary/aqc/approximate.py +116 -0
- qiskit/synthesis/unitary/aqc/aqc.py +175 -0
- qiskit/synthesis/unitary/aqc/cnot_structures.py +300 -0
- qiskit/synthesis/unitary/aqc/cnot_unit_circuit.py +103 -0
- qiskit/synthesis/unitary/aqc/cnot_unit_objective.py +299 -0
- qiskit/synthesis/unitary/aqc/elementary_operations.py +108 -0
- qiskit/synthesis/unitary/aqc/fast_gradient/__init__.py +164 -0
- qiskit/synthesis/unitary/aqc/fast_gradient/fast_grad_utils.py +237 -0
- qiskit/synthesis/unitary/aqc/fast_gradient/fast_gradient.py +226 -0
- qiskit/synthesis/unitary/aqc/fast_gradient/layer.py +370 -0
- qiskit/synthesis/unitary/aqc/fast_gradient/pmatrix.py +312 -0
- qiskit/synthesis/unitary/qsd.py +288 -0
- qiskit/transpiler/__init__.py +1345 -0
- qiskit/transpiler/basepasses.py +190 -0
- qiskit/transpiler/coupling.py +500 -0
- qiskit/transpiler/exceptions.py +59 -0
- qiskit/transpiler/instruction_durations.py +281 -0
- qiskit/transpiler/layout.py +740 -0
- qiskit/transpiler/passes/__init__.py +276 -0
- qiskit/transpiler/passes/analysis/__init__.py +23 -0
- qiskit/transpiler/passes/analysis/count_ops.py +30 -0
- qiskit/transpiler/passes/analysis/count_ops_longest_path.py +26 -0
- qiskit/transpiler/passes/analysis/dag_longest_path.py +24 -0
- qiskit/transpiler/passes/analysis/depth.py +33 -0
- qiskit/transpiler/passes/analysis/num_qubits.py +26 -0
- qiskit/transpiler/passes/analysis/num_tensor_factors.py +26 -0
- qiskit/transpiler/passes/analysis/resource_estimation.py +41 -0
- qiskit/transpiler/passes/analysis/size.py +36 -0
- qiskit/transpiler/passes/analysis/width.py +27 -0
- qiskit/transpiler/passes/basis/__init__.py +19 -0
- qiskit/transpiler/passes/basis/basis_translator.py +138 -0
- qiskit/transpiler/passes/basis/decompose.py +137 -0
- qiskit/transpiler/passes/basis/translate_parameterized.py +175 -0
- qiskit/transpiler/passes/basis/unroll_3q_or_more.py +84 -0
- qiskit/transpiler/passes/basis/unroll_custom_definitions.py +110 -0
- qiskit/transpiler/passes/layout/__init__.py +26 -0
- qiskit/transpiler/passes/layout/_csp_custom_solver.py +65 -0
- qiskit/transpiler/passes/layout/apply_layout.py +128 -0
- qiskit/transpiler/passes/layout/csp_layout.py +132 -0
- qiskit/transpiler/passes/layout/dense_layout.py +177 -0
- qiskit/transpiler/passes/layout/disjoint_utils.py +219 -0
- qiskit/transpiler/passes/layout/enlarge_with_ancilla.py +49 -0
- qiskit/transpiler/passes/layout/full_ancilla_allocation.py +116 -0
- qiskit/transpiler/passes/layout/layout_2q_distance.py +77 -0
- qiskit/transpiler/passes/layout/sabre_layout.py +506 -0
- qiskit/transpiler/passes/layout/sabre_pre_layout.py +225 -0
- qiskit/transpiler/passes/layout/set_layout.py +69 -0
- qiskit/transpiler/passes/layout/trivial_layout.py +66 -0
- qiskit/transpiler/passes/layout/vf2_layout.py +256 -0
- qiskit/transpiler/passes/layout/vf2_post_layout.py +376 -0
- qiskit/transpiler/passes/layout/vf2_utils.py +235 -0
- qiskit/transpiler/passes/optimization/__init__.py +42 -0
- qiskit/transpiler/passes/optimization/_gate_extension.py +80 -0
- qiskit/transpiler/passes/optimization/collect_1q_runs.py +31 -0
- qiskit/transpiler/passes/optimization/collect_2q_blocks.py +35 -0
- qiskit/transpiler/passes/optimization/collect_and_collapse.py +117 -0
- qiskit/transpiler/passes/optimization/collect_cliffords.py +109 -0
- qiskit/transpiler/passes/optimization/collect_linear_functions.py +85 -0
- qiskit/transpiler/passes/optimization/collect_multiqubit_blocks.py +242 -0
- qiskit/transpiler/passes/optimization/commutation_analysis.py +44 -0
- qiskit/transpiler/passes/optimization/commutative_cancellation.py +82 -0
- qiskit/transpiler/passes/optimization/commutative_inverse_cancellation.py +140 -0
- qiskit/transpiler/passes/optimization/consolidate_blocks.py +176 -0
- qiskit/transpiler/passes/optimization/contract_idle_wires_in_control_flow.py +104 -0
- qiskit/transpiler/passes/optimization/elide_permutations.py +91 -0
- qiskit/transpiler/passes/optimization/hoare_opt.py +420 -0
- qiskit/transpiler/passes/optimization/inverse_cancellation.py +95 -0
- qiskit/transpiler/passes/optimization/light_cone.py +135 -0
- qiskit/transpiler/passes/optimization/optimize_1q_commutation.py +267 -0
- qiskit/transpiler/passes/optimization/optimize_1q_decomposition.py +250 -0
- qiskit/transpiler/passes/optimization/optimize_1q_gates.py +384 -0
- qiskit/transpiler/passes/optimization/optimize_annotated.py +449 -0
- qiskit/transpiler/passes/optimization/optimize_cliffords.py +89 -0
- qiskit/transpiler/passes/optimization/optimize_swap_before_measure.py +71 -0
- qiskit/transpiler/passes/optimization/remove_diagonal_gates_before_measure.py +41 -0
- qiskit/transpiler/passes/optimization/remove_final_reset.py +37 -0
- qiskit/transpiler/passes/optimization/remove_identity_equiv.py +70 -0
- qiskit/transpiler/passes/optimization/remove_reset_in_zero_state.py +37 -0
- qiskit/transpiler/passes/optimization/reset_after_measure_simplification.py +50 -0
- qiskit/transpiler/passes/optimization/split_2q_unitaries.py +63 -0
- qiskit/transpiler/passes/optimization/template_matching/__init__.py +19 -0
- qiskit/transpiler/passes/optimization/template_matching/backward_match.py +749 -0
- qiskit/transpiler/passes/optimization/template_matching/forward_match.py +452 -0
- qiskit/transpiler/passes/optimization/template_matching/maximal_matches.py +77 -0
- qiskit/transpiler/passes/optimization/template_matching/template_matching.py +370 -0
- qiskit/transpiler/passes/optimization/template_matching/template_substitution.py +639 -0
- qiskit/transpiler/passes/optimization/template_optimization.py +158 -0
- qiskit/transpiler/passes/routing/__init__.py +21 -0
- qiskit/transpiler/passes/routing/algorithms/__init__.py +33 -0
- qiskit/transpiler/passes/routing/algorithms/token_swapper.py +105 -0
- qiskit/transpiler/passes/routing/algorithms/types.py +46 -0
- qiskit/transpiler/passes/routing/algorithms/util.py +103 -0
- qiskit/transpiler/passes/routing/basic_swap.py +166 -0
- qiskit/transpiler/passes/routing/commuting_2q_gate_routing/__init__.py +25 -0
- qiskit/transpiler/passes/routing/commuting_2q_gate_routing/commuting_2q_block.py +60 -0
- qiskit/transpiler/passes/routing/commuting_2q_gate_routing/commuting_2q_gate_router.py +397 -0
- qiskit/transpiler/passes/routing/commuting_2q_gate_routing/pauli_2q_evolution_commutation.py +145 -0
- qiskit/transpiler/passes/routing/commuting_2q_gate_routing/swap_strategy.py +306 -0
- qiskit/transpiler/passes/routing/layout_transformation.py +119 -0
- qiskit/transpiler/passes/routing/lookahead_swap.py +390 -0
- qiskit/transpiler/passes/routing/sabre_swap.py +463 -0
- qiskit/transpiler/passes/routing/star_prerouting.py +408 -0
- qiskit/transpiler/passes/routing/utils.py +35 -0
- qiskit/transpiler/passes/scheduling/__init__.py +21 -0
- qiskit/transpiler/passes/scheduling/alignments/__init__.py +79 -0
- qiskit/transpiler/passes/scheduling/alignments/check_durations.py +70 -0
- qiskit/transpiler/passes/scheduling/alignments/reschedule.py +251 -0
- qiskit/transpiler/passes/scheduling/padding/__init__.py +16 -0
- qiskit/transpiler/passes/scheduling/padding/base_padding.py +284 -0
- qiskit/transpiler/passes/scheduling/padding/dynamical_decoupling.py +415 -0
- qiskit/transpiler/passes/scheduling/padding/pad_delay.py +90 -0
- qiskit/transpiler/passes/scheduling/scheduling/__init__.py +17 -0
- qiskit/transpiler/passes/scheduling/scheduling/alap.py +93 -0
- qiskit/transpiler/passes/scheduling/scheduling/asap.py +100 -0
- qiskit/transpiler/passes/scheduling/scheduling/base_scheduler.py +88 -0
- qiskit/transpiler/passes/scheduling/scheduling/set_io_latency.py +64 -0
- qiskit/transpiler/passes/scheduling/time_unit_conversion.py +237 -0
- qiskit/transpiler/passes/synthesis/__init__.py +20 -0
- qiskit/transpiler/passes/synthesis/aqc_plugin.py +153 -0
- qiskit/transpiler/passes/synthesis/default_unitary_synth_plugin.py +653 -0
- qiskit/transpiler/passes/synthesis/high_level_synthesis.py +429 -0
- qiskit/transpiler/passes/synthesis/hls_plugins.py +1963 -0
- qiskit/transpiler/passes/synthesis/linear_functions_synthesis.py +41 -0
- qiskit/transpiler/passes/synthesis/plugin.py +738 -0
- qiskit/transpiler/passes/synthesis/solovay_kitaev_synthesis.py +313 -0
- qiskit/transpiler/passes/synthesis/unitary_synthesis.py +425 -0
- qiskit/transpiler/passes/utils/__init__.py +32 -0
- qiskit/transpiler/passes/utils/barrier_before_final_measurements.py +41 -0
- qiskit/transpiler/passes/utils/check_gate_direction.py +60 -0
- qiskit/transpiler/passes/utils/check_map.py +78 -0
- qiskit/transpiler/passes/utils/contains_instruction.py +45 -0
- qiskit/transpiler/passes/utils/control_flow.py +61 -0
- qiskit/transpiler/passes/utils/dag_fixed_point.py +36 -0
- qiskit/transpiler/passes/utils/error.py +69 -0
- qiskit/transpiler/passes/utils/filter_op_nodes.py +66 -0
- qiskit/transpiler/passes/utils/fixed_point.py +48 -0
- qiskit/transpiler/passes/utils/gate_direction.py +93 -0
- qiskit/transpiler/passes/utils/gates_basis.py +51 -0
- qiskit/transpiler/passes/utils/merge_adjacent_barriers.py +163 -0
- qiskit/transpiler/passes/utils/minimum_point.py +118 -0
- qiskit/transpiler/passes/utils/remove_barriers.py +50 -0
- qiskit/transpiler/passes/utils/remove_final_measurements.py +121 -0
- qiskit/transpiler/passes/utils/unroll_forloops.py +81 -0
- qiskit/transpiler/passmanager.py +503 -0
- qiskit/transpiler/passmanager_config.py +151 -0
- qiskit/transpiler/preset_passmanagers/__init__.py +93 -0
- qiskit/transpiler/preset_passmanagers/builtin_plugins.py +993 -0
- qiskit/transpiler/preset_passmanagers/common.py +672 -0
- qiskit/transpiler/preset_passmanagers/generate_preset_pass_manager.py +437 -0
- qiskit/transpiler/preset_passmanagers/level0.py +104 -0
- qiskit/transpiler/preset_passmanagers/level1.py +108 -0
- qiskit/transpiler/preset_passmanagers/level2.py +109 -0
- qiskit/transpiler/preset_passmanagers/level3.py +110 -0
- qiskit/transpiler/preset_passmanagers/plugin.py +346 -0
- qiskit/transpiler/target.py +905 -0
- qiskit/transpiler/timing_constraints.py +59 -0
- qiskit/user_config.py +266 -0
- qiskit/utils/__init__.py +90 -0
- qiskit/utils/classtools.py +146 -0
- qiskit/utils/deprecation.py +382 -0
- qiskit/utils/lazy_tester.py +363 -0
- qiskit/utils/optionals.py +354 -0
- qiskit/utils/parallel.py +318 -0
- qiskit/utils/units.py +146 -0
- qiskit/version.py +84 -0
- qiskit/visualization/__init__.py +290 -0
- qiskit/visualization/array.py +207 -0
- qiskit/visualization/bloch.py +778 -0
- qiskit/visualization/circuit/__init__.py +15 -0
- qiskit/visualization/circuit/_utils.py +675 -0
- qiskit/visualization/circuit/circuit_visualization.py +735 -0
- qiskit/visualization/circuit/latex.py +661 -0
- qiskit/visualization/circuit/matplotlib.py +2019 -0
- qiskit/visualization/circuit/qcstyle.py +278 -0
- qiskit/visualization/circuit/styles/__init__.py +13 -0
- qiskit/visualization/circuit/styles/bw.json +202 -0
- qiskit/visualization/circuit/styles/clifford.json +202 -0
- qiskit/visualization/circuit/styles/iqp-dark.json +214 -0
- qiskit/visualization/circuit/styles/iqp.json +214 -0
- qiskit/visualization/circuit/styles/textbook.json +202 -0
- qiskit/visualization/circuit/text.py +1849 -0
- qiskit/visualization/circuit_visualization.py +19 -0
- qiskit/visualization/counts_visualization.py +487 -0
- qiskit/visualization/dag_visualization.py +318 -0
- qiskit/visualization/exceptions.py +21 -0
- qiskit/visualization/gate_map.py +1424 -0
- qiskit/visualization/library.py +40 -0
- qiskit/visualization/pass_manager_visualization.py +312 -0
- qiskit/visualization/state_visualization.py +1546 -0
- qiskit/visualization/timeline/__init__.py +21 -0
- qiskit/visualization/timeline/core.py +495 -0
- qiskit/visualization/timeline/drawings.py +260 -0
- qiskit/visualization/timeline/generators.py +506 -0
- qiskit/visualization/timeline/interface.py +444 -0
- qiskit/visualization/timeline/layouts.py +115 -0
- qiskit/visualization/timeline/plotters/__init__.py +16 -0
- qiskit/visualization/timeline/plotters/base_plotter.py +58 -0
- qiskit/visualization/timeline/plotters/matplotlib.py +195 -0
- qiskit/visualization/timeline/stylesheet.py +301 -0
- qiskit/visualization/timeline/types.py +148 -0
- qiskit/visualization/transition_visualization.py +369 -0
- qiskit/visualization/utils.py +49 -0
- qiskit-2.0.3.dist-info/METADATA +220 -0
- qiskit-2.0.3.dist-info/RECORD +690 -0
- qiskit-2.0.3.dist-info/WHEEL +6 -0
- qiskit-2.0.3.dist-info/entry_points.txt +82 -0
- qiskit-2.0.3.dist-info/licenses/LICENSE.txt +203 -0
- qiskit-2.0.3.dist-info/top_level.txt +1 -0
@@ -0,0 +1,95 @@
|
|
1
|
+
# This code is part of Qiskit.
|
2
|
+
#
|
3
|
+
# (C) Copyright IBM 2021.
|
4
|
+
#
|
5
|
+
# This code is licensed under the Apache License, Version 2.0. You may
|
6
|
+
# obtain a copy of this license in the LICENSE.txt file in the root directory
|
7
|
+
# of this source tree or at http://www.apache.org/licenses/LICENSE-2.0.
|
8
|
+
#
|
9
|
+
# Any modifications or derivative works of this code must retain this
|
10
|
+
# copyright notice, and modified files need to carry a notice indicating
|
11
|
+
# that they have been altered from the originals.
|
12
|
+
|
13
|
+
"""
|
14
|
+
A generic InverseCancellation pass for any set of gate-inverse pairs.
|
15
|
+
"""
|
16
|
+
from typing import List, Tuple, Union
|
17
|
+
|
18
|
+
from qiskit.circuit import Gate
|
19
|
+
from qiskit.dagcircuit import DAGCircuit
|
20
|
+
from qiskit.transpiler.basepasses import TransformationPass
|
21
|
+
from qiskit.transpiler.exceptions import TranspilerError
|
22
|
+
from qiskit.transpiler.passes.utils import control_flow
|
23
|
+
|
24
|
+
from qiskit._accelerate.inverse_cancellation import inverse_cancellation
|
25
|
+
|
26
|
+
|
27
|
+
class InverseCancellation(TransformationPass):
|
28
|
+
"""Cancel specific Gates which are inverses of each other when they occur back-to-
|
29
|
+
back."""
|
30
|
+
|
31
|
+
def __init__(self, gates_to_cancel: List[Union[Gate, Tuple[Gate, Gate]]]):
|
32
|
+
"""Initialize InverseCancellation pass.
|
33
|
+
|
34
|
+
Args:
|
35
|
+
gates_to_cancel: List describing the gates to cancel. Each element of the
|
36
|
+
list is either a single gate or a pair of gates. If a single gate, then
|
37
|
+
it should be self-inverse. If a pair of gates, then the gates in the
|
38
|
+
pair should be inverses of each other.
|
39
|
+
|
40
|
+
Raises:
|
41
|
+
TranspilerError: Input is not a self-inverse gate or a pair of inverse gates.
|
42
|
+
"""
|
43
|
+
|
44
|
+
for gates in gates_to_cancel:
|
45
|
+
if isinstance(gates, Gate):
|
46
|
+
if gates != gates.inverse():
|
47
|
+
raise TranspilerError(f"Gate {gates.name} is not self-inverse")
|
48
|
+
elif isinstance(gates, tuple):
|
49
|
+
if len(gates) != 2:
|
50
|
+
raise TranspilerError(
|
51
|
+
f"Too many or too few inputs: {gates}. Only two are allowed."
|
52
|
+
)
|
53
|
+
if gates[0] != gates[1].inverse():
|
54
|
+
raise TranspilerError(
|
55
|
+
f"Gate {gates[0].name} and {gates[1].name} are not inverse."
|
56
|
+
)
|
57
|
+
else:
|
58
|
+
raise TranspilerError(
|
59
|
+
f"InverseCancellation pass does not take input type {type(gates)}. Input must be"
|
60
|
+
" a Gate."
|
61
|
+
)
|
62
|
+
|
63
|
+
self.self_inverse_gates = []
|
64
|
+
self.inverse_gate_pairs = []
|
65
|
+
self.self_inverse_gate_names = set()
|
66
|
+
self.inverse_gate_pairs_names = set()
|
67
|
+
|
68
|
+
for gates in gates_to_cancel:
|
69
|
+
if isinstance(gates, Gate):
|
70
|
+
self.self_inverse_gates.append(gates)
|
71
|
+
self.self_inverse_gate_names.add(gates.name)
|
72
|
+
else:
|
73
|
+
self.inverse_gate_pairs.append(gates)
|
74
|
+
self.inverse_gate_pairs_names.update(x.name for x in gates)
|
75
|
+
|
76
|
+
super().__init__()
|
77
|
+
|
78
|
+
@control_flow.trivial_recurse
|
79
|
+
def run(self, dag: DAGCircuit):
|
80
|
+
"""Run the InverseCancellation pass on `dag`.
|
81
|
+
|
82
|
+
Args:
|
83
|
+
dag: the directed acyclic graph to run on.
|
84
|
+
|
85
|
+
Returns:
|
86
|
+
DAGCircuit: Transformed DAG.
|
87
|
+
"""
|
88
|
+
inverse_cancellation(
|
89
|
+
dag,
|
90
|
+
self.inverse_gate_pairs,
|
91
|
+
self.self_inverse_gates,
|
92
|
+
self.inverse_gate_pairs_names,
|
93
|
+
self.self_inverse_gate_names,
|
94
|
+
)
|
95
|
+
return dag
|
@@ -0,0 +1,135 @@
|
|
1
|
+
# This code is part of Qiskit.
|
2
|
+
#
|
3
|
+
# (C) Copyright IBM 2017, 2019.
|
4
|
+
#
|
5
|
+
# This code is licensed under the Apache License, Version 2.0. You may
|
6
|
+
# obtain a copy of this license in the LICENSE.txt file in the root directory
|
7
|
+
# of this source tree or at http://www.apache.org/licenses/LICENSE-2.0.
|
8
|
+
#
|
9
|
+
# Any modifications or derivative works of this code must retain this
|
10
|
+
# copyright notice, and modified files need to carry a notice indicating
|
11
|
+
# that they have been altered from the originals.
|
12
|
+
|
13
|
+
"""Cancel the redundant (self-adjoint) gates through commutation relations."""
|
14
|
+
from __future__ import annotations
|
15
|
+
import warnings
|
16
|
+
from qiskit.circuit import Gate, Qubit
|
17
|
+
from qiskit.circuit.commutation_library import SessionCommutationChecker as scc
|
18
|
+
from qiskit.circuit.library import PauliGate, ZGate
|
19
|
+
from qiskit.dagcircuit import DAGCircuit
|
20
|
+
from qiskit.transpiler.basepasses import TransformationPass
|
21
|
+
from qiskit.transpiler.passes.utils.remove_final_measurements import calc_final_ops
|
22
|
+
|
23
|
+
translation_table = str.maketrans({"+": "X", "-": "X", "l": "Y", "r": "Y", "0": "Z", "1": "Z"})
|
24
|
+
|
25
|
+
|
26
|
+
class LightCone(TransformationPass):
|
27
|
+
"""Remove the gates that do not affect the outcome of a measurement on a circuit.
|
28
|
+
|
29
|
+
Pass for computing the light-cone of an observable or measurement. The Pass can handle
|
30
|
+
either an observable one would like to measure or a measurement on a set of qubits.
|
31
|
+
"""
|
32
|
+
|
33
|
+
def __init__(self, bit_terms: str | None = None, indices: list[int] | None = None) -> None:
|
34
|
+
"""
|
35
|
+
Args:
|
36
|
+
bit_terms: If ``None`` the light-cone will be computed for the set of measurements
|
37
|
+
in the circuit. If a string is specified, the light-cone will correspond to the
|
38
|
+
reduced circuit with the same expectation value for the observable.
|
39
|
+
indices: list of non-trivial indices corresponding to the observable in ``bit_terms``.
|
40
|
+
"""
|
41
|
+
super().__init__()
|
42
|
+
valid_characters = {"X", "Y", "Z", "+", "-", "l", "r", "0", "1"}
|
43
|
+
self.bit_terms = None
|
44
|
+
if bit_terms is not None:
|
45
|
+
if not indices:
|
46
|
+
raise ValueError("`indices` must be non-empty when providing `bit_terms`.")
|
47
|
+
if not set(bit_terms).issubset(valid_characters):
|
48
|
+
raise ValueError(
|
49
|
+
f"`bit_terms` should contain only characters in {valid_characters}."
|
50
|
+
)
|
51
|
+
if len(bit_terms) != len(indices):
|
52
|
+
raise ValueError("`bit_terms` must be the same length as `indices`.")
|
53
|
+
self.bit_terms = bit_terms.translate(translation_table)
|
54
|
+
self.indices = indices
|
55
|
+
|
56
|
+
@staticmethod
|
57
|
+
def _find_measurement_qubits(dag: DAGCircuit) -> set[Qubit]:
|
58
|
+
final_nodes = calc_final_ops(dag, {"measure"})
|
59
|
+
qubits_measured = set()
|
60
|
+
for node in final_nodes:
|
61
|
+
qubits_measured |= set(node.qargs)
|
62
|
+
return qubits_measured
|
63
|
+
|
64
|
+
def _get_initial_lightcone(
|
65
|
+
self, dag: DAGCircuit
|
66
|
+
) -> tuple[set[Qubit], list[tuple[Gate, list[Qubit]]]]:
|
67
|
+
"""Returns the initial light-cone.
|
68
|
+
If observable is `None`, the light-cone is the set of measured qubits.
|
69
|
+
If a `bit_terms` is provided, the qubits corresponding to the
|
70
|
+
non-trivial Paulis define the light-cone.
|
71
|
+
"""
|
72
|
+
lightcone_qubits = self._find_measurement_qubits(dag)
|
73
|
+
if self.bit_terms is None:
|
74
|
+
lightcone_operations = [(ZGate(), [qubit_index]) for qubit_index in lightcone_qubits]
|
75
|
+
else:
|
76
|
+
# Having both measurements and an observable is not allowed
|
77
|
+
if len(dag.qubits) < max(self.indices) + 1:
|
78
|
+
raise ValueError("`indices` contains values outside the qubit range.")
|
79
|
+
if lightcone_qubits:
|
80
|
+
raise ValueError(
|
81
|
+
"The circuit contains measurements and an observable has been given: "
|
82
|
+
"remove the observable or the measurements."
|
83
|
+
)
|
84
|
+
lightcone_qubits = [dag.qubits[i] for i in self.indices]
|
85
|
+
# `lightcone_operations` is a list of tuples, each containing (operation, list_of_qubits)
|
86
|
+
lightcone_operations = [(PauliGate(self.bit_terms), lightcone_qubits)]
|
87
|
+
|
88
|
+
return set(lightcone_qubits), lightcone_operations
|
89
|
+
|
90
|
+
def run(self, dag: DAGCircuit) -> DAGCircuit:
|
91
|
+
"""Run the LightCone pass on `dag`.
|
92
|
+
|
93
|
+
Args:
|
94
|
+
dag: The DAG to reduce.
|
95
|
+
|
96
|
+
Returns:
|
97
|
+
The DAG reduced to the light-cone of the observable.
|
98
|
+
"""
|
99
|
+
|
100
|
+
# Get the initial light-cone and operations
|
101
|
+
lightcone_qubits, lightcone_operations = self._get_initial_lightcone(dag)
|
102
|
+
|
103
|
+
# Initialize a new, empty DAG
|
104
|
+
new_dag = dag.copy_empty_like()
|
105
|
+
|
106
|
+
# Iterate over the nodes in reverse topological order
|
107
|
+
for node in reversed(list(dag.topological_op_nodes())):
|
108
|
+
# Check if the node belongs to the light-cone
|
109
|
+
if lightcone_qubits.intersection(node.qargs):
|
110
|
+
# Check commutation with all previous operations
|
111
|
+
commutes_bool = True
|
112
|
+
for op in lightcone_operations:
|
113
|
+
max_num_qubits = max(len(op[1]), len(node.qargs))
|
114
|
+
if max_num_qubits > 10:
|
115
|
+
warnings.warn(
|
116
|
+
"LightCone pass is checking commutation of"
|
117
|
+
f"operators of size {max_num_qubits}."
|
118
|
+
"This operation can be slow.",
|
119
|
+
category=RuntimeWarning,
|
120
|
+
)
|
121
|
+
commute_bool = scc.commute(
|
122
|
+
op[0], op[1], [], node.op, node.qargs, [], max_num_qubits=max_num_qubits
|
123
|
+
)
|
124
|
+
if not commute_bool:
|
125
|
+
# If the current node does not commute, update the light-cone
|
126
|
+
lightcone_qubits.update(node.qargs)
|
127
|
+
lightcone_operations.append((node.op, node.qargs))
|
128
|
+
commutes_bool = False
|
129
|
+
break
|
130
|
+
|
131
|
+
# If the node is in the light-cone and commutes with previous `ops`,
|
132
|
+
# add it to the new DAG at the front
|
133
|
+
if not commutes_bool:
|
134
|
+
new_dag.apply_operation_front(node.op, node.qargs, node.cargs)
|
135
|
+
return new_dag
|
@@ -0,0 +1,267 @@
|
|
1
|
+
# This code is part of Qiskit.
|
2
|
+
#
|
3
|
+
# (C) Copyright IBM 2017, 2021.
|
4
|
+
#
|
5
|
+
# This code is licensed under the Apache License, Version 2.0. You may
|
6
|
+
# obtain a copy of this license in the LICENSE.txt file in the root directory
|
7
|
+
# of this source tree or at http://www.apache.org/licenses/LICENSE-2.0.
|
8
|
+
#
|
9
|
+
# Any modifications or derivative works of this code must retain this
|
10
|
+
# copyright notice, and modified files need to carry a notice indicating
|
11
|
+
# that they have been altered from the originals.
|
12
|
+
|
13
|
+
"""Reduce 1Q gate complexity by commuting through 2Q gates and resynthesizing."""
|
14
|
+
|
15
|
+
from copy import copy
|
16
|
+
import logging
|
17
|
+
from collections import deque
|
18
|
+
|
19
|
+
from qiskit.dagcircuit import DAGCircuit
|
20
|
+
from qiskit.circuit import QuantumRegister
|
21
|
+
from qiskit.circuit.library.standard_gates import CXGate, RZXGate
|
22
|
+
from qiskit.dagcircuit import DAGOpNode
|
23
|
+
from qiskit.transpiler.basepasses import TransformationPass
|
24
|
+
from qiskit.transpiler.passes.optimization.optimize_1q_decomposition import (
|
25
|
+
Optimize1qGatesDecomposition,
|
26
|
+
)
|
27
|
+
|
28
|
+
logger = logging.getLogger(__name__)
|
29
|
+
|
30
|
+
|
31
|
+
commutation_table = {
|
32
|
+
RZXGate: (["rz", "p"], ["x", "sx", "rx"]),
|
33
|
+
CXGate: (["rz", "p"], ["x", "sx", "rx"]),
|
34
|
+
}
|
35
|
+
"""
|
36
|
+
Simple commutation rules: G belongs to commutation_table[barrier_type][qubit_preindex] when G
|
37
|
+
commutes with the indicated barrier on that qubit wire.
|
38
|
+
|
39
|
+
NOTE: Does not cover identities like
|
40
|
+
(X (x) I) . CX = CX . (X (x) X) , (duplication)
|
41
|
+
(U (x) I) . SWAP = SWAP . (I (x) U) . (permutation)
|
42
|
+
|
43
|
+
NOTE: These rules are _symmetric_, so that they may be applied in reverse.
|
44
|
+
"""
|
45
|
+
|
46
|
+
|
47
|
+
class Optimize1qGatesSimpleCommutation(TransformationPass):
|
48
|
+
"""
|
49
|
+
Optimizes 1Q gate strings interrupted by 2Q gates by commuting the components and
|
50
|
+
resynthesizing the results. The commutation rules are stored in ``commutation_table``.
|
51
|
+
|
52
|
+
NOTE: In addition to those mentioned in ``commutation_table``, this pass has some limitations:
|
53
|
+
+ Does not handle multiple commutations in a row without intermediate progress.
|
54
|
+
+ Can only commute into positions where there are pre-existing runs.
|
55
|
+
+ Does not exhaustively test all the different ways commuting gates can be assigned to
|
56
|
+
either side of a barrier to try to find low-depth configurations. (This is particularly
|
57
|
+
evident if all the gates in a run commute with both the predecessor and the successor
|
58
|
+
barriers.)
|
59
|
+
"""
|
60
|
+
|
61
|
+
# NOTE: A run from dag.collect_1q_runs is always nonempty, so we sometimes use an empty list
|
62
|
+
# to signify the absence of a run.
|
63
|
+
|
64
|
+
def __init__(self, basis=None, run_to_completion=False, target=None):
|
65
|
+
"""
|
66
|
+
Args:
|
67
|
+
basis (List[str]): See also `Optimize1qGatesDecomposition`.
|
68
|
+
run_to_completion (bool): If `True`, this pass retries until it is unable to do any more
|
69
|
+
work. If `False`, it finds and performs one optimization, and for full optimization
|
70
|
+
the user is obligated to re-call the pass until the output stabilizes.
|
71
|
+
target (Target): The :class:`~.Target` representing the target backend, if both
|
72
|
+
``basis`` and this are specified then this argument will take
|
73
|
+
precedence and ``basis`` will be ignored.
|
74
|
+
"""
|
75
|
+
super().__init__()
|
76
|
+
|
77
|
+
self._optimize1q = Optimize1qGatesDecomposition(basis=basis, target=target)
|
78
|
+
self._run_to_completion = run_to_completion
|
79
|
+
|
80
|
+
@staticmethod
|
81
|
+
def _find_adjoining_run(dag, runs, run, front=True):
|
82
|
+
"""
|
83
|
+
Finds the run which abuts `run` from the front (or the rear if `front == False`), separated
|
84
|
+
by a blocking node.
|
85
|
+
|
86
|
+
Returns a pair of the abutting multiqubit gate and the run which it separates from this
|
87
|
+
one. The next run can be the empty list `[]` if it is absent.
|
88
|
+
"""
|
89
|
+
edge_node = run[0] if front else run[-1]
|
90
|
+
blocker = next(dag.predecessors(edge_node) if front else dag.successors(edge_node))
|
91
|
+
possibilities = dag.predecessors(blocker) if front else dag.successors(blocker)
|
92
|
+
|
93
|
+
adjoining_run = []
|
94
|
+
for possibility in possibilities:
|
95
|
+
if isinstance(possibility, DAGOpNode) and possibility.qargs == edge_node.qargs:
|
96
|
+
adjoining_run = []
|
97
|
+
for single_run in runs:
|
98
|
+
if (
|
99
|
+
len(single_run) != 0 and single_run[0].qargs == possibility.qargs
|
100
|
+
): # allows us to only check the run on a particular qubit
|
101
|
+
if possibility in single_run:
|
102
|
+
adjoining_run = single_run
|
103
|
+
break
|
104
|
+
break
|
105
|
+
return (blocker, adjoining_run)
|
106
|
+
|
107
|
+
@staticmethod
|
108
|
+
def _commute_through(blocker, run, front=True):
|
109
|
+
"""
|
110
|
+
Pulls `DAGOpNode`s from the front of `run` (or the back, if `front == False`) until it
|
111
|
+
encounters a gate which does not commute with `blocker`.
|
112
|
+
|
113
|
+
Returns a pair of lists whose concatenation is `run`.
|
114
|
+
"""
|
115
|
+
|
116
|
+
if run == []:
|
117
|
+
return [], []
|
118
|
+
# use deque to have modification
|
119
|
+
# operations which are constant
|
120
|
+
# time
|
121
|
+
run_clone = deque(run)
|
122
|
+
|
123
|
+
commuted = deque([])
|
124
|
+
preindex, commutation_rule = None, None
|
125
|
+
if isinstance(blocker, DAGOpNode):
|
126
|
+
preindex = None
|
127
|
+
for i, q in enumerate(blocker.qargs):
|
128
|
+
if q == run[0].qargs[0]:
|
129
|
+
preindex = i
|
130
|
+
|
131
|
+
commutation_rule = None
|
132
|
+
if (
|
133
|
+
preindex is not None
|
134
|
+
and isinstance(blocker, DAGOpNode)
|
135
|
+
and blocker.op.base_class in commutation_table
|
136
|
+
):
|
137
|
+
commutation_rule = commutation_table[blocker.op.base_class][preindex]
|
138
|
+
|
139
|
+
if commutation_rule is not None:
|
140
|
+
while run_clone:
|
141
|
+
next_gate = run_clone[0] if front else run_clone[-1]
|
142
|
+
if next_gate.name not in commutation_rule:
|
143
|
+
break
|
144
|
+
if front:
|
145
|
+
run_clone.popleft()
|
146
|
+
commuted.append(next_gate)
|
147
|
+
else:
|
148
|
+
run_clone.pop()
|
149
|
+
commuted.appendleft(next_gate)
|
150
|
+
if front:
|
151
|
+
return list(commuted), list(run_clone)
|
152
|
+
else:
|
153
|
+
return list(run_clone), list(commuted)
|
154
|
+
|
155
|
+
def _resynthesize(self, run, qubit):
|
156
|
+
"""
|
157
|
+
Synthesizes an efficient circuit from a sequence `run` of `DAGOpNode`s.
|
158
|
+
|
159
|
+
NOTE: Returns None when resynthesis is not possible.
|
160
|
+
"""
|
161
|
+
if len(run) == 0:
|
162
|
+
dag = DAGCircuit()
|
163
|
+
dag.add_qreg(QuantumRegister(1))
|
164
|
+
return dag
|
165
|
+
operator = run[0].op.to_matrix()
|
166
|
+
for gate in run[1:]:
|
167
|
+
operator = gate.op.to_matrix().dot(operator)
|
168
|
+
return self._optimize1q._gate_sequence_to_dag(
|
169
|
+
self._optimize1q._resynthesize_run(operator, qubit)
|
170
|
+
)
|
171
|
+
|
172
|
+
@staticmethod
|
173
|
+
def _replace_subdag(dag, old_run, new_dag):
|
174
|
+
"""
|
175
|
+
Replaces a nonempty sequence `old_run` of `DAGNode`s, assumed to be a complete chain in
|
176
|
+
`dag`, with the circuit `new_circ`.
|
177
|
+
"""
|
178
|
+
|
179
|
+
node_map = dag.substitute_node_with_dag(old_run[0], new_dag)
|
180
|
+
|
181
|
+
for node in old_run[1:]:
|
182
|
+
dag.remove_op_node(node)
|
183
|
+
|
184
|
+
spliced_run = [node_map[node._node_id] for node in new_dag.topological_op_nodes()]
|
185
|
+
mov_list(old_run, spliced_run)
|
186
|
+
|
187
|
+
def _step(self, dag):
|
188
|
+
"""
|
189
|
+
Performs one full pass of optimization work.
|
190
|
+
|
191
|
+
Returns True if `dag` changed, False if no work on `dag` was possible.
|
192
|
+
"""
|
193
|
+
|
194
|
+
runs = dag.collect_1q_runs()
|
195
|
+
did_work = False
|
196
|
+
|
197
|
+
for run in runs:
|
198
|
+
# identify the preceding blocking gates
|
199
|
+
run_clone = copy(run)
|
200
|
+
if run == []:
|
201
|
+
continue
|
202
|
+
|
203
|
+
# try to modify preceding_run
|
204
|
+
preceding_blocker, preceding_run = self._find_adjoining_run(dag, runs, run)
|
205
|
+
commuted_preceding = []
|
206
|
+
if preceding_run != []:
|
207
|
+
commuted_preceding, run_clone = self._commute_through(preceding_blocker, run_clone)
|
208
|
+
|
209
|
+
# try to modify succeeding run
|
210
|
+
succeeding_blocker, succeeding_run = self._find_adjoining_run(
|
211
|
+
dag, runs, run, front=False
|
212
|
+
)
|
213
|
+
commuted_succeeding = []
|
214
|
+
if succeeding_run != []:
|
215
|
+
run_clone, commuted_succeeding = self._commute_through(
|
216
|
+
succeeding_blocker, run_clone, front=False
|
217
|
+
)
|
218
|
+
|
219
|
+
# re-synthesize
|
220
|
+
qubit = dag.find_bit(run[0].qargs[0]).index
|
221
|
+
new_preceding_run = self._resynthesize(preceding_run + commuted_preceding, qubit)
|
222
|
+
new_succeeding_run = self._resynthesize(commuted_succeeding + succeeding_run, qubit)
|
223
|
+
new_run = self._resynthesize(run_clone, qubit)
|
224
|
+
|
225
|
+
# perform the replacement if it was indeed a good idea
|
226
|
+
if self._optimize1q._substitution_checks(
|
227
|
+
(preceding_run or []) + run + (succeeding_run or []),
|
228
|
+
new_preceding_run.op_nodes() + new_run.op_nodes() + new_succeeding_run.op_nodes(),
|
229
|
+
self._optimize1q._basis_gates,
|
230
|
+
dag.find_bit(run[0].qargs[0]).index,
|
231
|
+
):
|
232
|
+
if preceding_run and new_preceding_run is not None:
|
233
|
+
self._replace_subdag(dag, preceding_run, new_preceding_run)
|
234
|
+
if succeeding_run and new_succeeding_run is not None:
|
235
|
+
self._replace_subdag(dag, succeeding_run, new_succeeding_run)
|
236
|
+
if new_run is not None:
|
237
|
+
self._replace_subdag(dag, run, new_run)
|
238
|
+
did_work = True
|
239
|
+
|
240
|
+
return did_work
|
241
|
+
|
242
|
+
def run(self, dag):
|
243
|
+
"""
|
244
|
+
Args:
|
245
|
+
dag (DAGCircuit): the DAG to be optimized.
|
246
|
+
|
247
|
+
Returns:
|
248
|
+
DAGCircuit: the optimized DAG.
|
249
|
+
"""
|
250
|
+
|
251
|
+
# python doesn't support tail calls
|
252
|
+
while True:
|
253
|
+
did_work = self._step(dag)
|
254
|
+
if not self._run_to_completion or not did_work:
|
255
|
+
break
|
256
|
+
|
257
|
+
return dag
|
258
|
+
|
259
|
+
|
260
|
+
def mov_list(destination, source):
|
261
|
+
"""
|
262
|
+
Replace `destination` in-place with `source`.
|
263
|
+
"""
|
264
|
+
|
265
|
+
while destination:
|
266
|
+
del destination[0]
|
267
|
+
destination += source
|