qiskit 1.1.2__cp38-abi3-macosx_10_9_universal2.whl → 1.2.0__cp38-abi3-macosx_10_9_universal2.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.
Files changed (343) hide show
  1. qiskit/VERSION.txt +1 -1
  2. qiskit/__init__.py +27 -24
  3. qiskit/_accelerate.abi3.so +0 -0
  4. qiskit/_numpy_compat.py +1 -1
  5. qiskit/assembler/assemble_circuits.py +107 -64
  6. qiskit/assembler/assemble_schedules.py +5 -12
  7. qiskit/assembler/disassemble.py +10 -1
  8. qiskit/circuit/__init__.py +6 -3
  9. qiskit/circuit/_classical_resource_map.py +5 -5
  10. qiskit/circuit/_utils.py +0 -13
  11. qiskit/circuit/add_control.py +1 -1
  12. qiskit/circuit/annotated_operation.py +23 -1
  13. qiskit/circuit/classical/expr/expr.py +4 -4
  14. qiskit/circuit/classical/expr/visitors.py +1 -1
  15. qiskit/circuit/classical/types/__init__.py +1 -1
  16. qiskit/circuit/classical/types/types.py +2 -2
  17. qiskit/circuit/classicalfunction/boolean_expression.py +1 -1
  18. qiskit/circuit/classicalfunction/classical_function_visitor.py +5 -5
  19. qiskit/circuit/classicalfunction/utils.py +1 -1
  20. qiskit/circuit/classicalregister.py +1 -1
  21. qiskit/circuit/commutation_checker.py +83 -35
  22. qiskit/circuit/controlflow/_builder_utils.py +1 -1
  23. qiskit/circuit/controlflow/builder.py +10 -6
  24. qiskit/circuit/controlflow/if_else.py +2 -2
  25. qiskit/circuit/controlflow/switch_case.py +1 -1
  26. qiskit/circuit/delay.py +1 -1
  27. qiskit/circuit/duration.py +2 -2
  28. qiskit/circuit/equivalence.py +5 -7
  29. qiskit/circuit/gate.py +11 -8
  30. qiskit/circuit/instruction.py +31 -13
  31. qiskit/circuit/instructionset.py +2 -5
  32. qiskit/circuit/library/__init__.py +2 -1
  33. qiskit/circuit/library/arithmetic/linear_amplitude_function.py +1 -1
  34. qiskit/circuit/library/arithmetic/linear_pauli_rotations.py +1 -1
  35. qiskit/circuit/library/arithmetic/piecewise_chebyshev.py +1 -1
  36. qiskit/circuit/library/arithmetic/piecewise_linear_pauli_rotations.py +1 -1
  37. qiskit/circuit/library/arithmetic/piecewise_polynomial_pauli_rotations.py +3 -3
  38. qiskit/circuit/library/arithmetic/polynomial_pauli_rotations.py +1 -1
  39. qiskit/circuit/library/basis_change/__init__.py +1 -1
  40. qiskit/circuit/library/basis_change/qft.py +40 -6
  41. qiskit/circuit/library/blueprintcircuit.py +3 -5
  42. qiskit/circuit/library/data_preparation/__init__.py +9 -2
  43. qiskit/circuit/library/data_preparation/initializer.py +8 -0
  44. qiskit/circuit/library/data_preparation/state_preparation.py +98 -178
  45. qiskit/circuit/library/generalized_gates/isometry.py +8 -8
  46. qiskit/circuit/library/generalized_gates/linear_function.py +3 -2
  47. qiskit/circuit/library/generalized_gates/mcg_up_to_diagonal.py +4 -4
  48. qiskit/circuit/library/generalized_gates/permutation.py +8 -9
  49. qiskit/circuit/library/generalized_gates/uc.py +3 -3
  50. qiskit/circuit/library/generalized_gates/uc_pauli_rot.py +2 -2
  51. qiskit/circuit/library/generalized_gates/unitary.py +13 -11
  52. qiskit/circuit/library/graph_state.py +1 -1
  53. qiskit/circuit/library/hamiltonian_gate.py +1 -2
  54. qiskit/circuit/library/hidden_linear_function.py +1 -1
  55. qiskit/circuit/library/n_local/evolved_operator_ansatz.py +3 -2
  56. qiskit/circuit/library/n_local/n_local.py +4 -5
  57. qiskit/circuit/library/n_local/pauli_two_design.py +1 -1
  58. qiskit/circuit/library/n_local/qaoa_ansatz.py +6 -8
  59. qiskit/circuit/library/n_local/two_local.py +1 -1
  60. qiskit/circuit/library/overlap.py +11 -5
  61. qiskit/circuit/library/pauli_evolution.py +7 -3
  62. qiskit/circuit/library/standard_gates/dcx.py +3 -0
  63. qiskit/circuit/library/standard_gates/ecr.py +3 -0
  64. qiskit/circuit/library/standard_gates/global_phase.py +3 -0
  65. qiskit/circuit/library/standard_gates/h.py +13 -5
  66. qiskit/circuit/library/standard_gates/i.py +3 -0
  67. qiskit/circuit/library/standard_gates/iswap.py +3 -0
  68. qiskit/circuit/library/standard_gates/multi_control_rotation_gates.py +19 -10
  69. qiskit/circuit/library/standard_gates/p.py +14 -9
  70. qiskit/circuit/library/standard_gates/r.py +3 -0
  71. qiskit/circuit/library/standard_gates/rx.py +21 -6
  72. qiskit/circuit/library/standard_gates/rxx.py +40 -1
  73. qiskit/circuit/library/standard_gates/ry.py +21 -6
  74. qiskit/circuit/library/standard_gates/ryy.py +40 -1
  75. qiskit/circuit/library/standard_gates/rz.py +22 -6
  76. qiskit/circuit/library/standard_gates/rzx.py +40 -1
  77. qiskit/circuit/library/standard_gates/rzz.py +41 -2
  78. qiskit/circuit/library/standard_gates/s.py +77 -0
  79. qiskit/circuit/library/standard_gates/swap.py +12 -5
  80. qiskit/circuit/library/standard_gates/sx.py +14 -5
  81. qiskit/circuit/library/standard_gates/t.py +5 -0
  82. qiskit/circuit/library/standard_gates/u.py +22 -7
  83. qiskit/circuit/library/standard_gates/u1.py +8 -3
  84. qiskit/circuit/library/standard_gates/u2.py +3 -0
  85. qiskit/circuit/library/standard_gates/u3.py +22 -7
  86. qiskit/circuit/library/standard_gates/x.py +156 -92
  87. qiskit/circuit/library/standard_gates/xx_minus_yy.py +40 -1
  88. qiskit/circuit/library/standard_gates/xx_plus_yy.py +52 -11
  89. qiskit/circuit/library/standard_gates/y.py +6 -1
  90. qiskit/circuit/library/standard_gates/z.py +8 -1
  91. qiskit/circuit/operation.py +1 -1
  92. qiskit/circuit/parameter.py +9 -10
  93. qiskit/circuit/parameterexpression.py +16 -13
  94. qiskit/circuit/parametertable.py +1 -190
  95. qiskit/circuit/parametervector.py +1 -1
  96. qiskit/circuit/quantumcircuit.py +395 -387
  97. qiskit/circuit/quantumcircuitdata.py +3 -5
  98. qiskit/circuit/quantumregister.py +1 -1
  99. qiskit/circuit/random/__init__.py +1 -1
  100. qiskit/circuit/random/utils.py +175 -26
  101. qiskit/circuit/register.py +5 -7
  102. qiskit/circuit/singleton.py +3 -3
  103. qiskit/circuit/tools/pi_check.py +4 -4
  104. qiskit/compiler/assembler.py +95 -24
  105. qiskit/compiler/scheduler.py +2 -2
  106. qiskit/compiler/transpiler.py +42 -128
  107. qiskit/converters/circuit_to_dag.py +4 -6
  108. qiskit/converters/circuit_to_gate.py +4 -8
  109. qiskit/converters/circuit_to_instruction.py +5 -17
  110. qiskit/converters/dag_to_circuit.py +2 -6
  111. qiskit/dagcircuit/collect_blocks.py +2 -2
  112. qiskit/dagcircuit/dagcircuit.py +190 -187
  113. qiskit/dagcircuit/dagdependency.py +4 -4
  114. qiskit/dagcircuit/dagdependency_v2.py +4 -4
  115. qiskit/dagcircuit/dagdepnode.py +1 -1
  116. qiskit/dagcircuit/dagnode.py +66 -157
  117. qiskit/passmanager/flow_controllers.py +1 -1
  118. qiskit/passmanager/passmanager.py +3 -3
  119. qiskit/primitives/__init__.py +1 -5
  120. qiskit/primitives/backend_estimator.py +25 -15
  121. qiskit/primitives/backend_estimator_v2.py +31 -7
  122. qiskit/primitives/backend_sampler.py +21 -12
  123. qiskit/primitives/backend_sampler_v2.py +12 -3
  124. qiskit/primitives/base/base_estimator.py +31 -4
  125. qiskit/primitives/base/base_primitive.py +2 -2
  126. qiskit/primitives/base/base_result.py +2 -2
  127. qiskit/primitives/base/base_sampler.py +26 -2
  128. qiskit/primitives/base/estimator_result.py +2 -2
  129. qiskit/primitives/base/sampler_result.py +2 -2
  130. qiskit/primitives/containers/__init__.py +0 -1
  131. qiskit/primitives/containers/bindings_array.py +2 -2
  132. qiskit/primitives/containers/bit_array.py +108 -10
  133. qiskit/primitives/containers/shape.py +3 -3
  134. qiskit/primitives/estimator.py +9 -2
  135. qiskit/primitives/primitive_job.py +1 -1
  136. qiskit/primitives/sampler.py +10 -3
  137. qiskit/primitives/statevector_estimator.py +5 -3
  138. qiskit/primitives/statevector_sampler.py +11 -5
  139. qiskit/primitives/utils.py +16 -0
  140. qiskit/providers/backend.py +15 -6
  141. qiskit/providers/backend_compat.py +7 -4
  142. qiskit/providers/basic_provider/basic_provider_tools.py +1 -1
  143. qiskit/providers/basic_provider/basic_simulator.py +33 -25
  144. qiskit/providers/fake_provider/fake_backend.py +10 -3
  145. qiskit/providers/fake_provider/fake_openpulse_2q.py +157 -149
  146. qiskit/providers/fake_provider/fake_openpulse_3q.py +228 -220
  147. qiskit/providers/fake_provider/fake_pulse_backend.py +2 -1
  148. qiskit/providers/fake_provider/fake_qasm_backend.py +7 -2
  149. qiskit/providers/fake_provider/generic_backend_v2.py +514 -68
  150. qiskit/providers/models/__init__.py +48 -11
  151. qiskit/providers/models/backendconfiguration.py +50 -4
  152. qiskit/providers/models/backendproperties.py +13 -2
  153. qiskit/providers/models/pulsedefaults.py +10 -11
  154. qiskit/providers/options.py +13 -13
  155. qiskit/providers/providerutils.py +3 -1
  156. qiskit/pulse/configuration.py +8 -12
  157. qiskit/pulse/instruction_schedule_map.py +3 -5
  158. qiskit/pulse/instructions/acquire.py +7 -8
  159. qiskit/pulse/instructions/instruction.py +2 -3
  160. qiskit/pulse/library/samplers/decorators.py +5 -9
  161. qiskit/pulse/library/symbolic_pulses.py +4 -7
  162. qiskit/pulse/library/waveform.py +2 -5
  163. qiskit/pulse/macros.py +11 -6
  164. qiskit/pulse/parser.py +8 -10
  165. qiskit/pulse/schedule.py +9 -17
  166. qiskit/pulse/transforms/alignments.py +1 -3
  167. qiskit/pulse/utils.py +1 -2
  168. qiskit/qasm/libs/stdgates.inc +35 -28
  169. qiskit/qasm2/__init__.py +7 -7
  170. qiskit/qasm2/export.py +5 -9
  171. qiskit/qasm2/parse.py +1 -1
  172. qiskit/qasm3/ast.py +9 -25
  173. qiskit/qasm3/exporter.py +582 -479
  174. qiskit/qasm3/printer.py +7 -16
  175. qiskit/qobj/common.py +10 -0
  176. qiskit/qobj/converters/lo_config.py +9 -0
  177. qiskit/qobj/converters/pulse_instruction.py +13 -6
  178. qiskit/qobj/pulse_qobj.py +69 -15
  179. qiskit/qobj/qasm_qobj.py +72 -20
  180. qiskit/qobj/utils.py +9 -0
  181. qiskit/qpy/__init__.py +1 -1
  182. qiskit/qpy/binary_io/circuits.py +8 -5
  183. qiskit/qpy/binary_io/schedules.py +1 -1
  184. qiskit/qpy/binary_io/value.py +3 -3
  185. qiskit/qpy/interface.py +3 -2
  186. qiskit/qpy/type_keys.py +2 -2
  187. qiskit/quantum_info/operators/channel/quantum_channel.py +3 -6
  188. qiskit/quantum_info/operators/channel/superop.py +2 -2
  189. qiskit/quantum_info/operators/channel/transformations.py +1 -1
  190. qiskit/quantum_info/operators/dihedral/dihedral.py +3 -4
  191. qiskit/quantum_info/operators/dihedral/dihedral_circuits.py +1 -3
  192. qiskit/quantum_info/operators/dihedral/random.py +6 -3
  193. qiskit/quantum_info/operators/measures.py +2 -2
  194. qiskit/quantum_info/operators/op_shape.py +12 -20
  195. qiskit/quantum_info/operators/operator.py +14 -21
  196. qiskit/quantum_info/operators/predicates.py +1 -0
  197. qiskit/quantum_info/operators/symplectic/base_pauli.py +7 -11
  198. qiskit/quantum_info/operators/symplectic/clifford.py +1 -1
  199. qiskit/quantum_info/operators/symplectic/pauli.py +3 -3
  200. qiskit/quantum_info/operators/symplectic/pauli_list.py +9 -10
  201. qiskit/quantum_info/operators/symplectic/random.py +1 -1
  202. qiskit/quantum_info/operators/symplectic/sparse_pauli_op.py +15 -17
  203. qiskit/quantum_info/quaternion.py +1 -1
  204. qiskit/quantum_info/states/densitymatrix.py +5 -8
  205. qiskit/quantum_info/states/stabilizerstate.py +128 -37
  206. qiskit/quantum_info/states/statevector.py +4 -8
  207. qiskit/result/counts.py +2 -2
  208. qiskit/result/mitigation/correlated_readout_mitigator.py +2 -2
  209. qiskit/result/mitigation/local_readout_mitigator.py +2 -2
  210. qiskit/result/mitigation/utils.py +1 -3
  211. qiskit/result/models.py +17 -16
  212. qiskit/result/result.py +15 -20
  213. qiskit/scheduler/lowering.py +2 -2
  214. qiskit/synthesis/__init__.py +2 -1
  215. qiskit/synthesis/clifford/__init__.py +1 -1
  216. qiskit/synthesis/clifford/clifford_decompose_ag.py +2 -2
  217. qiskit/synthesis/clifford/clifford_decompose_bm.py +10 -240
  218. qiskit/synthesis/clifford/clifford_decompose_greedy.py +9 -303
  219. qiskit/synthesis/clifford/clifford_decompose_layers.py +25 -23
  220. qiskit/synthesis/cnotdihedral/cnotdihedral_decompose_full.py +1 -1
  221. qiskit/synthesis/cnotdihedral/cnotdihedral_decompose_general.py +1 -1
  222. qiskit/synthesis/discrete_basis/generate_basis_approximations.py +1 -1
  223. qiskit/synthesis/discrete_basis/solovay_kitaev.py +2 -2
  224. qiskit/synthesis/evolution/evolution_synthesis.py +4 -2
  225. qiskit/synthesis/evolution/lie_trotter.py +46 -19
  226. qiskit/synthesis/evolution/product_formula.py +111 -55
  227. qiskit/synthesis/evolution/qdrift.py +40 -10
  228. qiskit/synthesis/evolution/suzuki_trotter.py +43 -33
  229. qiskit/synthesis/linear/__init__.py +1 -0
  230. qiskit/synthesis/linear/cnot_synth.py +22 -96
  231. qiskit/synthesis/linear/linear_depth_lnn.py +8 -8
  232. qiskit/synthesis/linear/linear_matrix_utils.py +13 -161
  233. qiskit/synthesis/linear_phase/cnot_phase_synth.py +1 -1
  234. qiskit/synthesis/linear_phase/cx_cz_depth_lnn.py +3 -3
  235. qiskit/synthesis/linear_phase/cz_depth_lnn.py +1 -1
  236. qiskit/synthesis/one_qubit/one_qubit_decompose.py +29 -29
  237. qiskit/synthesis/permutation/permutation_full.py +5 -29
  238. qiskit/synthesis/permutation/permutation_lnn.py +2 -24
  239. qiskit/synthesis/permutation/permutation_utils.py +2 -59
  240. qiskit/synthesis/qft/__init__.py +1 -0
  241. qiskit/synthesis/qft/qft_decompose_full.py +79 -0
  242. qiskit/synthesis/qft/qft_decompose_lnn.py +17 -9
  243. qiskit/synthesis/stabilizer/stabilizer_circuit.py +6 -6
  244. qiskit/synthesis/stabilizer/stabilizer_decompose.py +2 -2
  245. qiskit/synthesis/two_qubit/local_invariance.py +8 -38
  246. qiskit/synthesis/two_qubit/two_qubit_decompose.py +48 -129
  247. qiskit/synthesis/unitary/aqc/cnot_structures.py +1 -1
  248. qiskit/synthesis/unitary/qsd.py +5 -3
  249. qiskit/transpiler/__init__.py +1 -0
  250. qiskit/transpiler/basepasses.py +1 -1
  251. qiskit/transpiler/coupling.py +3 -3
  252. qiskit/transpiler/instruction_durations.py +1 -2
  253. qiskit/transpiler/layout.py +3 -3
  254. qiskit/transpiler/passes/__init__.py +2 -0
  255. qiskit/transpiler/passes/basis/basis_translator.py +84 -64
  256. qiskit/transpiler/passes/basis/translate_parameterized.py +3 -5
  257. qiskit/transpiler/passes/basis/unroll_3q_or_more.py +1 -1
  258. qiskit/transpiler/passes/basis/unroll_custom_definitions.py +10 -10
  259. qiskit/transpiler/passes/calibration/rx_builder.py +3 -3
  260. qiskit/transpiler/passes/calibration/rzx_builder.py +3 -3
  261. qiskit/transpiler/passes/layout/apply_layout.py +13 -3
  262. qiskit/transpiler/passes/layout/sabre_layout.py +10 -8
  263. qiskit/transpiler/passes/layout/sabre_pre_layout.py +4 -1
  264. qiskit/transpiler/passes/layout/set_layout.py +2 -2
  265. qiskit/transpiler/passes/layout/vf2_layout.py +1 -1
  266. qiskit/transpiler/passes/layout/vf2_utils.py +3 -3
  267. qiskit/transpiler/passes/optimization/__init__.py +1 -0
  268. qiskit/transpiler/passes/optimization/collect_multiqubit_blocks.py +2 -2
  269. qiskit/transpiler/passes/optimization/commutation_analysis.py +7 -10
  270. qiskit/transpiler/passes/optimization/commutative_cancellation.py +35 -19
  271. qiskit/transpiler/passes/optimization/consolidate_blocks.py +17 -8
  272. qiskit/transpiler/passes/optimization/inverse_cancellation.py +6 -6
  273. qiskit/transpiler/passes/optimization/optimize_1q_decomposition.py +64 -41
  274. qiskit/transpiler/passes/optimization/optimize_1q_gates.py +1 -1
  275. qiskit/transpiler/passes/optimization/split_2q_unitaries.py +83 -0
  276. qiskit/transpiler/passes/optimization/template_matching/backward_match.py +1 -1
  277. qiskit/transpiler/passes/optimization/template_matching/forward_match.py +2 -2
  278. qiskit/transpiler/passes/optimization/template_matching/template_substitution.py +1 -1
  279. qiskit/transpiler/passes/routing/commuting_2q_gate_routing/commuting_2q_gate_router.py +3 -2
  280. qiskit/transpiler/passes/routing/commuting_2q_gate_routing/swap_strategy.py +1 -1
  281. qiskit/transpiler/passes/routing/layout_transformation.py +2 -1
  282. qiskit/transpiler/passes/routing/sabre_swap.py +35 -26
  283. qiskit/transpiler/passes/routing/star_prerouting.py +80 -105
  284. qiskit/transpiler/passes/routing/stochastic_swap.py +1 -3
  285. qiskit/transpiler/passes/scheduling/alap.py +1 -2
  286. qiskit/transpiler/passes/scheduling/alignments/__init__.py +2 -2
  287. qiskit/transpiler/passes/scheduling/alignments/check_durations.py +1 -1
  288. qiskit/transpiler/passes/scheduling/alignments/pulse_gate_validation.py +2 -2
  289. qiskit/transpiler/passes/scheduling/alignments/reschedule.py +1 -1
  290. qiskit/transpiler/passes/scheduling/asap.py +1 -2
  291. qiskit/transpiler/passes/scheduling/base_scheduler.py +5 -5
  292. qiskit/transpiler/passes/scheduling/dynamical_decoupling.py +3 -3
  293. qiskit/transpiler/passes/scheduling/padding/base_padding.py +1 -1
  294. qiskit/transpiler/passes/scheduling/padding/dynamical_decoupling.py +20 -14
  295. qiskit/transpiler/passes/scheduling/scheduling/base_scheduler.py +7 -6
  296. qiskit/transpiler/passes/scheduling/time_unit_conversion.py +4 -3
  297. qiskit/transpiler/passes/synthesis/high_level_synthesis.py +211 -36
  298. qiskit/transpiler/passes/synthesis/plugin.py +2 -2
  299. qiskit/transpiler/passes/synthesis/unitary_synthesis.py +80 -40
  300. qiskit/transpiler/passes/utils/__init__.py +0 -1
  301. qiskit/transpiler/passes/utils/check_gate_direction.py +4 -4
  302. qiskit/transpiler/passes/utils/check_map.py +3 -6
  303. qiskit/transpiler/passes/utils/convert_conditions_to_if_ops.py +3 -4
  304. qiskit/transpiler/passes/utils/error.py +2 -2
  305. qiskit/transpiler/passes/utils/fixed_point.py +3 -3
  306. qiskit/transpiler/passes/utils/gate_direction.py +1 -1
  307. qiskit/transpiler/passes/utils/gates_basis.py +1 -2
  308. qiskit/transpiler/passmanager.py +7 -6
  309. qiskit/transpiler/preset_passmanagers/__init__.py +4 -228
  310. qiskit/transpiler/preset_passmanagers/builtin_plugins.py +73 -18
  311. qiskit/transpiler/preset_passmanagers/common.py +3 -6
  312. qiskit/transpiler/preset_passmanagers/generate_preset_pass_manager.py +518 -0
  313. qiskit/transpiler/preset_passmanagers/level0.py +1 -1
  314. qiskit/transpiler/target.py +27 -8
  315. qiskit/user_config.py +29 -6
  316. qiskit/utils/classtools.py +3 -3
  317. qiskit/utils/deprecation.py +3 -2
  318. qiskit/utils/lazy_tester.py +2 -2
  319. qiskit/utils/optionals.py +8 -8
  320. qiskit/visualization/bloch.py +18 -23
  321. qiskit/visualization/circuit/_utils.py +34 -10
  322. qiskit/visualization/circuit/circuit_visualization.py +23 -16
  323. qiskit/visualization/circuit/latex.py +29 -27
  324. qiskit/visualization/circuit/matplotlib.py +4 -2
  325. qiskit/visualization/circuit/qcstyle.py +2 -2
  326. qiskit/visualization/circuit/text.py +9 -15
  327. qiskit/visualization/dag_visualization.py +2 -2
  328. qiskit/visualization/pulse_v2/core.py +1 -1
  329. qiskit/visualization/pulse_v2/events.py +1 -1
  330. qiskit/visualization/pulse_v2/generators/frame.py +3 -4
  331. qiskit/visualization/pulse_v2/generators/waveform.py +5 -9
  332. qiskit/visualization/pulse_v2/layouts.py +1 -5
  333. qiskit/visualization/pulse_v2/plotters/matplotlib.py +1 -2
  334. qiskit/visualization/state_visualization.py +5 -6
  335. qiskit/visualization/timeline/plotters/matplotlib.py +1 -2
  336. qiskit/visualization/transition_visualization.py +7 -2
  337. {qiskit-1.1.2.dist-info → qiskit-1.2.0.dist-info}/METADATA +12 -12
  338. {qiskit-1.1.2.dist-info → qiskit-1.2.0.dist-info}/RECORD +342 -340
  339. {qiskit-1.1.2.dist-info → qiskit-1.2.0.dist-info}/entry_points.txt +3 -0
  340. qiskit/transpiler/passes/utils/block_to_matrix.py +0 -47
  341. {qiskit-1.1.2.dist-info → qiskit-1.2.0.dist-info}/LICENSE.txt +0 -0
  342. {qiskit-1.1.2.dist-info → qiskit-1.2.0.dist-info}/WHEEL +0 -0
  343. {qiskit-1.1.2.dist-info → qiskit-1.2.0.dist-info}/top_level.txt +0 -0
