classiq 0.93.0__py3-none-any.whl → 0.94.1__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of classiq might be problematic. Click here for more details.

Files changed (261) hide show
  1. classiq/__init__.py +6 -19
  2. classiq/_analyzer_extras/_ipywidgets_async_extension.py +7 -7
  3. classiq/_analyzer_extras/interactive_hardware.py +19 -12
  4. classiq/_internals/api_wrapper.py +38 -52
  5. classiq/_internals/async_utils.py +4 -7
  6. classiq/_internals/authentication/auth0.py +3 -3
  7. classiq/_internals/authentication/device.py +4 -4
  8. classiq/_internals/authentication/password_manager.py +13 -13
  9. classiq/_internals/authentication/token_manager.py +4 -5
  10. classiq/_internals/client.py +17 -44
  11. classiq/_internals/config.py +1 -2
  12. classiq/_internals/help.py +1 -2
  13. classiq/_internals/host_checker.py +3 -3
  14. classiq/_internals/jobs.py +14 -14
  15. classiq/_internals/type_validation.py +3 -3
  16. classiq/analyzer/analyzer.py +18 -18
  17. classiq/analyzer/rb.py +17 -8
  18. classiq/applications/chemistry/__init__.py +0 -30
  19. classiq/applications/chemistry/op_utils.py +4 -4
  20. classiq/applications/chemistry/problems.py +3 -3
  21. classiq/applications/chemistry/ucc.py +1 -2
  22. classiq/applications/chemistry/z2_symmetries.py +4 -4
  23. classiq/applications/combinatorial_helpers/allowed_constraints.py +1 -3
  24. classiq/applications/combinatorial_helpers/arithmetic/arithmetic_expression.py +2 -1
  25. classiq/applications/combinatorial_helpers/combinatorial_problem_utils.py +2 -2
  26. classiq/applications/combinatorial_helpers/encoding_mapping.py +2 -3
  27. classiq/applications/combinatorial_helpers/encoding_utils.py +2 -2
  28. classiq/applications/combinatorial_helpers/optimization_model.py +3 -4
  29. classiq/applications/combinatorial_helpers/pauli_helpers/pauli_sparsing.py +2 -2
  30. classiq/applications/combinatorial_helpers/pyomo_utils.py +8 -8
  31. classiq/applications/combinatorial_helpers/sympy_utils.py +1 -3
  32. classiq/applications/combinatorial_helpers/transformations/encoding.py +3 -3
  33. classiq/applications/combinatorial_helpers/transformations/fixed_variables.py +1 -2
  34. classiq/applications/combinatorial_optimization/combinatorial_optimization_config.py +2 -3
  35. classiq/applications/combinatorial_optimization/combinatorial_optimization_model_constructor.py +4 -6
  36. classiq/applications/combinatorial_optimization/combinatorial_problem.py +15 -10
  37. classiq/applications/hamiltonian/pauli_decomposition.py +6 -4
  38. classiq/applications/iqae/iqae.py +8 -8
  39. classiq/applications/qnn/datasets/dataset_base_classes.py +6 -6
  40. classiq/applications/qnn/datasets/dataset_parity.py +6 -6
  41. classiq/applications/qnn/qlayer.py +8 -7
  42. classiq/applications/qnn/torch_utils.py +3 -4
  43. classiq/applications/qnn/types.py +2 -1
  44. classiq/applications/qsp/qsp.py +5 -4
  45. classiq/applications/qsvm/qsvm_data_generation.py +1 -2
  46. classiq/evaluators/classical_expression.py +0 -4
  47. classiq/evaluators/parameter_types.py +7 -8
  48. classiq/evaluators/qmod_annotated_expression.py +24 -26
  49. classiq/evaluators/qmod_expression_visitors/qmod_expression_evaluator.py +14 -14
  50. classiq/evaluators/qmod_expression_visitors/qmod_expression_simplifier.py +2 -1
  51. classiq/evaluators/qmod_expression_visitors/sympy_wrappers.py +8 -8
  52. classiq/evaluators/qmod_node_evaluators/classical_function_evaluation.py +4 -4
  53. classiq/evaluators/qmod_node_evaluators/list_evaluation.py +2 -2
  54. classiq/evaluators/qmod_node_evaluators/numeric_attrs_utils.py +3 -3
  55. classiq/evaluators/qmod_node_evaluators/subscript_evaluation.py +9 -9
  56. classiq/evaluators/qmod_node_evaluators/utils.py +6 -6
  57. classiq/evaluators/qmod_type_inference/classical_type_inference.py +9 -10
  58. classiq/evaluators/qmod_type_inference/quantum_type_inference.py +5 -5
  59. classiq/execution/execution_session.py +18 -19
  60. classiq/execution/jobs.py +26 -26
  61. classiq/execution/qnn.py +1 -2
  62. classiq/execution/user_budgets.py +52 -7
  63. classiq/executor.py +1 -3
  64. classiq/interface/_version.py +1 -1
  65. classiq/interface/analyzer/analysis_params.py +4 -4
  66. classiq/interface/analyzer/cytoscape_graph.py +3 -3
  67. classiq/interface/analyzer/result.py +4 -4
  68. classiq/interface/applications/qsvm.py +5 -8
  69. classiq/interface/ast_node.py +3 -3
  70. classiq/interface/backend/backend_preferences.py +16 -16
  71. classiq/interface/backend/ionq/ionq_quantum_program.py +5 -5
  72. classiq/interface/chemistry/ansatz_library.py +3 -5
  73. classiq/interface/chemistry/operator.py +3 -3
  74. classiq/interface/combinatorial_optimization/examples/knapsack.py +2 -4
  75. classiq/interface/combinatorial_optimization/examples/tsp_digraph.py +1 -2
  76. classiq/interface/compression_utils.py +2 -3
  77. classiq/interface/debug_info/debug_info.py +7 -7
  78. classiq/interface/exceptions.py +2 -3
  79. classiq/interface/execution/iqcc.py +1 -3
  80. classiq/interface/execution/primitives.py +6 -6
  81. classiq/interface/executor/estimate_cost.py +1 -1
  82. classiq/interface/executor/execution_preferences.py +3 -5
  83. classiq/interface/executor/execution_request.py +10 -10
  84. classiq/interface/executor/execution_result.py +1 -2
  85. classiq/interface/executor/quantum_code.py +8 -8
  86. classiq/interface/executor/result.py +28 -18
  87. classiq/interface/executor/user_budget.py +2 -3
  88. classiq/interface/executor/vqe_result.py +5 -6
  89. classiq/interface/generator/ansatz_library.py +6 -8
  90. classiq/interface/generator/application_apis/__init__.py +0 -2
  91. classiq/interface/generator/arith/arithmetic.py +2 -2
  92. classiq/interface/generator/arith/arithmetic_arg_type_validator.py +2 -3
  93. classiq/interface/generator/arith/arithmetic_expression_abc.py +4 -5
  94. classiq/interface/generator/arith/arithmetic_expression_parser.py +11 -4
  95. classiq/interface/generator/arith/arithmetic_expression_validator.py +12 -15
  96. classiq/interface/generator/arith/arithmetic_operations.py +4 -6
  97. classiq/interface/generator/arith/arithmetic_param_getters.py +70 -107
  98. classiq/interface/generator/arith/arithmetic_result_builder.py +4 -4
  99. classiq/interface/generator/arith/ast_node_rewrite.py +8 -4
  100. classiq/interface/generator/arith/binary_ops.py +7 -36
  101. classiq/interface/generator/arith/logical_ops.py +2 -3
  102. classiq/interface/generator/arith/number_utils.py +2 -2
  103. classiq/interface/generator/arith/register_user_input.py +2 -2
  104. classiq/interface/generator/arith/unary_ops.py +2 -2
  105. classiq/interface/generator/circuit_code/circuit_code.py +8 -10
  106. classiq/interface/generator/circuit_code/types_and_constants.py +1 -1
  107. classiq/interface/generator/complex_type.py +2 -2
  108. classiq/interface/generator/copy.py +1 -3
  109. classiq/interface/generator/expressions/atomic_expression_functions.py +0 -5
  110. classiq/interface/generator/expressions/evaluated_expression.py +2 -3
  111. classiq/interface/generator/expressions/expression.py +2 -2
  112. classiq/interface/generator/expressions/proxies/classical/classical_array_proxy.py +4 -7
  113. classiq/interface/generator/function_param_list.py +0 -20
  114. classiq/interface/generator/function_params.py +5 -6
  115. classiq/interface/generator/functions/classical_function_declaration.py +2 -2
  116. classiq/interface/generator/functions/classical_type.py +3 -3
  117. classiq/interface/generator/functions/type_modifier.py +0 -14
  118. classiq/interface/generator/functions/type_name.py +2 -2
  119. classiq/interface/generator/generated_circuit_data.py +12 -13
  120. classiq/interface/generator/hamiltonian_evolution/exponentiation.py +2 -4
  121. classiq/interface/generator/hardware/hardware_data.py +8 -8
  122. classiq/interface/generator/hardware_efficient_ansatz.py +8 -8
  123. classiq/interface/generator/mcu.py +3 -3
  124. classiq/interface/generator/mcx.py +3 -3
  125. classiq/interface/generator/model/constraints.py +34 -5
  126. classiq/interface/generator/model/preferences/preferences.py +15 -21
  127. classiq/interface/generator/model/quantum_register.py +7 -10
  128. classiq/interface/generator/noise_properties.py +3 -7
  129. classiq/interface/generator/parameters.py +1 -1
  130. classiq/interface/generator/partitioned_register.py +1 -2
  131. classiq/interface/generator/preferences/qasm_to_qmod_params.py +11 -0
  132. classiq/interface/generator/qsvm.py +2 -2
  133. classiq/interface/generator/quantum_function_call.py +8 -11
  134. classiq/interface/generator/quantum_program.py +12 -15
  135. classiq/interface/generator/range_types.py +3 -3
  136. classiq/interface/generator/slice_parsing_utils.py +4 -5
  137. classiq/interface/generator/standard_gates/standard_gates.py +2 -4
  138. classiq/interface/generator/state_preparation/state_preparation.py +6 -8
  139. classiq/interface/generator/synthesis_execution_parameter.py +1 -3
  140. classiq/interface/generator/synthesis_metadata/synthesis_execution_data.py +2 -3
  141. classiq/interface/generator/transpiler_basis_gates.py +2 -4
  142. classiq/interface/generator/types/builtin_enum_declarations.py +0 -136
  143. classiq/interface/generator/types/compilation_metadata.py +12 -1
  144. classiq/interface/generator/types/enum_declaration.py +2 -1
  145. classiq/interface/generator/validations/flow_graph.py +3 -3
  146. classiq/interface/generator/visitor.py +10 -12
  147. classiq/interface/hardware.py +2 -2
  148. classiq/interface/helpers/classproperty.py +2 -2
  149. classiq/interface/helpers/custom_encoders.py +2 -1
  150. classiq/interface/helpers/custom_pydantic_types.py +1 -1
  151. classiq/interface/helpers/text_utils.py +1 -4
  152. classiq/interface/ide/visual_model.py +5 -5
  153. classiq/interface/jobs.py +3 -3
  154. classiq/interface/model/allocate.py +4 -4
  155. classiq/interface/model/block.py +2 -2
  156. classiq/interface/model/bounds.py +3 -3
  157. classiq/interface/model/control.py +1 -1
  158. classiq/interface/model/inplace_binary_operation.py +2 -2
  159. classiq/interface/model/model.py +4 -4
  160. classiq/interface/model/parameter.py +1 -3
  161. classiq/interface/model/port_declaration.py +1 -1
  162. classiq/interface/model/quantum_expressions/quantum_expression.py +1 -2
  163. classiq/interface/model/quantum_function_call.py +3 -6
  164. classiq/interface/model/quantum_function_declaration.py +1 -0
  165. classiq/interface/model/quantum_lambda_function.py +4 -4
  166. classiq/interface/model/quantum_statement.py +4 -4
  167. classiq/interface/model/quantum_type.py +14 -14
  168. classiq/interface/model/validation_handle.py +2 -3
  169. classiq/interface/model/variable_declaration_statement.py +2 -2
  170. classiq/interface/pretty_print/expression_to_qmod.py +3 -4
  171. classiq/interface/server/routes.py +0 -4
  172. classiq/interface/source_reference.py +3 -4
  173. classiq/model_expansions/arithmetic.py +6 -7
  174. classiq/model_expansions/arithmetic_compute_result_attrs.py +4 -5
  175. classiq/model_expansions/capturing/captured_vars.py +3 -3
  176. classiq/model_expansions/capturing/mangling_utils.py +1 -2
  177. classiq/model_expansions/closure.py +12 -11
  178. classiq/model_expansions/function_builder.py +14 -6
  179. classiq/model_expansions/generative_functions.py +1 -4
  180. classiq/model_expansions/interpreters/base_interpreter.py +2 -6
  181. classiq/model_expansions/interpreters/generative_interpreter.py +5 -3
  182. classiq/model_expansions/quantum_operations/allocate.py +4 -4
  183. classiq/model_expansions/quantum_operations/assignment_result_processor.py +2 -4
  184. classiq/model_expansions/quantum_operations/call_emitter.py +31 -37
  185. classiq/model_expansions/quantum_operations/declarative_call_emitter.py +2 -2
  186. classiq/model_expansions/quantum_operations/emitter.py +3 -5
  187. classiq/model_expansions/quantum_operations/expression_evaluator.py +3 -3
  188. classiq/model_expansions/quantum_operations/skip_control_verifier.py +1 -2
  189. classiq/model_expansions/quantum_operations/variable_decleration.py +2 -2
  190. classiq/model_expansions/scope.py +7 -7
  191. classiq/model_expansions/scope_initialization.py +4 -0
  192. classiq/model_expansions/visitors/symbolic_param_inference.py +3 -3
  193. classiq/model_expansions/visitors/uncomputation_signature_inference.py +317 -0
  194. classiq/model_expansions/visitors/variable_references.py +15 -14
  195. classiq/open_library/functions/__init__.py +6 -0
  196. classiq/open_library/functions/discrete_sine_cosine_transform.py +5 -5
  197. classiq/open_library/functions/grover.py +8 -10
  198. classiq/open_library/functions/modular_exponentiation.py +96 -8
  199. classiq/qmod/__init__.py +5 -2
  200. classiq/qmod/builtins/classical_execution_primitives.py +4 -11
  201. classiq/qmod/builtins/classical_functions.py +1 -42
  202. classiq/qmod/builtins/enums.py +0 -136
  203. classiq/qmod/builtins/functions/__init__.py +0 -13
  204. classiq/qmod/builtins/functions/allocation.py +4 -4
  205. classiq/qmod/builtins/functions/arithmetic.py +22 -27
  206. classiq/qmod/builtins/functions/standard_gates.py +27 -27
  207. classiq/qmod/builtins/operations.py +35 -58
  208. classiq/qmod/builtins/structs.py +2 -58
  209. classiq/qmod/cfunc.py +3 -2
  210. classiq/qmod/classical_function.py +2 -1
  211. classiq/qmod/cparam.py +2 -8
  212. classiq/qmod/create_model_function.py +7 -7
  213. classiq/qmod/declaration_inferrer.py +33 -30
  214. classiq/qmod/model_state_container.py +2 -2
  215. classiq/qmod/native/pretty_printer.py +25 -14
  216. classiq/qmod/pretty_print/expression_to_python.py +5 -3
  217. classiq/qmod/pretty_print/pretty_printer.py +39 -17
  218. classiq/qmod/python_classical_type.py +40 -13
  219. classiq/qmod/qfunc.py +139 -16
  220. classiq/qmod/qmod_constant.py +2 -2
  221. classiq/qmod/qmod_parameter.py +5 -2
  222. classiq/qmod/qmod_variable.py +47 -43
  223. classiq/qmod/quantum_callable.py +18 -13
  224. classiq/qmod/quantum_expandable.py +31 -26
  225. classiq/qmod/quantum_function.py +51 -32
  226. classiq/qmod/semantics/annotation/call_annotation.py +2 -2
  227. classiq/qmod/semantics/error_manager.py +5 -6
  228. classiq/qmod/semantics/lambdas.py +1 -2
  229. classiq/qmod/semantics/validation/types_validation.py +1 -2
  230. classiq/qmod/symbolic.py +2 -4
  231. classiq/qmod/utilities.py +13 -10
  232. classiq/qmod/write_qmod.py +3 -4
  233. classiq/quantum_program.py +1 -3
  234. classiq/synthesis.py +11 -7
  235. {classiq-0.93.0.dist-info → classiq-0.94.1.dist-info}/METADATA +2 -3
  236. {classiq-0.93.0.dist-info → classiq-0.94.1.dist-info}/RECORD +238 -260
  237. classiq/applications/chemistry/ansatz_parameters.py +0 -29
  238. classiq/applications/chemistry/chemistry_execution_parameters.py +0 -16
  239. classiq/applications/chemistry/chemistry_model_constructor.py +0 -532
  240. classiq/applications/chemistry/ground_state_problem.py +0 -42
  241. classiq/evaluators/qmod_expression_visitors/qmod_expression_bwc.py +0 -129
  242. classiq/interface/chemistry/elements.py +0 -120
  243. classiq/interface/chemistry/fermionic_operator.py +0 -208
  244. classiq/interface/chemistry/ground_state_problem.py +0 -132
  245. classiq/interface/chemistry/ground_state_result.py +0 -8
  246. classiq/interface/chemistry/molecule.py +0 -71
  247. classiq/interface/generator/application_apis/chemistry_declarations.py +0 -69
  248. classiq/interface/generator/application_apis/entangler_declarations.py +0 -29
  249. classiq/interface/generator/chemistry_function_params.py +0 -50
  250. classiq/interface/generator/entangler_params.py +0 -72
  251. classiq/interface/generator/entanglers.py +0 -14
  252. classiq/interface/generator/hartree_fock.py +0 -26
  253. classiq/interface/generator/hva.py +0 -22
  254. classiq/interface/generator/linear_pauli_rotations.py +0 -92
  255. classiq/interface/generator/qft.py +0 -37
  256. classiq/interface/generator/ucc.py +0 -74
  257. classiq/interface/helpers/backward_compatibility.py +0 -9
  258. classiq/model_expansions/transformers/type_modifier_inference.py +0 -392
  259. classiq/qmod/builtins/functions/chemistry.py +0 -123
  260. {classiq-0.93.0.dist-info → classiq-0.94.1.dist-info}/WHEEL +0 -0
  261. {classiq-0.93.0.dist-info → classiq-0.94.1.dist-info}/licenses/LICENSE.txt +0 -0
