qiskit 1.4.1__cp39-abi3-macosx_11_0_arm64.whl → 2.0.0__cp39-abi3-macosx_11_0_arm64.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 +3 -9
- qiskit/_accelerate.abi3.so +0 -0
- qiskit/circuit/__init__.py +35 -10
- qiskit/circuit/{add_control.py → _add_control.py} +32 -12
- qiskit/circuit/_classical_resource_map.py +5 -3
- qiskit/circuit/barrier.py +3 -7
- qiskit/circuit/classical/expr/__init__.py +31 -3
- qiskit/circuit/classical/expr/constructors.py +236 -28
- qiskit/circuit/classical/expr/expr.py +104 -3
- qiskit/circuit/classical/expr/visitors.py +75 -0
- qiskit/circuit/classical/types/__init__.py +12 -8
- qiskit/circuit/classical/types/ordering.py +14 -7
- qiskit/circuit/classical/types/types.py +36 -0
- qiskit/circuit/commutation_checker.py +34 -7
- qiskit/circuit/controlflow/__init__.py +32 -1
- qiskit/circuit/controlflow/_builder_utils.py +9 -5
- qiskit/circuit/controlflow/box.py +163 -0
- qiskit/circuit/controlflow/break_loop.py +1 -1
- qiskit/circuit/controlflow/builder.py +139 -39
- qiskit/circuit/controlflow/continue_loop.py +1 -3
- qiskit/circuit/controlflow/control_flow.py +10 -0
- qiskit/circuit/controlflow/for_loop.py +2 -1
- qiskit/circuit/controlflow/if_else.py +3 -16
- qiskit/circuit/controlflow/switch_case.py +2 -8
- qiskit/circuit/controlflow/while_loop.py +2 -7
- qiskit/circuit/controlledgate.py +2 -4
- qiskit/circuit/delay.py +40 -11
- qiskit/circuit/duration.py +0 -15
- qiskit/circuit/gate.py +2 -4
- qiskit/circuit/instruction.py +2 -141
- qiskit/circuit/instructionset.py +7 -54
- qiskit/circuit/library/__init__.py +469 -154
- qiskit/circuit/library/arithmetic/__init__.py +16 -10
- qiskit/circuit/library/arithmetic/adders/cdkm_ripple_carry_adder.py +1 -1
- qiskit/circuit/library/arithmetic/adders/draper_qft_adder.py +2 -2
- qiskit/circuit/library/arithmetic/adders/vbe_ripple_carry_adder.py +1 -1
- qiskit/circuit/library/arithmetic/exact_reciprocal.py +64 -21
- qiskit/circuit/library/arithmetic/integer_comparator.py +37 -80
- qiskit/circuit/library/arithmetic/linear_amplitude_function.py +169 -2
- qiskit/circuit/library/arithmetic/linear_pauli_rotations.py +59 -5
- qiskit/circuit/library/arithmetic/piecewise_chebyshev.py +154 -6
- qiskit/circuit/library/arithmetic/piecewise_linear_pauli_rotations.py +114 -4
- qiskit/circuit/library/arithmetic/piecewise_polynomial_pauli_rotations.py +191 -15
- qiskit/circuit/library/arithmetic/polynomial_pauli_rotations.py +93 -39
- qiskit/circuit/library/arithmetic/quadratic_form.py +168 -2
- qiskit/circuit/library/arithmetic/weighted_adder.py +73 -1
- qiskit/circuit/library/bit_flip_oracle.py +130 -0
- qiskit/circuit/library/blueprintcircuit.py +52 -16
- qiskit/circuit/library/data_preparation/initializer.py +1 -1
- qiskit/circuit/library/data_preparation/pauli_feature_map.py +4 -4
- qiskit/circuit/library/data_preparation/state_preparation.py +1 -1
- qiskit/circuit/library/generalized_gates/gms.py +1 -1
- qiskit/circuit/library/generalized_gates/isometry.py +1 -1
- qiskit/circuit/library/generalized_gates/pauli.py +1 -2
- qiskit/circuit/library/generalized_gates/uc.py +97 -7
- qiskit/circuit/library/generalized_gates/uc_pauli_rot.py +1 -1
- qiskit/circuit/library/generalized_gates/unitary.py +4 -2
- qiskit/circuit/library/graph_state.py +1 -0
- qiskit/circuit/library/hamiltonian_gate.py +1 -1
- qiskit/circuit/library/n_local/evolved_operator_ansatz.py +1 -1
- qiskit/circuit/library/n_local/n_local.py +1 -1
- qiskit/circuit/library/n_local/qaoa_ansatz.py +1 -1
- qiskit/circuit/library/overlap.py +2 -2
- qiskit/circuit/library/pauli_evolution.py +39 -24
- qiskit/circuit/library/phase_oracle.py +130 -51
- qiskit/circuit/library/standard_gates/__init__.py +0 -1
- qiskit/circuit/library/standard_gates/dcx.py +3 -4
- qiskit/circuit/library/standard_gates/ecr.py +3 -4
- qiskit/circuit/library/standard_gates/global_phase.py +5 -6
- qiskit/circuit/library/standard_gates/h.py +4 -9
- qiskit/circuit/library/standard_gates/i.py +2 -2
- qiskit/circuit/library/standard_gates/iswap.py +3 -4
- qiskit/circuit/library/standard_gates/p.py +15 -34
- qiskit/circuit/library/standard_gates/r.py +7 -10
- qiskit/circuit/library/standard_gates/rx.py +5 -15
- qiskit/circuit/library/standard_gates/rxx.py +3 -6
- qiskit/circuit/library/standard_gates/ry.py +5 -17
- qiskit/circuit/library/standard_gates/ryy.py +3 -6
- qiskit/circuit/library/standard_gates/rz.py +5 -17
- qiskit/circuit/library/standard_gates/rzx.py +3 -6
- qiskit/circuit/library/standard_gates/rzz.py +3 -6
- qiskit/circuit/library/standard_gates/s.py +6 -15
- qiskit/circuit/library/standard_gates/swap.py +4 -11
- qiskit/circuit/library/standard_gates/sx.py +7 -12
- qiskit/circuit/library/standard_gates/t.py +6 -7
- qiskit/circuit/library/standard_gates/u.py +2 -10
- qiskit/circuit/library/standard_gates/u1.py +5 -16
- qiskit/circuit/library/standard_gates/u2.py +2 -6
- qiskit/circuit/library/standard_gates/u3.py +3 -11
- qiskit/circuit/library/standard_gates/x.py +14 -62
- qiskit/circuit/library/standard_gates/xx_minus_yy.py +2 -5
- qiskit/circuit/library/standard_gates/xx_plus_yy.py +2 -5
- qiskit/circuit/library/standard_gates/y.py +4 -9
- qiskit/circuit/library/standard_gates/z.py +5 -15
- qiskit/circuit/measure.py +11 -2
- qiskit/circuit/parameterexpression.py +11 -0
- qiskit/circuit/quantumcircuit.py +890 -564
- qiskit/circuit/random/utils.py +12 -6
- qiskit/circuit/reset.py +5 -2
- qiskit/circuit/singleton.py +5 -11
- qiskit/circuit/store.py +0 -8
- qiskit/circuit/tools/pi_check.py +3 -0
- qiskit/compiler/__init__.py +1 -7
- qiskit/compiler/transpiler.py +38 -196
- qiskit/converters/circuit_to_dag.py +6 -4
- qiskit/converters/circuit_to_dagdependency.py +0 -2
- qiskit/converters/circuit_to_dagdependency_v2.py +0 -1
- qiskit/converters/circuit_to_gate.py +1 -1
- qiskit/converters/circuit_to_instruction.py +16 -29
- qiskit/converters/dag_to_circuit.py +7 -8
- qiskit/converters/dag_to_dagdependency.py +0 -1
- qiskit/converters/dag_to_dagdependency_v2.py +0 -1
- qiskit/converters/dagdependency_to_circuit.py +0 -6
- qiskit/converters/dagdependency_to_dag.py +0 -6
- qiskit/dagcircuit/collect_blocks.py +32 -20
- qiskit/dagcircuit/dagdependency.py +3 -37
- qiskit/dagcircuit/dagdependency_v2.py +5 -82
- qiskit/dagcircuit/dagnode.py +14 -2
- qiskit/passmanager/__init__.py +24 -6
- qiskit/passmanager/passmanager.py +26 -24
- qiskit/primitives/__init__.py +44 -35
- qiskit/primitives/backend_estimator_v2.py +102 -23
- qiskit/primitives/backend_sampler_v2.py +5 -20
- qiskit/primitives/base/__init__.py +4 -4
- qiskit/primitives/base/base_estimator.py +77 -82
- qiskit/primitives/base/base_primitive_job.py +2 -2
- qiskit/primitives/base/{base_primitive.py → base_primitive_v1.py} +1 -1
- qiskit/primitives/base/{base_result.py → base_result_v1.py} +1 -1
- qiskit/primitives/base/base_sampler.py +52 -60
- qiskit/primitives/base/{estimator_result.py → estimator_result_v1.py} +2 -2
- qiskit/primitives/base/{sampler_result.py → sampler_result_v1.py} +2 -2
- qiskit/primitives/base/{validation.py → validation_v1.py} +34 -15
- qiskit/primitives/containers/bindings_array.py +3 -1
- qiskit/primitives/containers/bit_array.py +23 -0
- qiskit/primitives/containers/data_bin.py +3 -1
- qiskit/primitives/containers/observables_array.py +19 -2
- qiskit/primitives/statevector_sampler.py +6 -8
- qiskit/primitives/utils.py +14 -189
- qiskit/providers/__init__.py +4 -130
- qiskit/providers/backend.py +11 -314
- qiskit/providers/basic_provider/__init__.py +3 -1
- qiskit/providers/basic_provider/basic_provider.py +29 -9
- qiskit/providers/basic_provider/basic_simulator.py +158 -298
- qiskit/providers/exceptions.py +0 -33
- qiskit/providers/fake_provider/__init__.py +0 -37
- qiskit/providers/fake_provider/generic_backend_v2.py +32 -693
- qiskit/qasm2/__init__.py +21 -6
- qiskit/qasm2/export.py +2 -10
- qiskit/qasm2/parse.py +11 -25
- qiskit/qasm3/__init__.py +5 -1
- qiskit/qasm3/ast.py +44 -0
- qiskit/qasm3/exporter.py +65 -27
- qiskit/qasm3/printer.py +35 -4
- qiskit/qpy/__init__.py +162 -19
- qiskit/qpy/binary_io/__init__.py +0 -1
- qiskit/qpy/binary_io/circuits.py +96 -116
- qiskit/qpy/binary_io/parse_sympy_repr.py +121 -0
- qiskit/qpy/binary_io/schedules.py +61 -388
- qiskit/qpy/binary_io/value.py +159 -33
- qiskit/qpy/common.py +10 -7
- qiskit/qpy/formats.py +41 -0
- qiskit/qpy/interface.py +29 -62
- qiskit/qpy/type_keys.py +58 -221
- qiskit/quantum_info/analysis/distance.py +3 -1
- qiskit/quantum_info/operators/dihedral/dihedral.py +3 -1
- qiskit/quantum_info/operators/operator.py +6 -2
- qiskit/quantum_info/operators/symplectic/clifford.py +3 -1
- qiskit/quantum_info/operators/symplectic/pauli.py +4 -2
- qiskit/quantum_info/operators/symplectic/pauli_list.py +17 -5
- qiskit/quantum_info/operators/symplectic/sparse_pauli_op.py +40 -6
- qiskit/quantum_info/states/densitymatrix.py +16 -6
- qiskit/quantum_info/states/stabilizerstate.py +35 -4
- qiskit/quantum_info/states/statevector.py +16 -6
- qiskit/result/__init__.py +5 -17
- qiskit/result/models.py +18 -11
- qiskit/result/result.py +38 -134
- qiskit/result/sampled_expval.py +1 -2
- qiskit/result/utils.py +3 -4
- qiskit/synthesis/__init__.py +21 -1
- qiskit/synthesis/arithmetic/__init__.py +3 -1
- qiskit/synthesis/arithmetic/adders/cdkm_ripple_carry_adder.py +1 -1
- qiskit/synthesis/arithmetic/adders/draper_qft_adder.py +1 -1
- qiskit/synthesis/arithmetic/adders/vbe_ripple_carry_adder.py +2 -2
- qiskit/{providers/fake_provider/backends_v1/fake_20q → synthesis/arithmetic/comparators}/__init__.py +4 -6
- qiskit/synthesis/arithmetic/comparators/compare_2s.py +112 -0
- qiskit/synthesis/arithmetic/comparators/compare_greedy.py +66 -0
- qiskit/synthesis/arithmetic/multipliers/hrs_cumulative_multiplier.py +1 -1
- qiskit/synthesis/arithmetic/multipliers/rg_qft_multiplier.py +1 -1
- qiskit/synthesis/arithmetic/weighted_sum.py +155 -0
- qiskit/{result/mitigation → synthesis/boolean}/__init__.py +2 -2
- 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/discrete_basis/generate_basis_approximations.py +2 -0
- qiskit/synthesis/evolution/lie_trotter.py +10 -7
- qiskit/synthesis/evolution/product_formula.py +44 -35
- qiskit/synthesis/evolution/qdrift.py +17 -24
- qiskit/synthesis/evolution/suzuki_trotter.py +20 -27
- qiskit/synthesis/linear/linear_depth_lnn.py +6 -221
- qiskit/synthesis/linear_phase/cx_cz_depth_lnn.py +4 -205
- qiskit/synthesis/multi_controlled/__init__.py +1 -0
- qiskit/synthesis/multi_controlled/mcx_synthesis.py +5 -2
- qiskit/synthesis/multi_controlled/multi_control_rotation_gates.py +206 -0
- qiskit/synthesis/one_qubit/one_qubit_decompose.py +1 -1
- qiskit/synthesis/two_qubit/__init__.py +1 -0
- qiskit/synthesis/two_qubit/two_qubit_decompose.py +28 -145
- qiskit/transpiler/__init__.py +32 -232
- qiskit/transpiler/basepasses.py +20 -51
- qiskit/transpiler/layout.py +1 -1
- qiskit/transpiler/passes/__init__.py +4 -40
- qiskit/transpiler/passes/basis/basis_translator.py +5 -4
- qiskit/transpiler/passes/basis/decompose.py +1 -15
- qiskit/transpiler/passes/basis/unroll_3q_or_more.py +1 -5
- qiskit/transpiler/passes/basis/unroll_custom_definitions.py +3 -2
- qiskit/transpiler/passes/layout/apply_layout.py +4 -0
- qiskit/transpiler/passes/layout/dense_layout.py +2 -39
- qiskit/transpiler/passes/layout/full_ancilla_allocation.py +3 -4
- qiskit/transpiler/passes/layout/sabre_layout.py +7 -3
- qiskit/transpiler/passes/layout/vf2_layout.py +2 -20
- qiskit/transpiler/passes/layout/vf2_post_layout.py +60 -125
- qiskit/transpiler/passes/layout/vf2_utils.py +2 -26
- qiskit/transpiler/passes/optimization/__init__.py +2 -3
- qiskit/transpiler/passes/optimization/collect_and_collapse.py +2 -0
- qiskit/transpiler/passes/optimization/collect_cliffords.py +5 -0
- qiskit/transpiler/passes/optimization/collect_linear_functions.py +5 -0
- qiskit/transpiler/passes/optimization/collect_multiqubit_blocks.py +16 -1
- qiskit/transpiler/passes/optimization/commutation_analysis.py +3 -3
- qiskit/transpiler/passes/optimization/consolidate_blocks.py +41 -19
- qiskit/transpiler/passes/optimization/contract_idle_wires_in_control_flow.py +104 -0
- qiskit/transpiler/passes/optimization/light_cone.py +135 -0
- qiskit/transpiler/passes/optimization/optimize_1q_commutation.py +0 -1
- qiskit/transpiler/passes/optimization/optimize_1q_decomposition.py +18 -22
- qiskit/transpiler/passes/optimization/optimize_annotated.py +3 -2
- qiskit/transpiler/passes/optimization/remove_identity_equiv.py +6 -4
- qiskit/transpiler/passes/optimization/reset_after_measure_simplification.py +5 -2
- qiskit/transpiler/passes/optimization/split_2q_unitaries.py +26 -3
- qiskit/transpiler/passes/optimization/template_matching/template_substitution.py +3 -2
- qiskit/transpiler/passes/routing/__init__.py +0 -1
- qiskit/transpiler/passes/routing/commuting_2q_gate_routing/commuting_2q_gate_router.py +3 -1
- qiskit/transpiler/passes/routing/sabre_swap.py +14 -6
- qiskit/transpiler/passes/routing/star_prerouting.py +1 -1
- qiskit/transpiler/passes/scheduling/__init__.py +1 -7
- qiskit/transpiler/passes/scheduling/alignments/__init__.py +2 -4
- qiskit/transpiler/passes/scheduling/alignments/check_durations.py +1 -9
- qiskit/transpiler/passes/scheduling/alignments/reschedule.py +17 -16
- qiskit/transpiler/passes/scheduling/padding/base_padding.py +32 -4
- qiskit/transpiler/passes/scheduling/padding/dynamical_decoupling.py +25 -63
- qiskit/transpiler/passes/scheduling/padding/pad_delay.py +12 -4
- qiskit/transpiler/passes/scheduling/scheduling/alap.py +5 -39
- qiskit/transpiler/passes/scheduling/scheduling/asap.py +4 -35
- qiskit/transpiler/passes/scheduling/scheduling/base_scheduler.py +10 -16
- qiskit/transpiler/passes/scheduling/time_unit_conversion.py +134 -62
- qiskit/transpiler/passes/synthesis/default_unitary_synth_plugin.py +653 -0
- qiskit/transpiler/passes/synthesis/high_level_synthesis.py +176 -601
- qiskit/transpiler/passes/synthesis/hls_plugins.py +294 -1
- qiskit/transpiler/passes/synthesis/plugin.py +4 -0
- qiskit/transpiler/passes/synthesis/solovay_kitaev_synthesis.py +16 -10
- qiskit/transpiler/passes/synthesis/unitary_synthesis.py +34 -697
- qiskit/transpiler/passes/utils/__init__.py +0 -1
- qiskit/transpiler/passes/utils/check_gate_direction.py +13 -5
- qiskit/transpiler/passes/utils/control_flow.py +2 -6
- qiskit/transpiler/passes/utils/gate_direction.py +7 -0
- qiskit/transpiler/passes/utils/remove_final_measurements.py +40 -33
- qiskit/transpiler/passmanager.py +13 -0
- qiskit/transpiler/passmanager_config.py +5 -81
- qiskit/transpiler/preset_passmanagers/builtin_plugins.py +225 -344
- qiskit/transpiler/preset_passmanagers/common.py +140 -167
- qiskit/transpiler/preset_passmanagers/generate_preset_pass_manager.py +107 -322
- qiskit/transpiler/preset_passmanagers/level0.py +2 -11
- qiskit/transpiler/preset_passmanagers/level1.py +2 -14
- qiskit/transpiler/preset_passmanagers/level2.py +2 -12
- qiskit/transpiler/preset_passmanagers/level3.py +2 -11
- qiskit/transpiler/preset_passmanagers/plugin.py +5 -3
- qiskit/transpiler/target.py +78 -524
- qiskit/user_config.py +8 -4
- qiskit/utils/__init__.py +13 -12
- qiskit/utils/deprecation.py +4 -112
- qiskit/utils/optionals.py +11 -4
- qiskit/utils/parallel.py +214 -87
- qiskit/utils/units.py +4 -1
- qiskit/visualization/__init__.py +3 -7
- qiskit/visualization/array.py +4 -1
- qiskit/visualization/bloch.py +1 -1
- qiskit/visualization/circuit/_utils.py +19 -19
- qiskit/visualization/circuit/circuit_visualization.py +11 -4
- qiskit/visualization/circuit/matplotlib.py +13 -23
- qiskit/visualization/circuit/text.py +7 -3
- qiskit/visualization/counts_visualization.py +4 -0
- qiskit/visualization/dag_visualization.py +2 -1
- qiskit/visualization/gate_map.py +39 -154
- qiskit/visualization/library.py +4 -1
- qiskit/visualization/pass_manager_visualization.py +6 -2
- qiskit/visualization/state_visualization.py +19 -2
- qiskit/visualization/timeline/core.py +19 -13
- qiskit/visualization/timeline/interface.py +19 -18
- qiskit/visualization/timeline/plotters/matplotlib.py +4 -1
- {qiskit-1.4.1.dist-info → qiskit-2.0.0.dist-info}/METADATA +4 -3
- {qiskit-1.4.1.dist-info → qiskit-2.0.0.dist-info}/RECORD +303 -449
- {qiskit-1.4.1.dist-info → qiskit-2.0.0.dist-info}/WHEEL +2 -1
- {qiskit-1.4.1.dist-info → qiskit-2.0.0.dist-info}/entry_points.txt +8 -2
- qiskit/assembler/__init__.py +0 -42
- qiskit/assembler/assemble_circuits.py +0 -451
- qiskit/assembler/assemble_schedules.py +0 -367
- qiskit/assembler/disassemble.py +0 -310
- qiskit/assembler/run_config.py +0 -77
- qiskit/circuit/bit.py +0 -106
- qiskit/circuit/classicalfunction/__init__.py +0 -152
- qiskit/circuit/classicalfunction/boolean_expression.py +0 -138
- qiskit/circuit/classicalfunction/classical_element.py +0 -54
- qiskit/circuit/classicalfunction/classical_function_visitor.py +0 -155
- qiskit/circuit/classicalfunction/classicalfunction.py +0 -182
- qiskit/circuit/classicalfunction/exceptions.py +0 -41
- qiskit/circuit/classicalfunction/types.py +0 -18
- qiskit/circuit/classicalfunction/utils.py +0 -91
- qiskit/circuit/classicalregister.py +0 -57
- qiskit/circuit/library/standard_gates/multi_control_rotation_gates.py +0 -405
- qiskit/circuit/quantumregister.py +0 -75
- qiskit/circuit/register.py +0 -246
- qiskit/compiler/assembler.py +0 -689
- qiskit/compiler/scheduler.py +0 -109
- qiskit/compiler/sequencer.py +0 -71
- qiskit/primitives/backend_estimator.py +0 -486
- qiskit/primitives/backend_sampler.py +0 -222
- qiskit/primitives/estimator.py +0 -172
- qiskit/primitives/sampler.py +0 -162
- qiskit/providers/backend_compat.py +0 -507
- qiskit/providers/fake_provider/backends_v1/__init__.py +0 -22
- qiskit/providers/fake_provider/backends_v1/fake_127q_pulse/__init__.py +0 -18
- qiskit/providers/fake_provider/backends_v1/fake_127q_pulse/conf_washington.json +0 -1
- qiskit/providers/fake_provider/backends_v1/fake_127q_pulse/defs_washington.json +0 -1
- qiskit/providers/fake_provider/backends_v1/fake_127q_pulse/fake_127q_pulse_v1.py +0 -37
- qiskit/providers/fake_provider/backends_v1/fake_127q_pulse/props_washington.json +0 -1
- qiskit/providers/fake_provider/backends_v1/fake_20q/conf_singapore.json +0 -1
- qiskit/providers/fake_provider/backends_v1/fake_20q/fake_20q.py +0 -43
- qiskit/providers/fake_provider/backends_v1/fake_20q/props_singapore.json +0 -1
- qiskit/providers/fake_provider/backends_v1/fake_27q_pulse/__init__.py +0 -18
- qiskit/providers/fake_provider/backends_v1/fake_27q_pulse/conf_hanoi.json +0 -1
- qiskit/providers/fake_provider/backends_v1/fake_27q_pulse/defs_hanoi.json +0 -1
- qiskit/providers/fake_provider/backends_v1/fake_27q_pulse/fake_27q_pulse_v1.py +0 -50
- qiskit/providers/fake_provider/backends_v1/fake_27q_pulse/props_hanoi.json +0 -1
- qiskit/providers/fake_provider/backends_v1/fake_5q/__init__.py +0 -18
- qiskit/providers/fake_provider/backends_v1/fake_5q/conf_yorktown.json +0 -1
- qiskit/providers/fake_provider/backends_v1/fake_5q/fake_5q_v1.py +0 -41
- qiskit/providers/fake_provider/backends_v1/fake_5q/props_yorktown.json +0 -1
- qiskit/providers/fake_provider/backends_v1/fake_7q_pulse/__init__.py +0 -18
- qiskit/providers/fake_provider/backends_v1/fake_7q_pulse/conf_nairobi.json +0 -1
- qiskit/providers/fake_provider/backends_v1/fake_7q_pulse/defs_nairobi.json +0 -1
- qiskit/providers/fake_provider/backends_v1/fake_7q_pulse/fake_7q_pulse_v1.py +0 -44
- qiskit/providers/fake_provider/backends_v1/fake_7q_pulse/props_nairobi.json +0 -1
- qiskit/providers/fake_provider/fake_1q.py +0 -91
- qiskit/providers/fake_provider/fake_backend.py +0 -165
- qiskit/providers/fake_provider/fake_openpulse_2q.py +0 -391
- qiskit/providers/fake_provider/fake_openpulse_3q.py +0 -340
- qiskit/providers/fake_provider/fake_pulse_backend.py +0 -49
- qiskit/providers/fake_provider/fake_qasm_backend.py +0 -77
- qiskit/providers/fake_provider/utils/backend_converter.py +0 -150
- qiskit/providers/fake_provider/utils/json_decoder.py +0 -109
- qiskit/providers/models/__init__.py +0 -89
- qiskit/providers/models/backendconfiguration.py +0 -1040
- qiskit/providers/models/backendproperties.py +0 -535
- qiskit/providers/models/backendstatus.py +0 -104
- qiskit/providers/models/jobstatus.py +0 -77
- qiskit/providers/models/pulsedefaults.py +0 -305
- qiskit/providers/provider.py +0 -95
- qiskit/pulse/__init__.py +0 -158
- qiskit/pulse/builder.py +0 -2262
- qiskit/pulse/calibration_entries.py +0 -381
- qiskit/pulse/channels.py +0 -227
- qiskit/pulse/configuration.py +0 -245
- qiskit/pulse/exceptions.py +0 -45
- qiskit/pulse/filters.py +0 -309
- qiskit/pulse/instruction_schedule_map.py +0 -424
- qiskit/pulse/instructions/__init__.py +0 -67
- qiskit/pulse/instructions/acquire.py +0 -150
- qiskit/pulse/instructions/delay.py +0 -71
- qiskit/pulse/instructions/directives.py +0 -154
- qiskit/pulse/instructions/frequency.py +0 -135
- qiskit/pulse/instructions/instruction.py +0 -270
- qiskit/pulse/instructions/phase.py +0 -152
- qiskit/pulse/instructions/play.py +0 -99
- qiskit/pulse/instructions/reference.py +0 -100
- qiskit/pulse/instructions/snapshot.py +0 -82
- qiskit/pulse/library/__init__.py +0 -97
- qiskit/pulse/library/continuous.py +0 -430
- qiskit/pulse/library/pulse.py +0 -148
- qiskit/pulse/library/samplers/__init__.py +0 -15
- qiskit/pulse/library/samplers/decorators.py +0 -295
- qiskit/pulse/library/samplers/strategies.py +0 -71
- qiskit/pulse/library/symbolic_pulses.py +0 -1989
- qiskit/pulse/library/waveform.py +0 -136
- qiskit/pulse/macros.py +0 -262
- qiskit/pulse/parameter_manager.py +0 -445
- qiskit/pulse/parser.py +0 -314
- qiskit/pulse/reference_manager.py +0 -58
- qiskit/pulse/schedule.py +0 -1854
- qiskit/pulse/transforms/__init__.py +0 -106
- qiskit/pulse/transforms/alignments.py +0 -406
- qiskit/pulse/transforms/base_transforms.py +0 -71
- qiskit/pulse/transforms/canonicalization.py +0 -498
- qiskit/pulse/transforms/dag.py +0 -122
- qiskit/pulse/utils.py +0 -149
- qiskit/qobj/__init__.py +0 -75
- qiskit/qobj/common.py +0 -81
- qiskit/qobj/converters/__init__.py +0 -18
- qiskit/qobj/converters/lo_config.py +0 -177
- qiskit/qobj/converters/pulse_instruction.py +0 -897
- qiskit/qobj/pulse_qobj.py +0 -709
- qiskit/qobj/qasm_qobj.py +0 -708
- qiskit/qobj/utils.py +0 -46
- qiskit/result/mitigation/base_readout_mitigator.py +0 -79
- qiskit/result/mitigation/correlated_readout_mitigator.py +0 -277
- qiskit/result/mitigation/local_readout_mitigator.py +0 -328
- qiskit/result/mitigation/utils.py +0 -217
- qiskit/scheduler/__init__.py +0 -40
- qiskit/scheduler/config.py +0 -37
- qiskit/scheduler/lowering.py +0 -187
- qiskit/scheduler/methods/__init__.py +0 -15
- qiskit/scheduler/methods/basic.py +0 -140
- qiskit/scheduler/schedule_circuit.py +0 -69
- qiskit/scheduler/sequence.py +0 -104
- qiskit/transpiler/passes/calibration/__init__.py +0 -17
- qiskit/transpiler/passes/calibration/base_builder.py +0 -79
- qiskit/transpiler/passes/calibration/builders.py +0 -20
- qiskit/transpiler/passes/calibration/exceptions.py +0 -22
- qiskit/transpiler/passes/calibration/pulse_gate.py +0 -100
- qiskit/transpiler/passes/calibration/rx_builder.py +0 -164
- qiskit/transpiler/passes/calibration/rzx_builder.py +0 -411
- qiskit/transpiler/passes/calibration/rzx_templates.py +0 -58
- qiskit/transpiler/passes/optimization/cx_cancellation.py +0 -65
- qiskit/transpiler/passes/optimization/echo_rzx_weyl_decomposition.py +0 -162
- qiskit/transpiler/passes/optimization/normalize_rx_angle.py +0 -157
- qiskit/transpiler/passes/routing/stochastic_swap.py +0 -532
- qiskit/transpiler/passes/scheduling/alap.py +0 -153
- qiskit/transpiler/passes/scheduling/alignments/align_measures.py +0 -255
- qiskit/transpiler/passes/scheduling/alignments/pulse_gate_validation.py +0 -107
- qiskit/transpiler/passes/scheduling/asap.py +0 -175
- qiskit/transpiler/passes/scheduling/base_scheduler.py +0 -310
- qiskit/transpiler/passes/scheduling/dynamical_decoupling.py +0 -313
- qiskit/transpiler/passes/utils/convert_conditions_to_if_ops.py +0 -93
- qiskit/utils/deprecate_pulse.py +0 -119
- qiskit/utils/multiprocessing.py +0 -56
- qiskit/visualization/pulse_v2/__init__.py +0 -21
- qiskit/visualization/pulse_v2/core.py +0 -901
- qiskit/visualization/pulse_v2/device_info.py +0 -173
- qiskit/visualization/pulse_v2/drawings.py +0 -253
- qiskit/visualization/pulse_v2/events.py +0 -254
- qiskit/visualization/pulse_v2/generators/__init__.py +0 -40
- qiskit/visualization/pulse_v2/generators/barrier.py +0 -76
- qiskit/visualization/pulse_v2/generators/chart.py +0 -208
- qiskit/visualization/pulse_v2/generators/frame.py +0 -436
- qiskit/visualization/pulse_v2/generators/snapshot.py +0 -133
- qiskit/visualization/pulse_v2/generators/waveform.py +0 -645
- qiskit/visualization/pulse_v2/interface.py +0 -459
- qiskit/visualization/pulse_v2/layouts.py +0 -387
- qiskit/visualization/pulse_v2/plotters/__init__.py +0 -17
- qiskit/visualization/pulse_v2/plotters/base_plotter.py +0 -53
- qiskit/visualization/pulse_v2/plotters/matplotlib.py +0 -201
- qiskit/visualization/pulse_v2/stylesheet.py +0 -312
- qiskit/visualization/pulse_v2/types.py +0 -242
- {qiskit-1.4.1.dist-info → qiskit-2.0.0.dist-info/licenses}/LICENSE.txt +0 -0
- {qiskit-1.4.1.dist-info → qiskit-2.0.0.dist-info}/top_level.txt +0 -0
@@ -19,6 +19,7 @@ from __future__ import annotations
|
|
19
19
|
|
20
20
|
__all__ = [
|
21
21
|
"lift",
|
22
|
+
"cast",
|
22
23
|
"bit_not",
|
23
24
|
"logic_not",
|
24
25
|
"bit_and",
|
@@ -32,6 +33,13 @@ __all__ = [
|
|
32
33
|
"less_equal",
|
33
34
|
"greater",
|
34
35
|
"greater_equal",
|
36
|
+
"shift_left",
|
37
|
+
"shift_right",
|
38
|
+
"index",
|
39
|
+
"add",
|
40
|
+
"sub",
|
41
|
+
"mul",
|
42
|
+
"div",
|
35
43
|
"lift_legacy_condition",
|
36
44
|
]
|
37
45
|
|
@@ -45,9 +53,9 @@ if typing.TYPE_CHECKING:
|
|
45
53
|
import qiskit
|
46
54
|
|
47
55
|
|
48
|
-
def _coerce_lossless(expr: Expr, type: types.Type) -> Expr:
|
56
|
+
def _coerce_lossless(expr: Expr, type: types.Type) -> Expr | None:
|
49
57
|
"""Coerce ``expr`` to ``type`` by inserting a suitable :class:`Cast` node, if the cast is
|
50
|
-
lossless. Otherwise,
|
58
|
+
lossless. Otherwise, return ``None``."""
|
51
59
|
kind = cast_kind(expr.type, type)
|
52
60
|
if kind is CastKind.EQUAL:
|
53
61
|
return expr
|
@@ -55,29 +63,13 @@ def _coerce_lossless(expr: Expr, type: types.Type) -> Expr:
|
|
55
63
|
return Cast(expr, type, implicit=True)
|
56
64
|
if kind is CastKind.LOSSLESS:
|
57
65
|
return Cast(expr, type, implicit=False)
|
58
|
-
|
59
|
-
raise TypeError(f"cannot cast '{expr}' to '{type}' without loss of precision")
|
60
|
-
raise TypeError(f"no cast is defined to take '{expr}' to '{type}'")
|
66
|
+
return None
|
61
67
|
|
62
68
|
|
63
69
|
def lift_legacy_condition(
|
64
70
|
condition: tuple[qiskit.circuit.Clbit | qiskit.circuit.ClassicalRegister, int], /
|
65
71
|
) -> Expr:
|
66
|
-
"""Lift a legacy two-tuple equality condition into a new-style :class:`Expr`.
|
67
|
-
|
68
|
-
Examples:
|
69
|
-
Taking an old-style conditional instruction and getting an :class:`Expr` from its
|
70
|
-
condition::
|
71
|
-
|
72
|
-
from qiskit.circuit import ClassicalRegister
|
73
|
-
from qiskit.circuit.library import HGate
|
74
|
-
from qiskit.circuit.classical import expr
|
75
|
-
|
76
|
-
cr = ClassicalRegister(2)
|
77
|
-
instr = HGate().c_if(cr, 3)
|
78
|
-
|
79
|
-
lifted = expr.lift_legacy_condition(instr.condition)
|
80
|
-
"""
|
72
|
+
"""Lift a legacy two-tuple equality condition into a new-style :class:`Expr`."""
|
81
73
|
from qiskit.circuit import Clbit # pylint: disable=cyclic-import
|
82
74
|
|
83
75
|
target, value = condition
|
@@ -121,7 +113,7 @@ def lift(value: typing.Any, /, type: types.Type | None = None) -> Expr:
|
|
121
113
|
if type is not None:
|
122
114
|
raise ValueError("use 'cast' to cast existing expressions, not 'lift'")
|
123
115
|
return value
|
124
|
-
from qiskit.circuit import Clbit, ClassicalRegister # pylint: disable=cyclic-import
|
116
|
+
from qiskit.circuit import Clbit, ClassicalRegister, Duration # pylint: disable=cyclic-import
|
125
117
|
|
126
118
|
inferred: types.Type
|
127
119
|
if value is True or value is False or isinstance(value, Clbit):
|
@@ -135,6 +127,12 @@ def lift(value: typing.Any, /, type: types.Type | None = None) -> Expr:
|
|
135
127
|
raise ValueError("cannot represent a negative value")
|
136
128
|
inferred = types.Uint(width=value.bit_length() or 1)
|
137
129
|
constructor = Value
|
130
|
+
elif isinstance(value, float):
|
131
|
+
inferred = types.Float()
|
132
|
+
constructor = Value
|
133
|
+
elif isinstance(value, Duration):
|
134
|
+
inferred = types.Duration()
|
135
|
+
constructor = Value
|
138
136
|
else:
|
139
137
|
raise TypeError(f"failed to infer a type for '{value}'")
|
140
138
|
if type is None:
|
@@ -195,11 +193,15 @@ def logic_not(operand: typing.Any, /) -> Expr:
|
|
195
193
|
>>> expr.logic_not(ClassicalRegister(3, "c"))
|
196
194
|
Unary(\
|
197
195
|
Unary.Op.LOGIC_NOT, \
|
198
|
-
Cast(Var(ClassicalRegister(3, 'c'), Uint(3)),
|
196
|
+
Cast(Var(ClassicalRegister(3, 'c'), Uint(3)), \
|
197
|
+
Bool(), implicit=True), \
|
199
198
|
Bool())
|
200
199
|
"""
|
201
|
-
operand =
|
202
|
-
|
200
|
+
operand = lift(operand)
|
201
|
+
coerced_operand = _coerce_lossless(operand, types.Bool())
|
202
|
+
if coerced_operand is None:
|
203
|
+
raise TypeError(f"cannot apply '{Unary.Op.LOGIC_NOT}' to type '{operand.type}'")
|
204
|
+
return Unary(Unary.Op.LOGIC_NOT, coerced_operand, coerced_operand.type)
|
203
205
|
|
204
206
|
|
205
207
|
def _lift_binary_operands(left: typing.Any, right: typing.Any) -> tuple[Expr, Expr]:
|
@@ -314,9 +316,13 @@ Uint(3))
|
|
314
316
|
|
315
317
|
def _binary_logical(op: Binary.Op, left: typing.Any, right: typing.Any) -> Expr:
|
316
318
|
bool_ = types.Bool()
|
317
|
-
left =
|
318
|
-
right =
|
319
|
-
|
319
|
+
left = lift(left)
|
320
|
+
right = lift(right)
|
321
|
+
coerced_left = _coerce_lossless(left, bool_)
|
322
|
+
coerced_right = _coerce_lossless(right, bool_)
|
323
|
+
if coerced_left is None or coerced_right is None:
|
324
|
+
raise TypeError(f"invalid types for '{op}': '{left.type}' and '{right.type}'")
|
325
|
+
return Binary(op, coerced_left, coerced_right, bool_)
|
320
326
|
|
321
327
|
|
322
328
|
def logic_and(left: typing.Any, right: typing.Any, /) -> Expr:
|
@@ -354,6 +360,8 @@ def _equal_like(op: Binary.Op, left: typing.Any, right: typing.Any) -> Expr:
|
|
354
360
|
if left.type.kind is not right.type.kind:
|
355
361
|
raise TypeError(f"invalid types for '{op}': '{left.type}' and '{right.type}'")
|
356
362
|
type = types.greater(left.type, right.type)
|
363
|
+
# Note that we don't check the return value of _coerce_lossless for these
|
364
|
+
# since 'left' and 'right' are guaranteed to be the same kind here.
|
357
365
|
return Binary(op, _coerce_lossless(left, type), _coerce_lossless(right, type), types.Bool())
|
358
366
|
|
359
367
|
|
@@ -398,6 +406,8 @@ def _binary_relation(op: Binary.Op, left: typing.Any, right: typing.Any) -> Expr
|
|
398
406
|
if left.type.kind is not right.type.kind or left.type.kind is types.Bool:
|
399
407
|
raise TypeError(f"invalid types for '{op}': '{left.type}' and '{right.type}'")
|
400
408
|
type = types.greater(left.type, right.type)
|
409
|
+
# Note that we don't check the return value of _coerce_lossless for these
|
410
|
+
# since 'left' and 'right' are guaranteed to be the same kind here.
|
401
411
|
return Binary(op, _coerce_lossless(left, type), _coerce_lossless(right, type), types.Bool())
|
402
412
|
|
403
413
|
|
@@ -479,7 +489,11 @@ def _shift_like(
|
|
479
489
|
if type is not None and type.kind is not types.Uint:
|
480
490
|
raise TypeError(f"type '{type}' is not a valid bitshift operand type")
|
481
491
|
if isinstance(left, Expr):
|
482
|
-
|
492
|
+
if type is not None:
|
493
|
+
coerced_left = _coerce_lossless(left, type)
|
494
|
+
if coerced_left is None:
|
495
|
+
raise TypeError(f"type '{type}' cannot losslessly represent '{left.type}'")
|
496
|
+
left = coerced_left
|
483
497
|
else:
|
484
498
|
left = lift(left, type)
|
485
499
|
right = lift(right)
|
@@ -554,3 +568,197 @@ def index(target: typing.Any, index: typing.Any, /) -> Expr:
|
|
554
568
|
if target.type.kind is not types.Uint or index.type.kind is not types.Uint:
|
555
569
|
raise TypeError(f"invalid types for indexing: '{target.type}' and '{index.type}'")
|
556
570
|
return Index(target, index, types.Bool())
|
571
|
+
|
572
|
+
|
573
|
+
def _binary_sum(op: Binary.Op, left: typing.Any, right: typing.Any) -> Expr:
|
574
|
+
left, right = _lift_binary_operands(left, right)
|
575
|
+
if left.type.kind is right.type.kind and left.type.kind in {
|
576
|
+
types.Uint,
|
577
|
+
types.Float,
|
578
|
+
types.Duration,
|
579
|
+
}:
|
580
|
+
type = types.greater(left.type, right.type)
|
581
|
+
return Binary(
|
582
|
+
op,
|
583
|
+
_coerce_lossless(left, type),
|
584
|
+
_coerce_lossless(right, type),
|
585
|
+
type,
|
586
|
+
)
|
587
|
+
raise TypeError(f"invalid types for '{op}': '{left.type}' and '{right.type}'")
|
588
|
+
|
589
|
+
|
590
|
+
def add(left: typing.Any, right: typing.Any, /) -> Expr:
|
591
|
+
"""Create an addition expression node from the given values, resolving any implicit casts and
|
592
|
+
lifting the values into :class:`Value` nodes if required.
|
593
|
+
|
594
|
+
Examples:
|
595
|
+
Addition of two floating point numbers::
|
596
|
+
|
597
|
+
>>> from qiskit.circuit.classical import expr
|
598
|
+
>>> expr.add(5.0, 2.0)
|
599
|
+
Binary(\
|
600
|
+
Binary.Op.ADD, \
|
601
|
+
Value(5.0, Float()), \
|
602
|
+
Value(2.0, Float()), \
|
603
|
+
Float())
|
604
|
+
|
605
|
+
Addition of two durations::
|
606
|
+
|
607
|
+
>>> from qiskit.circuit import Duration
|
608
|
+
>>> from qiskit.circuit.classical import expr
|
609
|
+
>>> expr.add(Duration.dt(1000), Duration.dt(1000))
|
610
|
+
Binary(\
|
611
|
+
Binary.Op.ADD, \
|
612
|
+
Value(Duration.dt(1000), Duration()), \
|
613
|
+
Value(Duration.dt(1000), Duration()), \
|
614
|
+
Duration())
|
615
|
+
"""
|
616
|
+
return _binary_sum(Binary.Op.ADD, left, right)
|
617
|
+
|
618
|
+
|
619
|
+
def sub(left: typing.Any, right: typing.Any, /) -> Expr:
|
620
|
+
"""Create a subtraction expression node from the given values, resolving any implicit casts and
|
621
|
+
lifting the values into :class:`Value` nodes if required.
|
622
|
+
|
623
|
+
Examples:
|
624
|
+
Subtraction of two floating point numbers::
|
625
|
+
|
626
|
+
>>> from qiskit.circuit.classical import expr
|
627
|
+
>>> expr.sub(5.0, 2.0)
|
628
|
+
Binary(\
|
629
|
+
Binary.Op.SUB, \
|
630
|
+
Value(5.0, Float()), \
|
631
|
+
Value(2.0, Float()), \
|
632
|
+
Float())
|
633
|
+
|
634
|
+
Subtraction of two durations::
|
635
|
+
|
636
|
+
>>> from qiskit.circuit import Duration
|
637
|
+
>>> from qiskit.circuit.classical import expr
|
638
|
+
>>> expr.add(Duration.dt(1000), Duration.dt(1000))
|
639
|
+
Binary(\
|
640
|
+
Binary.Op.SUB, \
|
641
|
+
Value(Duration.dt(1000), Duration()), \
|
642
|
+
Value(Duration.dt(1000), Duration()), \
|
643
|
+
Duration())
|
644
|
+
"""
|
645
|
+
return _binary_sum(Binary.Op.SUB, left, right)
|
646
|
+
|
647
|
+
|
648
|
+
def mul(left: typing.Any, right: typing.Any) -> Expr:
|
649
|
+
"""Create a multiplication expression node from the given values, resolving any implicit casts and
|
650
|
+
lifting the values into :class:`Value` nodes if required.
|
651
|
+
|
652
|
+
This can be used to multiply numeric operands of the same type kind, or to multiply a duration
|
653
|
+
operand by a numeric operand.
|
654
|
+
|
655
|
+
Examples:
|
656
|
+
Multiplication of two floating point numbers::
|
657
|
+
|
658
|
+
>>> from qiskit.circuit.classical import expr
|
659
|
+
>>> expr.mul(5.0, 2.0)
|
660
|
+
Binary(\
|
661
|
+
Binary.Op.MUL, \
|
662
|
+
Value(5.0, Float()), \
|
663
|
+
Value(2.0, Float()), \
|
664
|
+
Float())
|
665
|
+
|
666
|
+
Multiplication of a duration by a float::
|
667
|
+
|
668
|
+
>>> from qiskit.circuit import Duration
|
669
|
+
>>> from qiskit.circuit.classical import expr
|
670
|
+
>>> expr.mul(Duration.dt(1000), 0.5)
|
671
|
+
Binary(\
|
672
|
+
Binary.Op.MUL, \
|
673
|
+
Value(Duration.dt(1000), Duration()), \
|
674
|
+
Value(0.5, Float()), \
|
675
|
+
Duration())
|
676
|
+
"""
|
677
|
+
left, right = _lift_binary_operands(left, right)
|
678
|
+
type: types.Type
|
679
|
+
if left.type.kind is right.type.kind is types.Duration:
|
680
|
+
raise TypeError("cannot multiply two durations")
|
681
|
+
if left.type.kind is right.type.kind and left.type.kind in {types.Uint, types.Float}:
|
682
|
+
type = types.greater(left.type, right.type)
|
683
|
+
left = _coerce_lossless(left, type)
|
684
|
+
right = _coerce_lossless(right, type)
|
685
|
+
elif left.type.kind is types.Duration and right.type.kind in {types.Uint, types.Float}:
|
686
|
+
type = left.type
|
687
|
+
elif right.type.kind is types.Duration and left.type.kind in {types.Uint, types.Float}:
|
688
|
+
type = right.type
|
689
|
+
else:
|
690
|
+
raise TypeError(f"invalid types for '{Binary.Op.MUL}': '{left.type}' and '{right.type}'")
|
691
|
+
return Binary(
|
692
|
+
Binary.Op.MUL,
|
693
|
+
left,
|
694
|
+
right,
|
695
|
+
type,
|
696
|
+
)
|
697
|
+
|
698
|
+
|
699
|
+
def div(left: typing.Any, right: typing.Any) -> Expr:
|
700
|
+
"""Create a division expression node from the given values, resolving any implicit casts and
|
701
|
+
lifting the values into :class:`Value` nodes if required.
|
702
|
+
|
703
|
+
This can be used to divide numeric operands of the same type kind, to divide a
|
704
|
+
:class`~.types.Duration` operand by a numeric operand, or to divide two
|
705
|
+
:class`~.types.Duration` operands which yields an expression of type
|
706
|
+
:class:`~.types.Float`.
|
707
|
+
|
708
|
+
Examples:
|
709
|
+
Division of two floating point numbers::
|
710
|
+
|
711
|
+
>>> from qiskit.circuit.classical import expr
|
712
|
+
>>> expr.div(5.0, 2.0)
|
713
|
+
Binary(\
|
714
|
+
Binary.Op.DIV, \
|
715
|
+
Value(5.0, Float()), \
|
716
|
+
Value(2.0, Float()), \
|
717
|
+
Float())
|
718
|
+
|
719
|
+
Division of two durations::
|
720
|
+
|
721
|
+
>>> from qiskit.circuit import Duration
|
722
|
+
>>> from qiskit.circuit.classical import expr
|
723
|
+
>>> expr.div(Duration.dt(10000), Duration.dt(1000))
|
724
|
+
Binary(\
|
725
|
+
Binary.Op.DIV, \
|
726
|
+
Value(Duration.dt(10000), Duration()), \
|
727
|
+
Value(Duration.dt(1000), Duration()), \
|
728
|
+
Float())
|
729
|
+
|
730
|
+
|
731
|
+
Division of a duration by a float::
|
732
|
+
|
733
|
+
>>> from qiskit.circuit import Duration
|
734
|
+
>>> from qiskit.circuit.classical import expr
|
735
|
+
>>> expr.div(Duration.dt(10000), 12.0)
|
736
|
+
Binary(\
|
737
|
+
Binary.Op.DIV, \
|
738
|
+
Value(Duration.dt(10000), Duration()), \
|
739
|
+
Value(12.0, types.Float()), \
|
740
|
+
Duration())
|
741
|
+
"""
|
742
|
+
left, right = _lift_binary_operands(left, right)
|
743
|
+
type: types.Type
|
744
|
+
if left.type.kind is right.type.kind and left.type.kind in {
|
745
|
+
types.Duration,
|
746
|
+
types.Uint,
|
747
|
+
types.Float,
|
748
|
+
}:
|
749
|
+
if left.type.kind is types.Duration:
|
750
|
+
type = types.Float()
|
751
|
+
elif types.order(left.type, right.type) is not types.Ordering.NONE:
|
752
|
+
type = types.greater(left.type, right.type)
|
753
|
+
left = _coerce_lossless(left, type)
|
754
|
+
right = _coerce_lossless(right, type)
|
755
|
+
elif left.type.kind is types.Duration and right.type.kind in {types.Uint, types.Float}:
|
756
|
+
type = left.type
|
757
|
+
else:
|
758
|
+
raise TypeError(f"invalid types for '{Binary.Op.DIV}': '{left.type}' and '{right.type}'")
|
759
|
+
return Binary(
|
760
|
+
Binary.Op.DIV,
|
761
|
+
left,
|
762
|
+
right,
|
763
|
+
type,
|
764
|
+
)
|
@@ -22,10 +22,12 @@ from __future__ import annotations
|
|
22
22
|
__all__ = [
|
23
23
|
"Expr",
|
24
24
|
"Var",
|
25
|
+
"Stretch",
|
25
26
|
"Value",
|
26
27
|
"Cast",
|
27
28
|
"Unary",
|
28
29
|
"Binary",
|
30
|
+
"Index",
|
29
31
|
]
|
30
32
|
|
31
33
|
import abc
|
@@ -55,9 +57,10 @@ class Expr(abc.ABC):
|
|
55
57
|
All subclasses are responsible for setting their ``type`` attribute in their ``__init__``, and
|
56
58
|
should not call the parent initializer."""
|
57
59
|
|
58
|
-
__slots__ = ("type",)
|
60
|
+
__slots__ = ("type", "const")
|
59
61
|
|
60
62
|
type: types.Type
|
63
|
+
const: bool
|
61
64
|
|
62
65
|
# Sentinel to prevent instantiation of the base class.
|
63
66
|
@abc.abstractmethod
|
@@ -89,6 +92,7 @@ class Cast(Expr):
|
|
89
92
|
|
90
93
|
def __init__(self, operand: Expr, type: types.Type, implicit: bool = False):
|
91
94
|
self.type = type
|
95
|
+
self.const = operand.const
|
92
96
|
self.operand = operand
|
93
97
|
self.implicit = implicit
|
94
98
|
|
@@ -99,6 +103,7 @@ class Cast(Expr):
|
|
99
103
|
return (
|
100
104
|
isinstance(other, Cast)
|
101
105
|
and self.type == other.type
|
106
|
+
and self.const == other.const
|
102
107
|
and self.operand == other.operand
|
103
108
|
and self.implicit == other.implicit
|
104
109
|
)
|
@@ -141,6 +146,7 @@ class Var(Expr):
|
|
141
146
|
name: str | None = None,
|
142
147
|
):
|
143
148
|
super().__setattr__("type", type)
|
149
|
+
super().__setattr__("const", False)
|
144
150
|
super().__setattr__("var", var)
|
145
151
|
super().__setattr__("name", name)
|
146
152
|
|
@@ -151,8 +157,9 @@ class Var(Expr):
|
|
151
157
|
|
152
158
|
@property
|
153
159
|
def standalone(self) -> bool:
|
154
|
-
"""Whether this :class:`Var` is a standalone variable that owns its storage
|
155
|
-
false, this is a wrapper :class:`Var` around a
|
160
|
+
"""Whether this :class:`Var` is a standalone variable that owns its storage
|
161
|
+
location, if applicable. If false, this is a wrapper :class:`Var` around a
|
162
|
+
pre-existing circuit object."""
|
156
163
|
return isinstance(self.var, uuid.UUID)
|
157
164
|
|
158
165
|
def accept(self, visitor, /):
|
@@ -185,6 +192,76 @@ class Var(Expr):
|
|
185
192
|
def __setstate__(self, state):
|
186
193
|
var, type, name = state
|
187
194
|
super().__setattr__("type", type)
|
195
|
+
super().__setattr__("const", False)
|
196
|
+
super().__setattr__("var", var)
|
197
|
+
super().__setattr__("name", name)
|
198
|
+
|
199
|
+
def __copy__(self):
|
200
|
+
# I am immutable...
|
201
|
+
return self
|
202
|
+
|
203
|
+
def __deepcopy__(self, memo):
|
204
|
+
# ... as are all my constituent parts.
|
205
|
+
return self
|
206
|
+
|
207
|
+
|
208
|
+
@typing.final
|
209
|
+
class Stretch(Expr):
|
210
|
+
"""A stretch variable.
|
211
|
+
|
212
|
+
In general, construction of stretch variables for use in programs should use :meth:`Stretch.new`
|
213
|
+
or :meth:`.QuantumCircuit.add_stretch`.
|
214
|
+
"""
|
215
|
+
|
216
|
+
__slots__ = (
|
217
|
+
"var",
|
218
|
+
"name",
|
219
|
+
)
|
220
|
+
|
221
|
+
var: uuid.UUID
|
222
|
+
"""A :class:`~uuid.UUID` to uniquely identify this stretch."""
|
223
|
+
name: str
|
224
|
+
"""The name of the stretch variable."""
|
225
|
+
|
226
|
+
def __init__(
|
227
|
+
self,
|
228
|
+
var: uuid.UUID,
|
229
|
+
name: str,
|
230
|
+
):
|
231
|
+
super().__setattr__("type", types.Duration())
|
232
|
+
super().__setattr__("const", True)
|
233
|
+
super().__setattr__("var", var)
|
234
|
+
super().__setattr__("name", name)
|
235
|
+
|
236
|
+
@classmethod
|
237
|
+
def new(cls, name: str) -> typing.Self:
|
238
|
+
"""Generate a new named stretch variable."""
|
239
|
+
return cls(uuid.uuid4(), name)
|
240
|
+
|
241
|
+
def accept(self, visitor, /):
|
242
|
+
return visitor.visit_stretch(self)
|
243
|
+
|
244
|
+
def __setattr__(self, key, value):
|
245
|
+
if hasattr(self, key):
|
246
|
+
raise AttributeError(f"'Stretch' object attribute '{key}' is read-only")
|
247
|
+
raise AttributeError(f"'Stretch' object has no attribute '{key}'")
|
248
|
+
|
249
|
+
def __hash__(self):
|
250
|
+
return hash((self.var, self.name))
|
251
|
+
|
252
|
+
def __eq__(self, other):
|
253
|
+
return isinstance(other, Stretch) and self.var == other.var and self.name == other.name
|
254
|
+
|
255
|
+
def __repr__(self):
|
256
|
+
return f"Stretch({self.var}, {self.name})"
|
257
|
+
|
258
|
+
def __getstate__(self):
|
259
|
+
return (self.var, self.name)
|
260
|
+
|
261
|
+
def __setstate__(self, state):
|
262
|
+
var, name = state
|
263
|
+
super().__setattr__("type", types.Duration())
|
264
|
+
super().__setattr__("const", True)
|
188
265
|
super().__setattr__("var", var)
|
189
266
|
super().__setattr__("name", name)
|
190
267
|
|
@@ -206,6 +283,7 @@ class Value(Expr):
|
|
206
283
|
def __init__(self, value: typing.Any, type: types.Type):
|
207
284
|
self.type = type
|
208
285
|
self.value = value
|
286
|
+
self.const = True
|
209
287
|
|
210
288
|
def accept(self, visitor, /):
|
211
289
|
return visitor.visit_value(self)
|
@@ -257,6 +335,7 @@ class Unary(Expr):
|
|
257
335
|
self.op = op
|
258
336
|
self.operand = operand
|
259
337
|
self.type = type
|
338
|
+
self.const = operand.const
|
260
339
|
|
261
340
|
def accept(self, visitor, /):
|
262
341
|
return visitor.visit_unary(self)
|
@@ -265,6 +344,7 @@ class Unary(Expr):
|
|
265
344
|
return (
|
266
345
|
isinstance(other, Unary)
|
267
346
|
and self.type == other.type
|
347
|
+
and self.const == other.const
|
268
348
|
and self.op is other.op
|
269
349
|
and self.operand == other.operand
|
270
350
|
)
|
@@ -305,6 +385,15 @@ class Binary(Expr):
|
|
305
385
|
container types (e.g. unsigned integers) as the left operand, and any integer type as the
|
306
386
|
right-hand operand. In all cases, the output bit width is the same as the input, and zeros
|
307
387
|
fill in the "exposed" spaces.
|
388
|
+
|
389
|
+
The binary arithmetic operators :data:`ADD`, :data:`SUB:, :data:`MUL`, and :data:`DIV`
|
390
|
+
can be applied to two floats or two unsigned integers, which should be made to be of
|
391
|
+
the same width during construction via a cast.
|
392
|
+
The :data:`ADD`, :data:`SUB`, and :data:`DIV` operators can be applied on two durations
|
393
|
+
yielding another duration, or a float in the case of :data:`DIV`. The :data:`MUL` operator
|
394
|
+
can also be applied to a duration and a numeric type, yielding another duration. Finally,
|
395
|
+
the :data:`DIV` operator can be used to divide a duration by a numeric type, yielding a
|
396
|
+
duration.
|
308
397
|
"""
|
309
398
|
|
310
399
|
# If adding opcodes, remember to add helper constructor functions in `constructors.py`
|
@@ -336,6 +425,14 @@ class Binary(Expr):
|
|
336
425
|
"""Zero-padding bitshift to the left. ``lhs << rhs``."""
|
337
426
|
SHIFT_RIGHT = 13
|
338
427
|
"""Zero-padding bitshift to the right. ``lhs >> rhs``."""
|
428
|
+
ADD = 14
|
429
|
+
"""Addition. ``lhs + rhs``."""
|
430
|
+
SUB = 15
|
431
|
+
"""Subtraction. ``lhs - rhs``."""
|
432
|
+
MUL = 16
|
433
|
+
"""Multiplication. ``lhs * rhs``."""
|
434
|
+
DIV = 17
|
435
|
+
"""Division. ``lhs / rhs``."""
|
339
436
|
|
340
437
|
def __str__(self):
|
341
438
|
return f"Binary.{super().__str__()}"
|
@@ -348,6 +445,7 @@ class Binary(Expr):
|
|
348
445
|
self.left = left
|
349
446
|
self.right = right
|
350
447
|
self.type = type
|
448
|
+
self.const = left.const and right.const
|
351
449
|
|
352
450
|
def accept(self, visitor, /):
|
353
451
|
return visitor.visit_binary(self)
|
@@ -356,6 +454,7 @@ class Binary(Expr):
|
|
356
454
|
return (
|
357
455
|
isinstance(other, Binary)
|
358
456
|
and self.type == other.type
|
457
|
+
and self.const == other.const
|
359
458
|
and self.op is other.op
|
360
459
|
and self.left == other.left
|
361
460
|
and self.right == other.right
|
@@ -381,6 +480,7 @@ class Index(Expr):
|
|
381
480
|
self.target = target
|
382
481
|
self.index = index
|
383
482
|
self.type = type
|
483
|
+
self.const = target.const and index.const
|
384
484
|
|
385
485
|
def accept(self, visitor, /):
|
386
486
|
return visitor.visit_index(self)
|
@@ -389,6 +489,7 @@ class Index(Expr):
|
|
389
489
|
return (
|
390
490
|
isinstance(other, Index)
|
391
491
|
and self.type == other.type
|
492
|
+
and self.const == other.const
|
392
493
|
and self.target == other.target
|
393
494
|
and self.index == other.index
|
394
495
|
)
|
@@ -17,7 +17,9 @@ from __future__ import annotations
|
|
17
17
|
__all__ = [
|
18
18
|
"ExprVisitor",
|
19
19
|
"iter_vars",
|
20
|
+
"iter_identifiers",
|
20
21
|
"structurally_equivalent",
|
22
|
+
"is_lvalue",
|
21
23
|
]
|
22
24
|
|
23
25
|
import typing
|
@@ -43,6 +45,9 @@ class ExprVisitor(typing.Generic[_T_co]):
|
|
43
45
|
def visit_var(self, node: expr.Var, /) -> _T_co: # pragma: no cover
|
44
46
|
return self.visit_generic(node)
|
45
47
|
|
48
|
+
def visit_stretch(self, node: expr.Stretch, /) -> _T_co: # pragma: no cover
|
49
|
+
return self.visit_generic(node)
|
50
|
+
|
46
51
|
def visit_value(self, node: expr.Value, /) -> _T_co: # pragma: no cover
|
47
52
|
return self.visit_generic(node)
|
48
53
|
|
@@ -65,6 +70,36 @@ class _VarWalkerImpl(ExprVisitor[typing.Iterable[expr.Var]]):
|
|
65
70
|
def visit_var(self, node, /):
|
66
71
|
yield node
|
67
72
|
|
73
|
+
def visit_stretch(self, node, /):
|
74
|
+
yield from ()
|
75
|
+
|
76
|
+
def visit_value(self, node, /):
|
77
|
+
yield from ()
|
78
|
+
|
79
|
+
def visit_unary(self, node, /):
|
80
|
+
yield from node.operand.accept(self)
|
81
|
+
|
82
|
+
def visit_binary(self, node, /):
|
83
|
+
yield from node.left.accept(self)
|
84
|
+
yield from node.right.accept(self)
|
85
|
+
|
86
|
+
def visit_cast(self, node, /):
|
87
|
+
yield from node.operand.accept(self)
|
88
|
+
|
89
|
+
def visit_index(self, node, /):
|
90
|
+
yield from node.target.accept(self)
|
91
|
+
yield from node.index.accept(self)
|
92
|
+
|
93
|
+
|
94
|
+
class _IdentWalkerImpl(ExprVisitor[typing.Iterable[typing.Union[expr.Var, expr.Stretch]]]):
|
95
|
+
__slots__ = ()
|
96
|
+
|
97
|
+
def visit_var(self, node, /):
|
98
|
+
yield node
|
99
|
+
|
100
|
+
def visit_stretch(self, node, /):
|
101
|
+
yield node
|
102
|
+
|
68
103
|
def visit_value(self, node, /):
|
69
104
|
yield from ()
|
70
105
|
|
@@ -84,6 +119,7 @@ class _VarWalkerImpl(ExprVisitor[typing.Iterable[expr.Var]]):
|
|
84
119
|
|
85
120
|
|
86
121
|
_VAR_WALKER = _VarWalkerImpl()
|
122
|
+
_IDENT_WALKER = _IdentWalkerImpl()
|
87
123
|
|
88
124
|
|
89
125
|
def iter_vars(node: expr.Expr) -> typing.Iterator[expr.Var]:
|
@@ -102,10 +138,39 @@ def iter_vars(node: expr.Expr) -> typing.Iterator[expr.Var]:
|
|
102
138
|
for node in expr.iter_vars(expr.bit_and(expr.bit_not(cr1), cr2)):
|
103
139
|
if isinstance(node.var, ClassicalRegister):
|
104
140
|
print(node.var.name)
|
141
|
+
|
142
|
+
.. seealso::
|
143
|
+
:func:`iter_identifiers`
|
144
|
+
Get an iterator over all identifier nodes in the expression, including
|
145
|
+
both :class:`~.expr.Var` and :class:`~.expr.Stretch` nodes.
|
105
146
|
"""
|
106
147
|
yield from node.accept(_VAR_WALKER)
|
107
148
|
|
108
149
|
|
150
|
+
def iter_identifiers(node: expr.Expr) -> typing.Iterator[typing.Union[expr.Var, expr.Stretch]]:
|
151
|
+
"""Get an iterator over the :class:`~.expr.Var` and :class:`~.expr.Stretch`
|
152
|
+
nodes referenced at any level in the given :class:`~.expr.Expr`.
|
153
|
+
|
154
|
+
Examples:
|
155
|
+
Print out the name of each :class:`.ClassicalRegister` encountered::
|
156
|
+
|
157
|
+
from qiskit.circuit import ClassicalRegister
|
158
|
+
from qiskit.circuit.classical import expr
|
159
|
+
|
160
|
+
cr1 = ClassicalRegister(3, "a")
|
161
|
+
cr2 = ClassicalRegister(3, "b")
|
162
|
+
|
163
|
+
for node in expr.iter_vars(expr.bit_and(expr.bit_not(cr1), cr2)):
|
164
|
+
if isinstance(node.var, ClassicalRegister):
|
165
|
+
print(node.var.name)
|
166
|
+
|
167
|
+
.. seealso::
|
168
|
+
:func:`iter_vars`
|
169
|
+
Get an iterator over just the :class:`~.expr.Var` nodes in the expression.
|
170
|
+
"""
|
171
|
+
yield from node.accept(_IDENT_WALKER)
|
172
|
+
|
173
|
+
|
109
174
|
class _StructuralEquivalenceImpl(ExprVisitor[bool]):
|
110
175
|
# The strategy here is to continue to do regular double dispatch through the visitor format,
|
111
176
|
# since we simply exit out with a ``False`` as soon as the structure of the two trees isn't the
|
@@ -134,6 +199,11 @@ class _StructuralEquivalenceImpl(ExprVisitor[bool]):
|
|
134
199
|
other_var = self.other.var
|
135
200
|
return self_var == other_var
|
136
201
|
|
202
|
+
def visit_stretch(self, node, /):
|
203
|
+
if self.other.__class__ is not node.__class__:
|
204
|
+
return False
|
205
|
+
return node.var == self.other.var
|
206
|
+
|
137
207
|
def visit_value(self, node, /):
|
138
208
|
return (
|
139
209
|
node.__class__ is self.other.__class__
|
@@ -240,6 +310,9 @@ class _IsLValueImpl(ExprVisitor[bool]):
|
|
240
310
|
def visit_var(self, node, /):
|
241
311
|
return True
|
242
312
|
|
313
|
+
def visit_stretch(self, node, /):
|
314
|
+
return False
|
315
|
+
|
243
316
|
def visit_value(self, node, /):
|
244
317
|
return False
|
245
318
|
|
@@ -268,6 +341,8 @@ def is_lvalue(node: expr.Expr, /) -> bool:
|
|
268
341
|
the scope that attempts to write to it. This would be an access property of the containing
|
269
342
|
program, however, and not an inherent property of the expression system.
|
270
343
|
|
344
|
+
A constant expression is never an lvalue.
|
345
|
+
|
271
346
|
Examples:
|
272
347
|
Literal values are never l-values; there's no memory location associated with (for example)
|
273
348
|
the constant ``1``::
|