@@ -131,9 +131,38 @@ Permutation Synthesis
131
131
  ACGSynthesisPermutation
132
132
  KMSSynthesisPermutation
133
133
  TokenSwapperSynthesisPermutation
134
+
135
+
136
+ QFT Synthesis
137
+ '''''''''''''
138
+
139
+ .. list-table:: Plugins for :class:`.QFTGate` (key = ``"qft"``)
140
+ :header-rows: 1
141
+
142
+ * - Plugin name
143
+ - Plugin class
144
+ - Targeted connectivity
145
+ * - ``"full"``
146
+ - :class:`~.QFTSynthesisFull`
147
+ - all-to-all
148
+ * - ``"line"``
149
+ - :class:`~.QFTSynthesisLine`
150
+ - linear
151
+ * - ``"default"``
152
+ - :class:`~.QFTSynthesisFull`
153
+ - all-to-all
154
+
155
+ .. autosummary::
156
+ :toctree: ../stubs/
157
+
158
+ QFTSynthesisFull
159
+ QFTSynthesisLine
134
160
  """
135
161
 
136
- from typing import Optional, Union, List, Tuple, Callable
162
+ from __future__ import annotations
163
+
164
+ import typing
165
+ from typing import Optional, Union, List, Tuple, Callable, Sequence
137
166
 
138
167
  import numpy as np
139
168
  import rustworkx as rx
@@ -142,7 +171,7 @@ from qiskit.circuit.operation import Operation
142
171
  from qiskit.converters import circuit_to_dag, dag_to_circuit
143
172
  from qiskit.transpiler.basepasses import TransformationPass
144
173
  from qiskit.circuit.quantumcircuit import QuantumCircuit
145
- from qiskit.circuit import ControlFlowOp, ControlledGate, EquivalenceLibrary
174
+ from qiskit.circuit import ControlledGate, EquivalenceLibrary, equivalence
146
175
  from qiskit.circuit.library import LinearFunction
147
176
  from qiskit.transpiler.passes.utils import control_flow
148
177
  from qiskit.transpiler.target import Target
@@ -157,6 +186,7 @@ from qiskit.circuit.annotated_operation import (
157
186
  ControlModifier,
158
187
  PowerModifier,
159
188
  )
189
+ from qiskit.circuit.library import QFTGate
160
190
  from qiskit.synthesis.clifford import (
161
191
  synth_clifford_full,
162
192
  synth_clifford_layers,
@@ -176,9 +206,16 @@ from qiskit.synthesis.permutation import (
176
206
  synth_permutation_acg,
177
207
  synth_permutation_depth_lnn_kms,
178
208
  )
209
+ from qiskit.synthesis.qft import (
210
+ synth_qft_full,
211
+ synth_qft_line,
212
+ )
179
213
 
180
214
  from .plugin import HighLevelSynthesisPluginManager, HighLevelSynthesisPlugin
181
215
 
216
+ if typing.TYPE_CHECKING:
217
+ from qiskit.dagcircuit import DAGOpNode
218
+
182
219
 
183
220
  class HLSConfig:
184
221
  """The high-level-synthesis config allows to specify a list of "methods" used by