@@ -1,5 +1,4 @@
1
1
  ANALYZER_PREFIX = "/analyzer"
2
- CHEMISTRY_PREFIX = "/chemistry"
3
2
  EXECUTION_PREFIX = "/execution"
4
3
  EXECUTION_SESSIONS_PREFIX = EXECUTION_PREFIX + "/sessions"
5
4
  CONVERSION_PREFIX = "/conversion"
@@ -62,9 +61,6 @@ ANALYZER_RB_FULL_PATH = ANALYZER_PREFIX + TASK_RB_SUFFIX
62
61
 
63
62
  TASKS_SOLVE_EXACT_SUFFIX = "/tasks/solve_exact"
64
63
 
65
- GENERATE_HAMILTONIAN_SUFFIX = "/generate_hamiltonian"
66
- GENERATE_HAMILTONIAN_FULL_PATH = CHEMISTRY_PREFIX + GENERATE_HAMILTONIAN_SUFFIX
67
-
68
64
  CONVERSION_GENERATED_CIRCUIT_TO_EXECUTION_INPUT_SUFFIX = "/execution_input"
69
65
  CONVERSION_GENERATED_CIRCUIT_TO_EXECUTION_INPUT_FULL = (
70
66
  CONVERSION_PREFIX + CONVERSION_GENERATED_CIRCUIT_TO_EXECUTION_INPUT_SUFFIX
@@ -1,7 +1,6 @@
1
1
  import os
2
2
  import re
3
3
  from pathlib import Path
4
- from typing import Optional
5
4
 
6
5
  import pydantic
7
6
 
@@ -30,7 +29,7 @@ class SourceReference(HashablePydanticBaseModel):
30
29
  start_column: int
31
30
  end_line: int
32
31
  end_column: int
33
- file_name: Optional[str] = pydantic.Field(default=None)
32
+ file_name: str | None = pydantic.Field(default=None)
34
33
 
35
34
  def __str__(self) -> str:
36
35
  return f"{self.file_string()}{self.ref_inside_file()}"
@@ -47,8 +46,8 @@ class SourceReference(HashablePydanticBaseModel):
47
46
 
48
47
  class SourceReferencedError(pydantic.BaseModel):
49
48
  error: str
50
- source_ref: Optional[SourceReference] = None
51
- function: Optional[str] = None
49
+ source_ref: SourceReference | None = None
50
+ function: str | None = None
52
51
 
53
52
  def __str__(self) -> str:
54
53
  source_referenced_error = (
@@ -1,5 +1,4 @@
1
1
  from dataclasses import dataclass
2
- from typing import Optional, Union
3
2
 
4
3
  from classiq.interface.generator.arith import number_utils
5
4
  from classiq.interface.generator.arith.register_user_input import RegisterArithmeticInfo
@@ -23,7 +22,7 @@ class NumericAttributes:
23
22
  size: int,
24
23
  is_signed: bool,
25
24
  fraction_digits: int,
26
- bounds: Optional[tuple[float, float]] = None,
25
+ bounds: tuple[float, float] | None = None,
27
26
  trim_bounds: bool = False,
28
27
  ) -> None:
29
28
  self.size = size
@@ -108,7 +107,7 @@ class NumericAttributes:
108
107
  def from_constant(
109
108
  cls,
110
109
  value: float,
111
- machine_precision: Optional[int] = None,
110
+ machine_precision: int | None = None,
112
111
  ) -> "NumericAttributes":
113
112
  if machine_precision is not None:
114
113
  value = number_utils.limit_fraction_places(value, machine_precision)
@@ -124,7 +123,7 @@ class NumericAttributes:
124
123
  def from_quantum_scalar(
125
124
  cls,
126
125
  quantum_type: QuantumScalar,
127
- machine_precision: Optional[int] = None,
126
+ machine_precision: int | None = None,
128
127
  ) -> "NumericAttributes":
129
128
  return cls(
130
129
  size=quantum_type.size_in_bits,
@@ -137,7 +136,7 @@ class NumericAttributes:
137
136
  def from_register_arithmetic_info(
138
137
  cls,
139
138
  register: RegisterArithmeticInfo,
140
- machine_precision: Optional[int] = None,
139
+ machine_precision: int | None = None,
141
140
  ) -> "NumericAttributes":
142
141
  return cls.from_quantum_scalar(
143
142
  quantum_type=register_info_to_quantum_type(register),
@@ -147,8 +146,8 @@ class NumericAttributes:
147
146
  @classmethod
148
147
  def from_type_or_constant(
149
148
  cls,
150
- from_: Union[float, QuantumScalar, RegisterArithmeticInfo],
151
- machine_precision: Optional[int] = None,
149
+ from_: float | QuantumScalar | RegisterArithmeticInfo,
150
+ machine_precision: int | None = None,
152
151
  ) -> "NumericAttributes":
153
152
  if isinstance(from_, QuantumScalar):
154
153
  return cls.from_quantum_scalar(from_, machine_precision)
@@ -1,6 +1,5 @@
1
1
  import math
2
2
  from collections.abc import Sequence
3
- from typing import Union
4
3
 
5
4
  from classiq.interface.exceptions import ClassiqValueError
6
5
 
@@ -153,7 +152,7 @@ def compute_result_attrs_multiply(
153
152
 
154
153
  def compute_result_attrs_power(
155
154
  left: NumericAttributes,
156
- right: Union[int, float],
155
+ right: int | float,
157
156
  machine_precision: int,
158
157
  ) -> NumericAttributes:
159
158
  if not float(right).is_integer() or right <= 0:
@@ -174,7 +173,7 @@ def compute_result_attrs_power(
174
173
 
175
174
  def compute_result_attrs_lshift(
176
175
  left: NumericAttributes,
177
- right: Union[int, float],
176
+ right: int | float,
178
177
  machine_precision: int,
179
178
  ) -> NumericAttributes:
180
179
  if not float(right).is_integer() or right < 0:
@@ -196,7 +195,7 @@ def compute_result_attrs_lshift(
196
195
 
197
196
  def compute_result_attrs_rshift(
198
197
  left: NumericAttributes,
199
- right: Union[int, float],
198
+ right: int | float,
200
199
  machine_precision: int,
201
200
  ) -> NumericAttributes:
202
201
  if not float(right).is_integer() or right < 0:
@@ -219,7 +218,7 @@ def compute_result_attrs_rshift(
219
218
 
220
219
  def compute_result_attrs_modulo(
221
220
  left: NumericAttributes,
222
- right: Union[int, float],
221
+ right: int | float,
223
222
  machine_precision: int,
224
223
  ) -> NumericAttributes:
225
224
  if not float(right).is_integer() or right < 2:
@@ -1,8 +1,8 @@
1
1
  import ast
2
2
  import dataclasses
3
- from collections.abc import Sequence
3
+ from collections.abc import Callable, Sequence
4
4
  from dataclasses import dataclass, field
5
- from typing import TYPE_CHECKING, Callable, Union, cast
5
+ from typing import TYPE_CHECKING, cast
6
6
 
7
7
  from typing_extensions import Self
8
8
 
@@ -297,7 +297,7 @@ class CapturedVars:
297
297
 
298
298
  def _conjugate_direction(
299
299
  self,
300
- source_direction: Union[PortDirection, bool],
300
+ source_direction: PortDirection | bool,
301
301
  target_direction: PortDirection,
302
302
  var_name: str,
303
303
  ) -> PortDirection:
@@ -1,5 +1,4 @@
1
1
  import re
2
- from typing import Optional
3
2
 
4
3
  from classiq.interface.generator.compiler_keywords import CAPTURE_SUFFIX
5
4
  from classiq.interface.model.handle_binding import HANDLE_ID_SEPARATOR, HandleBinding
@@ -17,7 +16,7 @@ def mangle_captured_var_name(
17
16
  return f"{var_name}{CAPTURE_SUFFIX}{function_name}__{function_depth}"
18
17
 
19
18
 
20
- def _match_capture_pattern(name: str) -> Optional[re.Match[str]]:
19
+ def _match_capture_pattern(name: str) -> re.Match[str] | None:
21
20
  return re.match(CAPTURE_PATTERN, name)
22
21
 
23
22
 
@@ -2,7 +2,7 @@ import dataclasses
2
2
  from collections.abc import Sequence
3
3
  from copy import deepcopy
4
4
  from dataclasses import dataclass, field
5
- from typing import Any, Optional
5
+ from typing import Any
6
6
 
7
7
  from typing_extensions import Self
8
8
 
@@ -47,7 +47,8 @@ class FunctionClosure(Closure):
47
47
  is_lambda: bool = False
48
48
  is_atomic: bool = False
49
49
  signature_scope: Scope = field(default_factory=Scope)
50
- _depth: Optional[int] = None
50
+ permutation: bool = False
51
+ _depth: int | None = None
51
52
 
52
53
  @property
53
54
  def depth(self) -> int:
@@ -67,9 +68,9 @@ class FunctionClosure(Closure):
67
68
  cls,
68
69
  name: str,
69
70
  scope: Scope,
70
- body: Optional[Sequence[QuantumStatement]] = None,
71
+ body: Sequence[QuantumStatement] | None = None,
71
72
  positional_arg_declarations: Sequence[PositionalArg] = tuple(),
72
- lambda_external_vars: Optional[CapturedVars] = None,
73
+ lambda_external_vars: CapturedVars | None = None,
73
74
  is_atomic: bool = False,
74
75
  **kwargs: Any,
75
76
  ) -> Self:
@@ -78,13 +79,13 @@ class FunctionClosure(Closure):
78
79
  if lambda_external_vars is not None:
79
80
  captured_vars.set_parent(lambda_external_vars)
80
81
  return cls(
81
- name,
82
- blocks,
83
- scope,
84
- positional_arg_declarations,
85
- captured_vars,
86
- lambda_external_vars is not None,
87
- is_atomic,
82
+ name=name,
83
+ blocks=blocks,
84
+ scope=scope,
85
+ positional_arg_declarations=positional_arg_declarations,
86
+ captured_vars=captured_vars,
87
+ is_lambda=lambda_external_vars is not None,
88
+ is_atomic=is_atomic,
88
89
  **kwargs,
89
90
  )
90
91
 
@@ -1,7 +1,7 @@
1
1
  from collections.abc import Iterator, Sequence
2
2
  from contextlib import contextmanager
3
3
  from dataclasses import dataclass, field
4
- from typing import Generic, Optional, TypeVar
4
+ from typing import Generic, TypeVar
5
5
 
6
6
  from classiq.interface.exceptions import (
7
7
  ClassiqExpansionError,
@@ -13,6 +13,7 @@ from classiq.interface.generator.compiler_keywords import (
13
13
  )
14
14
  from classiq.interface.generator.functions.builtins.internal_operators import (
15
15
  BLOCK_OPERATOR_NAME,
16
+ SKIP_CONTROL_OPERATOR_NAME,
16
17
  WITHIN_APPLY_NAME,
17
18
  )
18
19
  from classiq.interface.model.model import MAIN_FUNCTION_NAME
@@ -39,7 +40,11 @@ from classiq.model_expansions.utils.counted_name_allocator import CountedNameAll
39
40
 
40
41
  ClosureType = TypeVar("ClosureType", bound=Closure)
41
42
 
42
- BLOCKS_ALLOWED_CAPTURING = (WITHIN_APPLY_NAME, BLOCK_OPERATOR_NAME)
43
+ BLOCKS_ALLOWED_CAPTURING = (
44
+ WITHIN_APPLY_NAME,
45
+ BLOCK_OPERATOR_NAME,
46
+ SKIP_CONTROL_OPERATOR_NAME,
47
+ )
43
48
 
44
49
 
45
50
  @dataclass
@@ -87,6 +92,10 @@ class FunctionContext(OperationContext[FunctionClosure]):
87
92
  def is_lambda(self) -> bool:
88
93
  return self.closure.is_lambda
89
94
 
95
+ @property
96
+ def permutation(self) -> bool:
97
+ return self.closure.permutation
98
+
90
99
 
91
100
  class OperationBuilder:
92
101
  def __init__(
@@ -95,7 +104,7 @@ class OperationBuilder:
95
104
  self._operations: list[OperationContext] = []
96
105
  self._blocks: list[str] = []
97
106
  self._functions_scope = functions_scope
98
- self._current_source_ref: Optional[SourceReference] = None
107
+ self._current_source_ref: SourceReference | None = None
99
108
  self._counted_name_allocator = counted_name_allocator
100
109
 
101
110
  @property
@@ -201,9 +210,7 @@ class OperationBuilder:
201
210
  parent_block.captured_vars.update(captured_vars)
202
211
 
203
212
  @contextmanager
204
- def source_ref_context(
205
- self, source_ref: Optional[SourceReference]
206
- ) -> Iterator[None]:
213
+ def source_ref_context(self, source_ref: SourceReference | None) -> Iterator[None]:
207
214
  previous_source_ref = self._current_source_ref
208
215
  self._current_source_ref = source_ref
209
216
  yield
@@ -218,6 +225,7 @@ class OperationBuilder:
218
225
  name=name,
219
226
  body=function_context.body,
220
227
  positional_arg_declarations=params,
228
+ permutation=function_context.permutation,
221
229
  )
222
230
 
223
231
  def _get_expanded_function_name(self, function_context: FunctionContext) -> str:
@@ -113,10 +113,7 @@ def translate_ast_arg_to_python_qmod(param: PositionalArg, value: Any) -> Any:
113
113
  if isinstance(param, PortDeclaration):
114
114
  return _create_qvar_for_qtype(value.quantum_type, value.handle)
115
115
  if isinstance(param, QuantumOperandDeclaration):
116
- if not param.is_list or not param.is_generative:
117
- return QTerminalCallable(param)
118
- inner_decl = param.model_copy(update={"is_list": False})
119
- return [QTerminalCallable(inner_decl, index_=idx) for idx in range(len(value))]
116
+ return QTerminalCallable(param)
120
117
  if (
121
118
  isinstance(value, QmodStructInstance)
122
119
  and not param.classical_type.is_purely_generative
@@ -1,10 +1,10 @@
1
1
  import ast
2
2
  from abc import abstractmethod
3
3
  from collections import defaultdict
4
- from collections.abc import Sequence
4
+ from collections.abc import Callable, Sequence
5
5
  from contextlib import nullcontext
6
6
  from functools import singledispatchmethod
7
- from typing import Any, Callable, cast
7
+ from typing import Any, cast
8
8
 
9
9
  from pydantic import ValidationError
10
10
 
@@ -42,9 +42,6 @@ from classiq.interface.model.quantum_statement import QuantumStatement
42
42
 
43
43
  from classiq.evaluators.classical_expression import process_scope_val
44
44
  from classiq.evaluators.qmod_annotated_expression import QmodAnnotatedExpression
45
- from classiq.evaluators.qmod_expression_visitors.qmod_expression_bwc import (
46
- QmodExpressionBwc,
47
- )
48
45
  from classiq.evaluators.qmod_expression_visitors.qmod_expression_evaluator import (
49
46
  evaluate_qmod_expression,
50
47
  )
@@ -214,7 +211,6 @@ class BaseInterpreter:
214
211
  if expression.is_evaluated():
215
212
  return Evaluated(value=expression.value.value)
216
213
  expr_ast = ast.parse(expression.expr, mode="eval").body
217
- expr_ast = QmodExpressionBwc().visit(expr_ast)
218
214
  expr_val = self._eval_expr(ast.unparse(expr_ast), treat_qnum_as_float)
219
215
  if simplify and not expr_val.has_value(expr_val.root):
220
216
  simplified_expr = simplify_qmod_expression(expr_val)
@@ -1,5 +1,5 @@
1
1
  from functools import singledispatchmethod
2
- from typing import Any, Optional
2
+ from typing import Any
3
3
 
4
4
  import numpy as np
5
5
  from numpy.random import permutation
@@ -119,9 +119,9 @@ class GenerativeInterpreter(BaseInterpreter):
119
119
  def infer_symbolic_parameters(
120
120
  self,
121
121
  functions: list[NativeFunctionDefinition],
122
- additional_signatures: Optional[
122
+ additional_signatures: None | (
123
123
  list[NamedParamsQuantumFunctionDeclaration]
124
- ] = None,
124
+ ) = None,
125
125
  ) -> None:
126
126
  pass
127
127
 
@@ -134,6 +134,7 @@ class GenerativeInterpreter(BaseInterpreter):
134
134
  function.func_decl.name or "<lambda>"
135
135
  ),
136
136
  positional_arg_declarations=function.named_func_decl.positional_arg_declarations,
137
+ permutation=function.named_func_decl.permutation,
137
138
  )
138
139
 
139
140
  closure_class: type[FunctionClosure]
@@ -152,6 +153,7 @@ class GenerativeInterpreter(BaseInterpreter):
152
153
  closure = closure_class.create(
153
154
  name=func_decl.name,
154
155
  positional_arg_declarations=func_decl.positional_arg_declarations,
156
+ permutation=func_decl.permutation,
155
157
  body=function.body,
156
158
  scope=Scope(parent=self._builder.current_scope),
157
159
  lambda_external_vars=self._builder.current_block.captured_vars,
@@ -1,4 +1,4 @@
1
- from typing import TYPE_CHECKING, Any, Union
1
+ from typing import TYPE_CHECKING, Any
2
2
 
3
3
  import sympy
4
4
 
@@ -193,7 +193,7 @@ class AllocateEmitter(Emitter[Allocate]):
193
193
 
194
194
  def _interpret_size(
195
195
  self, size: Expression, var_name: str
196
- ) -> Union[int, float, sympy.Basic, QmodAnnotatedExpression]:
196
+ ) -> int | float | sympy.Basic | QmodAnnotatedExpression:
197
197
  size_value = self._interpreter.evaluate(size).value
198
198
  if not (
199
199
  (
@@ -221,7 +221,7 @@ class AllocateEmitter(Emitter[Allocate]):
221
221
 
222
222
  def _interpret_is_signed(
223
223
  self, is_signed: Expression
224
- ) -> Union[bool, sympy.Basic, QmodAnnotatedExpression]:
224
+ ) -> bool | sympy.Basic | QmodAnnotatedExpression:
225
225
  is_signed_value = self._interpreter.evaluate(is_signed).value
226
226
  if not self._allow_symbolic_attrs and not (
227
227
  isinstance(is_signed_value, bool)
@@ -238,7 +238,7 @@ class AllocateEmitter(Emitter[Allocate]):
238
238
 
239
239
  def _interpret_fraction_digits(
240
240
  self, fraction_digits: Expression
241
- ) -> Union[int, float, sympy.Expr, QmodAnnotatedExpression]:
241
+ ) -> int | float | sympy.Expr | QmodAnnotatedExpression:
242
242
  fraction_digits_value = self._interpreter.evaluate(fraction_digits).value
243
243
  if not self._allow_symbolic_attrs and not (
244
244
  isinstance(fraction_digits_value, (int, float))
@@ -1,4 +1,4 @@
1
- from typing import TYPE_CHECKING, Optional
1
+ from typing import TYPE_CHECKING
2
2
 
3
3
  from classiq.interface.exceptions import ClassiqExpansionError
4
4
  from classiq.interface.generator.expressions.expression import Expression
@@ -111,9 +111,7 @@ class AssignmentResultProcessor(Emitter[QuantumAssignmentOperation]):
111
111
  self._assign_to_inferred_var_and_bind(op, result_type, expression_type)
112
112
  return True
113
113
 
114
- def _infer_expression_type(
115
- self, op: ArithmeticOperation
116
- ) -> Optional[QuantumScalar]:
114
+ def _infer_expression_type(self, op: ArithmeticOperation) -> QuantumScalar | None:
117
115
  expr = self._evaluate_expression(op.expression)
118
116
  expr_val = expr.value.value
119
117
  if isinstance(expr_val, QmodAnnotatedExpression):
@@ -2,7 +2,6 @@ from collections.abc import Sequence
2
2
  from itertools import chain, combinations
3
3
  from typing import (
4
4
  Generic,
5
- Optional,
6
5
  cast,
7
6
  )
8
7
  from uuid import UUID
@@ -16,9 +15,7 @@ from classiq.interface.exceptions import ClassiqExpansionError
16
15
  from classiq.interface.generator.functions.port_declaration import (
17
16
  PortDeclarationDirection,
18
17
  )
19
- from classiq.interface.generator.functions.type_modifier import TypeModifier
20
18
  from classiq.interface.generator.types.compilation_metadata import CompilationMetadata
21
- from classiq.interface.helpers.backward_compatibility import zip_strict
22
19
  from classiq.interface.helpers.text_utils import are, readable_list, s
23
20
  from classiq.interface.model.block import Block
24
21
  from classiq.interface.model.classical_parameter_declaration import (
@@ -72,8 +69,8 @@ from classiq.model_expansions.scope import (
72
69
  Scope,
73
70
  )
74
71
  from classiq.model_expansions.transformers.model_renamer import ModelRenamer
75
- from classiq.model_expansions.transformers.type_modifier_inference import (
76
- TypeModifierValidation,
72
+ from classiq.model_expansions.visitors.uncomputation_signature_inference import (
73
+ infer_and_validate_uncomputation_signature,
77
74
  )
78
75
  from classiq.qmod.pretty_print.expression_to_python import transform_expression
79
76
  from classiq.qmod.semantics.validation.signature_validation import (
@@ -106,7 +103,7 @@ def _validate_cloning(evaluated_args: list[Evaluated]) -> None:
106
103
  def _validate_gen_args(
107
104
  function: FunctionClosure, evaluated_args: list[Evaluated]
108
105
  ) -> None:
109
- for param, arg in zip_strict(
106
+ for param, arg in zip(
110
107
  function.positional_arg_declarations, evaluated_args, strict=True
111
108
  ):
112
109
  if (
@@ -158,7 +155,7 @@ class CallEmitter(Generic[QuantumStatementT], Emitter[QuantumStatementT], ModelR
158
155
  self,
159
156
  name: str,
160
157
  body: Sequence[QuantumStatement],
161
- debug_info: Optional[FunctionDebugInfo] = None,
158
+ debug_info: FunctionDebugInfo | None = None,
162
159
  ) -> QuantumFunctionCall:
163
160
  wrapping_function = FunctionClosure.create(
164
161
  name=self._counted_name_allocator.allocate(name),
@@ -172,7 +169,7 @@ class CallEmitter(Generic[QuantumStatementT], Emitter[QuantumStatementT], ModelR
172
169
  self,
173
170
  function: FunctionClosure,
174
171
  args: list[ArgValue],
175
- propagated_debug_info: Optional[FunctionDebugInfo],
172
+ propagated_debug_info: FunctionDebugInfo | None,
176
173
  ) -> QuantumFunctionCall:
177
174
  call = self._create_quantum_function_call(
178
175
  function, args, propagated_debug_info=propagated_debug_info
@@ -182,8 +179,8 @@ class CallEmitter(Generic[QuantumStatementT], Emitter[QuantumStatementT], ModelR
182
179
 
183
180
  @staticmethod
184
181
  def _get_back_ref(
185
- propagated_debug_info: Optional[FunctionDebugInfo],
186
- ) -> Optional[UUID]:
182
+ propagated_debug_info: FunctionDebugInfo | None,
183
+ ) -> UUID | None:
187
184
  if propagated_debug_info is None:
188
185
  return None
189
186
  if propagated_debug_info.node is None:
@@ -194,7 +191,7 @@ class CallEmitter(Generic[QuantumStatementT], Emitter[QuantumStatementT], ModelR
194
191
  self,
195
192
  function: FunctionClosure,
196
193
  args: list[ArgValue],
197
- propagated_debug_info: Optional[FunctionDebugInfo],
194
+ propagated_debug_info: FunctionDebugInfo | None,
198
195
  ) -> QuantumFunctionCall:
199
196
  function = function.clone()
200
197
  function = function.set_depth(self._builder.current_function.depth + 1)
@@ -218,7 +215,7 @@ class CallEmitter(Generic[QuantumStatementT], Emitter[QuantumStatementT], ModelR
218
215
  new_positional_arg_decls = new_declaration.positional_arg_declarations
219
216
  evaluated_args = [
220
217
  arg
221
- for param, arg in zip_strict(
218
+ for param, arg in zip(
222
219
  function.positional_arg_declarations, evaluated_args, strict=True
223
220
  )
224
221
  if isinstance(arg.value, QuantumVariable)
@@ -235,7 +232,7 @@ class CallEmitter(Generic[QuantumStatementT], Emitter[QuantumStatementT], ModelR
235
232
  )
236
233
  new_positional_args = [
237
234
  arg.emit(param)
238
- for param, arg in zip_strict(
235
+ for param, arg in zip(
239
236
  new_positional_arg_decls[
240
237
  : len(new_positional_arg_decls) - len(captured_args)
241
238
  ],
@@ -394,6 +391,7 @@ class CallEmitter(Generic[QuantumStatementT], Emitter[QuantumStatementT], ModelR
394
391
  function,
395
392
  evaluated_args,
396
393
  ),
394
+ permutation=function.permutation,
397
395
  )
398
396
 
399
397
  def _validate_call_args(
@@ -425,27 +423,30 @@ class CallEmitter(Generic[QuantumStatementT], Emitter[QuantumStatementT], ModelR
425
423
  def _validate_type_modifiers(
426
424
  self, func_context: FunctionContext, func_def: NativeFunctionDefinition
427
425
  ) -> None:
428
- if self._should_override_type_modifiers(func_context):
429
- self._override_type_modifiers(func_def)
430
-
431
- unchecked = self._functions_compilation_metadata.get(
426
+ compilation_metadata = self._functions_compilation_metadata.get(
432
427
  func_context.name, CompilationMetadata()
433
- ).unchecked
434
- TypeModifierValidation(
435
- skip_validation=self._interpreter.skip_type_modifier_validation
436
- ).run(func_def, unchecked)
428
+ )
429
+ infer_and_validate_uncomputation_signature(
430
+ func_def,
431
+ disable_perm_check=self._interpreter.skip_type_modifier_validation
432
+ or compilation_metadata.disable_perm_check,
433
+ disable_const_checks=self._interpreter.skip_type_modifier_validation
434
+ or compilation_metadata.disable_const_checks,
435
+ tighten_signature=self._should_tighten_signature(func_context),
436
+ )
437
437
 
438
438
  @staticmethod
439
- def _should_override_type_modifiers(func_context: FunctionContext) -> bool:
439
+ def _should_tighten_signature(func_context: FunctionContext) -> bool:
440
440
  """
441
- The type modifier can be changed according to the operand passed to the
442
- function. For example,
443
- apply_to_all(X, q) --> q will be Permutable after expansion
444
- apply_to_all(H, q) --> q will be Quantum after expansion
445
- This also holds for the intermediate lambda created during the expansion.
446
-
447
- We don't override the type modifier if it's explicitly specified (Permutable or
448
- Const), neither in the function declaration nor in the operand declaration.
441
+ In some cases we want to tighten the function signature (adding "const" or
442
+ "permutation" modifiers) when possible:
443
+ - Lambda functions (which are defined without modifiers)
444
+ - Functions which receive operands and their modifiers depend on the operand
445
+
446
+ For example:
447
+ - apply_to_all(Z, q) --> q will become `const` and the function will become `permutation`
448
+ - apply_to_all(X, q) --> the function will become `permutation`
449
+ - apply_to_all(H, q) --> no change
449
450
  """
450
451
 
451
452
  if func_context.is_lambda:
@@ -466,10 +467,3 @@ class CallEmitter(Generic[QuantumStatementT], Emitter[QuantumStatementT], ModelR
466
467
  for param_decl in orig_func.positional_arg_declarations
467
468
  )
468
469
  )
469
-
470
- @staticmethod
471
- def _override_type_modifiers(func_def: NativeFunctionDefinition) -> None:
472
- # only override the modifier if it's unspecified (not Permutable or Const)
473
- for port in func_def.port_declarations:
474
- if port.type_modifier is TypeModifier.Mutable:
475
- port.type_modifier = TypeModifier.Inferred
@@ -1,5 +1,5 @@
1
1
  from itertools import chain
2
- from typing import TYPE_CHECKING, Generic, Optional
2
+ from typing import TYPE_CHECKING, Generic
3
3
 
4
4
  from classiq.interface.generator.functions.port_declaration import (
5
5
  PortDeclarationDirection,
@@ -41,7 +41,7 @@ class DeclarativeCallEmitter(
41
41
  return True
42
42
 
43
43
  def _is_function_purely_declarative(
44
- self, function: FunctionClosure, seen_funcs: Optional[set[str]] = None
44
+ self, function: FunctionClosure, seen_funcs: set[str] | None = None
45
45
  ) -> bool:
46
46
  if seen_funcs is None:
47
47
  seen_funcs = set()
@@ -3,9 +3,7 @@ from collections.abc import Sequence
3
3
  from typing import (
4
4
  TYPE_CHECKING,
5
5
  Generic,
6
- Optional,
7
6
  TypeVar,
8
- Union,
9
7
  )
10
8
 
11
9
  from classiq.interface.debug_info.debug_info import (
@@ -113,9 +111,9 @@ class Emitter(Generic[QuantumStatementT], ABC):
113
111
  self,
114
112
  op: QuantumOperation,
115
113
  context_name: str,
116
- block_names: Union[None, str, list[str]] = None,
117
- params: Optional[Sequence[PositionalArg]] = None,
118
- scope: Optional[Scope] = None,
114
+ block_names: None | str | list[str] = None,
115
+ params: Sequence[PositionalArg] | None = None,
116
+ scope: Scope | None = None,
119
117
  ) -> OperationContext:
120
118
  if isinstance(block_names, str):
121
119
  block_names = [block_names]
@@ -1,4 +1,4 @@
1
- from typing import TYPE_CHECKING, Optional
1
+ from typing import TYPE_CHECKING
2
2
 
3
3
  from classiq.interface.exceptions import (
4
4
  ClassiqExpansionError,
@@ -24,7 +24,7 @@ class ExpressionEvaluator(Emitter[QuantumOperation]):
24
24
  interpreter: "BaseInterpreter",
25
25
  expression_name: str,
26
26
  *,
27
- readable_expression_name: Optional[str] = None,
27
+ readable_expression_name: str | None = None,
28
28
  simplify: bool = False,
29
29
  treat_qnum_as_float: bool = False,
30
30
  allow_link_time_vars: bool = True,
@@ -73,7 +73,7 @@ class ExpressionEvaluator(Emitter[QuantumOperation]):
73
73
  link_time_vars.append(var_name)
74
74
  self._capture_classical_var(var_name, var_type)
75
75
  if not self._allow_link_time_vars and len(link_time_vars) > 0:
76
- link_time_message = f"link-time variable{s(link_time_vars)} {readable_list(link_time_vars, quote=True)}"
76
+ link_time_message = f"execution parameter{s(link_time_vars)} {readable_list(link_time_vars, quote=True)}"
77
77
  else:
78
78
  link_time_message = None
79
79
  if not self._allow_runtime_vars and len(runtime_vars) > 0:
@@ -1,5 +1,4 @@
1
1
  from classiq.interface.exceptions import ClassiqExpansionError
2
- from classiq.interface.helpers.backward_compatibility import zip_strict
3
2
  from classiq.interface.model.skip_control import SkipControl
4
3
 
5
4
  from classiq.model_expansions.function_builder import FunctionContext
@@ -9,7 +8,7 @@ from classiq.model_expansions.quantum_operations.emitter import Emitter
9
8
  class SkipControlVerifier(Emitter[SkipControl]):
10
9
  def emit(self, skip_control: SkipControl, /) -> bool:
11
10
  for op, block in list(
12
- zip_strict(self._builder._operations, self._builder._blocks, strict=True)
11
+ zip(self._builder._operations, self._builder._blocks, strict=True)
13
12
  )[::-1]:
14
13
  if isinstance(op, FunctionContext):
15
14
  break