@@ -365,6 +402,8 @@ class HighLevelSynthesis(TransformationPass):
365
402
  if not self._top_level_only and (self._target is None or self._target.num_qubits is None):
366
403
  basic_insts = {"measure", "reset", "barrier", "snapshot", "delay", "store"}
367
404
  self._device_insts = basic_insts | set(self._basis_gates)
405
+ else:
406
+ self._device_insts = set()
368
407
 
369
408
  def run(self, dag: DAGCircuit) -> DAGCircuit:
370
409
  """Run the HighLevelSynthesis pass on `dag`.
@@ -384,11 +423,11 @@ class HighLevelSynthesis(TransformationPass):
384
423
  dag_op_nodes = dag.op_nodes()
385
424
 
386
425
  for node in dag_op_nodes:
387
- if isinstance(node.op, ControlFlowOp):
426
+ if node.is_control_flow():
388
427
  node.op = control_flow.map_blocks(self.run, node.op)
389
428
  continue
390
429
 
391
- if getattr(node.op, "_directive", False):
430
+ if node.is_directive():
392
431
  continue
393
432
 
394
433
  if dag.has_calibration_for(node) or len(node.qargs) < self._min_qubits:
@@ -398,6 +437,9 @@ class HighLevelSynthesis(TransformationPass):
398
437
  [dag.find_bit(x).index for x in node.qargs] if self._use_qubit_indices else None
399
438
  )
400
439
 
440
+ if self._definitely_skip_node(node, qubits):
441
+ continue
442
+
401
443
  decomposition, modified = self._recursively_handle_op(node.op, qubits)
402
444
 
403
445
  if not modified:
@@ -414,6 +456,43 @@ class HighLevelSynthesis(TransformationPass):
414
456
 
415
457
  return dag
416
458
 
459
+ def _definitely_skip_node(self, node: DAGOpNode, qubits: Sequence[int] | None) -> bool:
460
+ """Fast-path determination of whether a node can certainly be skipped (i.e. nothing will
461
+ attempt to synthesise it) without accessing its Python-space `Operation`.
462
+
463
+ This is tightly coupled to `_recursively_handle_op`; it exists as a temporary measure to
464
+ avoid Python-space `Operation` creation from a `DAGOpNode` if we wouldn't do anything to the
465
+ node (which is _most_ nodes)."""
466
+ return (
467
+ # The fast path is just for Rust-space standard gates (which excludes
468
+ # `AnnotatedOperation`).
469
+ node.is_standard_gate()
470
+ # If it's a controlled gate, we might choose to do funny things to it.
471
+ and not node.is_controlled_gate()
472
+ # If there are plugins to try, they need to be tried.
473
+ and not self._methods_to_try(node.name)
474
+ # If all the above constraints hold, and it's already supported or the basis translator
475
+ # can handle it, we'll leave it be.
476
+ and (
477
+ self._instruction_supported(node.name, qubits)
478
+ # This uses unfortunately private details of `EquivalenceLibrary`, but so does the
479
+ # `BasisTranslator`, and this is supposed to just be temporary til this is moved
480
+ # into Rust space.
481
+ or (
482
+ self._equiv_lib is not None
483
+ and equivalence.Key(name=node.name, num_qubits=node.num_qubits)
484
+ in self._equiv_lib._key_to_node_index
485
+ )
486
+ )
487
+ )
488
+
489
+ def _instruction_supported(self, name: str, qubits: Sequence[int]) -> bool:
490
+ qubits = tuple(qubits) if qubits is not None else None
491
+ # include path for when target exists but target.num_qubits is None (BasicSimulator)
492
+ if self._target is None or self._target.num_qubits is None:
493
+ return name in self._device_insts
494
+ return self._target.instruction_supported(operation_name=name, qargs=qubits)
495
+
417
496
  def _recursively_handle_op(
418
497
  self, op: Operation, qubits: Optional[List] = None
419
498
  ) -> Tuple[Union[QuantumCircuit, DAGCircuit, Operation], bool]:
@@ -441,6 +520,9 @@ class HighLevelSynthesis(TransformationPass):
441
520
  an annotated operation.
442
521
  """
443
522
 
523
+ # WARNING: if adding new things in here, ensure that `_definitely_skip_node` is also
524
+ # up-to-date.
525
+
444
526
  # Try to apply plugin mechanism
445
527
  decomposition = self._synthesize_op_using_plugins(op, qubits)
446
528
  if decomposition is not None:
@@ -459,17 +541,9 @@ class HighLevelSynthesis(TransformationPass):
459
541
  # or is in equivalence library
460
542
  controlled_gate_open_ctrl = isinstance(op, ControlledGate) and op._open_ctrl
461
543
  if not controlled_gate_open_ctrl:
462
- qargs = tuple(qubits) if qubits is not None else None
463
- # include path for when target exists but target.num_qubits is None (BasicSimulator)
464
- inst_supported = (
465
- self._target.instruction_supported(
466
- operation_name=op.name,
467
- qargs=qargs,
468
- )
469
- if self._target is not None and self._target.num_qubits is not None
470
- else op.name in self._device_insts
471
- )
472
- if inst_supported or (self._equiv_lib is not None and self._equiv_lib.has_entry(op)):
544
+ if self._instruction_supported(op.name, qubits) or (
545
+ self._equiv_lib is not None and self._equiv_lib.has_entry(op)
546
+ ):
473
547
  return op, False
474
548
 
475
549
  try:
@@ -490,6 +564,22 @@ class HighLevelSynthesis(TransformationPass):
490
564
  dag = self.run(dag)
491
565
  return dag, True
492
566
 
567
+ def _methods_to_try(self, name: str):
568
+ """Get a sequence of methods to try for a given op name."""
569
+ if (methods := self.hls_config.methods.get(name)) is not None:
570
+ # the operation's name appears in the user-provided config,
571
+ # we use the list of methods provided by the user
572
+ return methods
573
+ if (
574
+ self.hls_config.use_default_on_unspecified
575
+ and "default" in self.hls_plugin_manager.method_names(name)
576
+ ):
577
+ # the operation's name does not appear in the user-specified config,
578
+ # we use the "default" method when instructed to do so and the "default"
579
+ # method is available
580
+ return ["default"]
581
+ return []
582
+
493
583
  def _synthesize_op_using_plugins(
494
584
  self, op: Operation, qubits: List
495
585
  ) -> Union[QuantumCircuit, None]:
@@ -500,25 +590,10 @@ class HighLevelSynthesis(TransformationPass):
500
590
  """
501
591
  hls_plugin_manager = self.hls_plugin_manager
502
592
 
503
- if op.name in self.hls_config.methods.keys():
504
- # the operation's name appears in the user-provided config,
505
- # we use the list of methods provided by the user
506
- methods = self.hls_config.methods[op.name]
507
- elif (
508
- self.hls_config.use_default_on_unspecified
509
- and "default" in hls_plugin_manager.method_names(op.name)
510
- ):
511
- # the operation's name does not appear in the user-specified config,
512
- # we use the "default" method when instructed to do so and the "default"
513
- # method is available
514
- methods = ["default"]
515
- else:
516
- methods = []
517
-
518
593
  best_decomposition = None
519
594
  best_score = np.inf
520
595
 
521
- for method in methods:
596
+ for method in self._methods_to_try(op.name):
522
597
  # There are two ways to specify a synthesis method. The more explicit
523
598
  # way is to specify it as a tuple consisting of a synthesis algorithm and a
524
599
  # list of additional arguments, e.g.,
@@ -540,8 +615,8 @@ class HighLevelSynthesis(TransformationPass):
540
615
  if isinstance(plugin_specifier, str):
541
616
  if plugin_specifier not in hls_plugin_manager.method_names(op.name):
542
617
  raise TranspilerError(
543
- "Specified method: %s not found in available plugins for %s"
544
- % (plugin_specifier, op.name)
618
+ f"Specified method: {plugin_specifier} not found in available "
619
+ f"plugins for {op.name}"
545
620
  )
546
621
  plugin_method = hls_plugin_manager.method(op.name, plugin_specifier)
547
622
  else:
@@ -779,7 +854,7 @@ class KMSSynthesisLinearFunction(HighLevelSynthesisPlugin):
779
854
  use_inverted = options.get("use_inverted", False)
780
855
  use_transposed = options.get("use_transposed", False)
781
856
 
782
- mat = high_level_object.linear.astype(int)
857
+ mat = high_level_object.linear.astype(bool, copy=False)
783
858
 
784
859
  if use_transposed:
785
860
  mat = np.transpose(mat)
@@ -831,7 +906,7 @@ class PMHSynthesisLinearFunction(HighLevelSynthesisPlugin):
831
906
  use_inverted = options.get("use_inverted", False)
832
907
  use_transposed = options.get("use_transposed", False)
833
908
 
834
- mat = high_level_object.linear.astype(int)
909
+ mat = high_level_object.linear.astype(bool, copy=False)
835
910
 
836
911
  if use_transposed:
837
912
  mat = np.transpose(mat)
@@ -887,6 +962,107 @@ class ACGSynthesisPermutation(HighLevelSynthesisPlugin):
887
962
  return decomposition
888
963
 
889
964
 
965
+ class QFTSynthesisFull(HighLevelSynthesisPlugin):
966
+ """Synthesis plugin for QFT gates using all-to-all connectivity.
967
+
968
+ This plugin name is :``qft.full`` which can be used as the key on
969
+ an :class:`~.HLSConfig` object to use this method with :class:`~.HighLevelSynthesis`.
970
+
971
+ The plugin supports the following additional options:
972
+
973
+ * reverse_qubits (bool): Whether to synthesize the "QFT" operation (if ``False``,
974
+ which is the default) or the "QFT-with-reversal" operation (if ``True``).
975
+ Some implementation of the ``QFTGate`` include a layer of swap gates at the end
976
+ of the synthesized circuit, which can in principle be dropped if the ``QFTGate``
977
+ itself is the last gate in the circuit.
978
+ * approximation_degree (int): The degree of approximation (0 for no approximation).
979
+ It is possible to implement the QFT approximately by ignoring
980
+ controlled-phase rotations with the angle beneath a threshold. This is discussed
981
+ in more detail in [1] or [2].
982
+ * insert_barriers (bool): If True, barriers are inserted as visualization improvement.
983
+ * inverse (bool): If True, the inverse Fourier transform is constructed.
984
+ * name (str): The name of the circuit.
985
+
986
+ References:
987
+ 1. Adriano Barenco, Artur Ekert, Kalle-Antti Suominen, and Päivi Törmä,
988
+ *Approximate Quantum Fourier Transform and Decoherence*,
989
+ Physical Review A (1996).
990
+ `arXiv:quant-ph/9601018 [quant-ph] <https://arxiv.org/abs/quant-ph/9601018>`_
991
+ 2. Donny Cheung,
992
+ *Improved Bounds for the Approximate QFT* (2004),
993
+ `arXiv:quant-ph/0403071 [quant-ph] <https://https://arxiv.org/abs/quant-ph/0403071>`_
994
+ """
995
+
996
+ def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
997
+ """Run synthesis for the given QFTGate."""
998
+ if not isinstance(high_level_object, QFTGate):
999
+ raise TranspilerError(
1000
+ "The synthesis plugin 'qft.full` only applies to objects of type QFTGate."
1001
+ )
1002
+
1003
+ reverse_qubits = options.get("reverse_qubits", False)
1004
+ approximation_degree = options.get("approximation_degree", 0)
1005
+ insert_barriers = options.get("insert_barriers", False)
1006
+ inverse = options.get("inverse", False)
1007
+ name = options.get("name", None)
1008
+
1009
+ decomposition = synth_qft_full(
1010
+ num_qubits=high_level_object.num_qubits,
1011
+ do_swaps=not reverse_qubits,
1012
+ approximation_degree=approximation_degree,
1013
+ insert_barriers=insert_barriers,
1014
+ inverse=inverse,
1015
+ name=name,
1016
+ )
1017
+ return decomposition
1018
+
1019
+
1020
+ class QFTSynthesisLine(HighLevelSynthesisPlugin):
1021
+ """Synthesis plugin for QFT gates using linear connectivity.
1022
+
1023
+ This plugin name is :``qft.line`` which can be used as the key on
1024
+ an :class:`~.HLSConfig` object to use this method with :class:`~.HighLevelSynthesis`.
1025
+
1026
+ The plugin supports the following additional options:
1027
+
1028
+ * reverse_qubits (bool): Whether to synthesize the "QFT" operation (if ``False``,
1029
+ which is the default) or the "QFT-with-reversal" operation (if ``True``).
1030
+ Some implementation of the ``QFTGate`` include a layer of swap gates at the end
1031
+ of the synthesized circuit, which can in principle be dropped if the ``QFTGate``
1032
+ itself is the last gate in the circuit.
1033
+ * approximation_degree (int): the degree of approximation (0 for no approximation).
1034
+ It is possible to implement the QFT approximately by ignoring
1035
+ controlled-phase rotations with the angle beneath a threshold. This is discussed
1036
+ in more detail in [1] or [2].
1037
+
1038
+ References:
1039
+ 1. Adriano Barenco, Artur Ekert, Kalle-Antti Suominen, and Päivi Törmä,
1040
+ *Approximate Quantum Fourier Transform and Decoherence*,
1041
+ Physical Review A (1996).
1042
+ `arXiv:quant-ph/9601018 [quant-ph] <https://arxiv.org/abs/quant-ph/9601018>`_
1043
+ 2. Donny Cheung,
1044
+ *Improved Bounds for the Approximate QFT* (2004),
1045
+ `arXiv:quant-ph/0403071 [quant-ph] <https://https://arxiv.org/abs/quant-ph/0403071>`_
1046
+ """
1047
+
1048
+ def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
1049
+ """Run synthesis for the given QFTGate."""
1050
+ if not isinstance(high_level_object, QFTGate):
1051
+ raise TranspilerError(
1052
+ "The synthesis plugin 'qft.line` only applies to objects of type QFTGate."
1053
+ )
1054
+
1055
+ reverse_qubits = options.get("reverse_qubits", False)
1056
+ approximation_degree = options.get("approximation_degree", 0)
1057
+
1058
+ decomposition = synth_qft_line(
1059
+ num_qubits=high_level_object.num_qubits,
1060
+ do_swaps=not reverse_qubits,
1061
+ approximation_degree=approximation_degree,
1062
+ )
1063
+ return decomposition
1064
+
1065
+
890
1066
  class TokenSwapperSynthesisPermutation(HighLevelSynthesisPlugin):
891
1067
  """The permutation synthesis plugin based on the token swapper algorithm.
892
1068
 
@@ -917,7 +1093,6 @@ class TokenSwapperSynthesisPermutation(HighLevelSynthesisPlugin):
917
1093
 
918
1094
  For more details on the token swapper algorithm, see to the paper:
919
1095
  `arXiv:1902.09102 <https://arxiv.org/abs/1902.09102>`__.
920
-
921
1096
  """
922
1097
 
923
1098
  def run(self, high_level_object, coupling_map=None, target=None, qubits=None, **options):
@@ -698,13 +698,13 @@ class HighLevelSynthesisPluginManager:
698
698
  self.plugins_by_op = {}
699
699
  for plugin_name in self.plugins.names():
700
700
  op_name, method_name = plugin_name.split(".")
701
- if op_name not in self.plugins_by_op.keys():
701
+ if op_name not in self.plugins_by_op:
702
702
  self.plugins_by_op[op_name] = []
703
703
  self.plugins_by_op[op_name].append(method_name)
704
704
 
705
705
  def method_names(self, op_name):
706
706
  """Returns plugin methods for op_name."""
707
- if op_name in self.plugins_by_op.keys():
707
+ if op_name in self.plugins_by_op:
708
708
  return self.plugins_by_op[op_name]
709
709
  else:
710
710
  return []
@@ -28,21 +28,9 @@ from itertools import product
28
28
  from functools import partial
29
29
  import numpy as np
30
30
 
31
- from qiskit.converters import circuit_to_dag, dag_to_circuit
32
- from qiskit.transpiler import CouplingMap, Target
33
- from qiskit.transpiler.basepasses import TransformationPass
34
- from qiskit.transpiler.exceptions import TranspilerError
35
- from qiskit.dagcircuit.dagcircuit import DAGCircuit
36
- from qiskit.synthesis.one_qubit import one_qubit_decompose
37
- from qiskit.transpiler.passes.optimization.optimize_1q_decomposition import _possible_decomposers
38
- from qiskit.synthesis.two_qubit.xx_decompose import XXDecomposer, XXEmbodiments
39
- from qiskit.synthesis.two_qubit.two_qubit_decompose import (
40
- TwoQubitBasisDecomposer,
41
- TwoQubitWeylDecomposition,
42
- GATE_NAME_MAP,
43
- )
44
- from qiskit.quantum_info import Operator
45
- from qiskit.circuit import ControlFlowOp, Gate, Parameter
31
+ from qiskit.circuit.controlflow import CONTROL_FLOW_OP_NAMES
32
+ from qiskit.circuit import Gate, Parameter, CircuitInstruction
33
+ from qiskit.circuit.library.standard_gates import get_standard_gate_name_mapping
46
34
  from qiskit.circuit.library.standard_gates import (
47
35
  iSwapGate,
48
36
  CXGate,
@@ -51,14 +39,54 @@ from qiskit.circuit.library.standard_gates import (
51
39
  RZXGate,
52
40
  RZZGate,
53
41
  ECRGate,
42
+ RXGate,
43
+ SXGate,
44
+ XGate,
45
+ RZGate,
46
+ UGate,
47
+ PhaseGate,
48
+ U1Gate,
49
+ U2Gate,
50
+ U3Gate,
51
+ RYGate,
52
+ RGate,
54
53
  )
55
- from qiskit.transpiler.passes.synthesis import plugin
54
+ from qiskit.converters import circuit_to_dag, dag_to_circuit
55
+ from qiskit.dagcircuit.dagcircuit import DAGCircuit, DAGOpNode
56
+ from qiskit.exceptions import QiskitError
57
+ from qiskit.providers.models.backendproperties import BackendProperties
58
+ from qiskit.quantum_info import Operator
59
+ from qiskit.synthesis.one_qubit import one_qubit_decompose
60
+ from qiskit.synthesis.two_qubit.xx_decompose import XXDecomposer, XXEmbodiments
61
+ from qiskit.synthesis.two_qubit.two_qubit_decompose import (
62
+ TwoQubitBasisDecomposer,
63
+ TwoQubitWeylDecomposition,
64
+ )
65
+ from qiskit.transpiler.basepasses import TransformationPass
66
+ from qiskit.transpiler.coupling import CouplingMap
67
+ from qiskit.transpiler.exceptions import TranspilerError
56
68
  from qiskit.transpiler.passes.optimization.optimize_1q_decomposition import (
57
69
  Optimize1qGatesDecomposition,
70
+ _possible_decomposers,
58
71
  )
59
- from qiskit.providers.models import BackendProperties
60
- from qiskit.circuit.library.standard_gates import get_standard_gate_name_mapping
61
- from qiskit.exceptions import QiskitError
72
+ from qiskit.transpiler.passes.synthesis import plugin
73
+ from qiskit.transpiler.target import Target
74
+
75
+
76
+ GATE_NAME_MAP = {
77
+ "cx": CXGate._standard_gate,
78
+ "rx": RXGate._standard_gate,
79
+ "sx": SXGate._standard_gate,
80
+ "x": XGate._standard_gate,
81
+ "rz": RZGate._standard_gate,
82
+ "u": UGate._standard_gate,
83
+ "p": PhaseGate._standard_gate,
84
+ "u1": U1Gate._standard_gate,
85
+ "u2": U2Gate._standard_gate,
86
+ "u3": U3Gate._standard_gate,
87
+ "ry": RYGate._standard_gate,
88
+ "r": RGate._standard_gate,
89
+ }
62
90
 
63
91
 
64
92
  KAK_GATE_NAMES = {
@@ -415,7 +443,7 @@ class UnitarySynthesis(TransformationPass):
415
443
  if self.method == "default":
416
444
  # If the method is the default, we only need to evaluate one set of keyword arguments.
417
445
  # To simplify later logic, and avoid cases where static analysis might complain that we
418
- # haven't initialised the "default" handler, we rebind the names so they point to the
446
+ # haven't initialized the "default" handler, we rebind the names so they point to the
419
447
  # same object as the chosen method.
420
448
  default_method = plugin_method
421
449
  default_kwargs = plugin_kwargs
@@ -480,7 +508,9 @@ class UnitarySynthesis(TransformationPass):
480
508
  self, dag, qubit_indices, plugin_method, plugin_kwargs, default_method, default_kwargs
481
509
  ):
482
510
  """Inner loop for the optimizer, after all DAG-independent set-up has been completed."""
483
- for node in dag.op_nodes(ControlFlowOp):
511
+ for node in dag.op_nodes():
512
+ if node.name not in CONTROL_FLOW_OP_NAMES:
513
+ continue
484
514
  node.op = node.op.replace_blocks(
485
515
  [
486
516
  dag_to_circuit(
@@ -503,9 +533,9 @@ class UnitarySynthesis(TransformationPass):
503
533
 
504
534
  out_dag = dag.copy_empty_like()
505
535
  for node in dag.topological_op_nodes():
506
- if node.op.name == "unitary" and len(node.qargs) >= self._min_qubits:
536
+ if node.name == "unitary" and len(node.qargs) >= self._min_qubits:
507
537
  synth_dag = None
508
- unitary = node.op.to_matrix()
538
+ unitary = node.matrix
509
539
  n_qubits = len(node.qargs)
510
540
  if (
511
541
  plugin_method.max_qubits is not None and n_qubits > plugin_method.max_qubits
@@ -520,35 +550,42 @@ class UnitarySynthesis(TransformationPass):
520
550
  )
521
551
  synth_dag = method.run(unitary, **kwargs)
522
552
  if synth_dag is None:
523
- out_dag.apply_operation_back(node.op, node.qargs, node.cargs, check=False)
553
+ out_dag._apply_op_node_back(node)
524
554
  continue
525
555
  if isinstance(synth_dag, DAGCircuit):
526
556
  qubit_map = dict(zip(synth_dag.qubits, node.qargs))
527
557
  for node in synth_dag.topological_op_nodes():
528
- out_dag.apply_operation_back(
529
- node.op, (qubit_map[x] for x in node.qargs), check=False
530
- )
558
+ node.qargs = tuple(qubit_map[x] for x in node.qargs)
559
+ out_dag._apply_op_node_back(node)
531
560
  out_dag.global_phase += synth_dag.global_phase
532
561
  else:
533
562
  node_list, global_phase, gate = synth_dag
534
563
  qubits = node.qargs
564
+ user_gate_node = DAGOpNode(gate)
535
565
  for (
536
- op_name,
566
+ gate,
537
567
  params,
538
568
  qargs,
539
569
  ) in node_list:
540
- if op_name == "USER_GATE":
541
- op = gate
570
+ if gate is None:
571
+ node = DAGOpNode.from_instruction(
572
+ user_gate_node._to_circuit_instruction().replace(
573
+ params=user_gate_node.params,
574
+ qubits=tuple(qubits[x] for x in qargs),
575
+ ),
576
+ dag=out_dag,
577
+ )
542
578
  else:
543
- op = GATE_NAME_MAP[op_name](*params)
544
- out_dag.apply_operation_back(
545
- op,
546
- (qubits[x] for x in qargs),
547
- check=False,
548
- )
579
+ node = DAGOpNode.from_instruction(
580
+ CircuitInstruction.from_standard(
581
+ gate, tuple(qubits[x] for x in qargs), params
582
+ ),
583
+ dag=out_dag,
584
+ )
585
+ out_dag._apply_op_node_back(node)
549
586
  out_dag.global_phase += global_phase
550
587
  else:
551
- out_dag.apply_operation_back(node.op, node.qargs, node.cargs, check=False)
588
+ out_dag._apply_op_node_back(node)
552
589
  return out_dag
553
590
 
554
591
 
@@ -975,8 +1012,8 @@ class DefaultUnitarySynthesis(plugin.UnitarySynthesisPlugin):
975
1012
  # if the gates in synthesis are in the opposite direction of the preferred direction
976
1013
  # resynthesize a new operator which is the original conjugated by swaps.
977
1014
  # this new operator is doubly mirrored from the original and is locally equivalent.
978
- for op_name, _params, qubits in synth_circ:
979
- if op_name in {"USER_GATE", "cx"}:
1015
+ for gate, _params, qubits in synth_circ:
1016
+ if gate is None or gate == CXGate._standard_gate:
980
1017
  synth_direction = qubits
981
1018
  if synth_direction is not None and synth_direction != preferred_direction:
982
1019
  # TODO: Avoid using a dag to correct the synthesis direction
@@ -1011,5 +1048,8 @@ class DefaultUnitarySynthesis(plugin.UnitarySynthesisPlugin):
1011
1048
  flip_bits = out_dag.qubits[::-1]
1012
1049
  for node in synth_circ.topological_op_nodes():
1013
1050
  qubits = tuple(flip_bits[synth_circ.find_bit(x).index] for x in node.qargs)
1014
- out_dag.apply_operation_back(node.op, qubits, check=False)
1051
+ node = DAGOpNode.from_instruction(
1052
+ node._to_circuit_instruction().replace(qubits=qubits, params=node.params)
1053
+ )
1054
+ out_dag._apply_op_node_back(node)
1015
1055
  return out_dag
@@ -31,4 +31,3 @@ from .filter_op_nodes import FilterOpNodes
31
31
 
32
32
  # Utility functions
33
33
  from . import control_flow
34
- from .block_to_matrix import _block_to_matrix
@@ -12,7 +12,7 @@
12
12
 
13
13
  """Check if the gates follow the right direction with respect to the coupling map."""
14
14
 
15
- from qiskit.circuit import ControlFlowOp
15
+ from qiskit.circuit.controlflow import CONTROL_FLOW_OP_NAMES
16
16
  from qiskit.converters import circuit_to_dag
17
17
  from qiskit.transpiler.basepasses import AnalysisPass
18
18
 
@@ -39,7 +39,7 @@ class CheckGateDirection(AnalysisPass):
39
39
  edges = self.coupling_map.get_edges()
40
40
  # Don't include directives to avoid things like barrier, which are assumed always supported.
41
41
  for node in dag.op_nodes(include_directives=False):
42
- if isinstance(node.op, ControlFlowOp):
42
+ if node.name in CONTROL_FLOW_OP_NAMES:
43
43
  for block in node.op.blocks:
44
44
  inner_wire_map = {
45
45
  inner: wire_map[outer] for outer, inner in zip(node.qargs, block.qubits)
@@ -57,7 +57,7 @@ class CheckGateDirection(AnalysisPass):
57
57
  def _target_visit(self, dag, wire_map):
58
58
  # Don't include directives to avoid things like barrier, which are assumed always supported.
59
59
  for node in dag.op_nodes(include_directives=False):
60
- if isinstance(node.op, ControlFlowOp):
60
+ if node.name in CONTROL_FLOW_OP_NAMES:
61
61
  for block in node.op.blocks:
62
62
  inner_wire_map = {
63
63
  inner: wire_map[outer] for outer, inner in zip(node.qargs, block.qubits)
@@ -65,7 +65,7 @@ class CheckGateDirection(AnalysisPass):
65
65
  if not self._target_visit(circuit_to_dag(block), inner_wire_map):
66
66
  return False
67
67
  elif len(node.qargs) == 2 and not self.target.instruction_supported(
68
- node.op.name, (wire_map[node.qargs[0]], wire_map[node.qargs[1]])
68
+ node.name, (wire_map[node.qargs[0]], wire_map[node.qargs[1]])
69
69
  ):
70
70
  return False
71
71
  return True
@@ -14,7 +14,6 @@
14
14
 
15
15
  from qiskit.transpiler.basepasses import AnalysisPass
16
16
  from qiskit.transpiler.target import Target
17
- from qiskit.circuit.controlflow import ControlFlowOp
18
17
  from qiskit.converters import circuit_to_dag
19
18
 
20
19
 
@@ -73,7 +72,7 @@ class CheckMap(AnalysisPass):
73
72
 
74
73
  def _recurse(self, dag, wire_map) -> bool:
75
74
  for node in dag.op_nodes(include_directives=False):
76
- if isinstance(node.op, ControlFlowOp):
75
+ if node.is_control_flow():
77
76
  for block in node.op.blocks:
78
77
  inner_wire_map = {
79
78
  inner: wire_map[outer] for inner, outer in zip(block.qubits, node.qargs)
@@ -85,10 +84,8 @@ class CheckMap(AnalysisPass):
85
84
  and not dag.has_calibration_for(node)
86
85
  and (wire_map[node.qargs[0]], wire_map[node.qargs[1]]) not in self.qargs
87
86
  ):
88
- self.property_set["check_map_msg"] = "{}({}, {}) failed".format(
89
- node.name,
90
- wire_map[node.qargs[0]],
91
- wire_map[node.qargs[1]],
87
+ self.property_set["check_map_msg"] = (
88
+ f"{node.name}({wire_map[node.qargs[0]]}, {wire_map[node.qargs[1]]}) failed"
92
89
  )
93
90
  return False
94
91
  return True