classiq 0.93.0__py3-none-any.whl → 0.94.0__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.0.dist-info}/METADATA +2 -3
  236. {classiq-0.93.0.dist-info → classiq-0.94.0.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.0.dist-info}/WHEEL +0 -0
  261. {classiq-0.93.0.dist-info → classiq-0.94.0.dist-info}/licenses/LICENSE.txt +0 -0
@@ -1,392 +0,0 @@
1
- import functools
2
- import itertools
3
- import warnings
4
- from collections.abc import Collection, Iterator, Sequence
5
- from contextlib import contextmanager
6
- from typing import Optional, Union
7
-
8
- from classiq.interface.exceptions import (
9
- ClassiqDeprecationWarning,
10
- ClassiqInternalExpansionError,
11
- )
12
- from classiq.interface.generator.functions.port_declaration import (
13
- PortDeclarationDirection,
14
- )
15
- from classiq.interface.generator.functions.type_modifier import TypeModifier
16
- from classiq.interface.model.allocate import Allocate
17
- from classiq.interface.model.bind_operation import BindOperation
18
- from classiq.interface.model.block import Block
19
- from classiq.interface.model.control import Control
20
- from classiq.interface.model.invert import Invert
21
- from classiq.interface.model.model_visitor import ModelVisitor
22
- from classiq.interface.model.native_function_definition import NativeFunctionDefinition
23
- from classiq.interface.model.phase_operation import PhaseOperation
24
- from classiq.interface.model.port_declaration import PortDeclaration
25
- from classiq.interface.model.power import Power
26
- from classiq.interface.model.quantum_expressions.amplitude_loading_operation import (
27
- AmplitudeLoadingOperation,
28
- )
29
- from classiq.interface.model.quantum_expressions.arithmetic_operation import (
30
- ArithmeticOperation,
31
- )
32
- from classiq.interface.model.quantum_expressions.quantum_expression import (
33
- QuantumExpressionOperation,
34
- )
35
- from classiq.interface.model.quantum_function_call import QuantumFunctionCall
36
- from classiq.interface.model.within_apply_operation import WithinApply
37
- from classiq.interface.source_reference import SourceReference
38
-
39
- from classiq.evaluators.qmod_annotated_expression import QmodAnnotatedExpression
40
-
41
-
42
- def _inconsistent_type_modifier_error(
43
- port_name: str,
44
- expected: TypeModifier,
45
- actual: TypeModifier,
46
- source_ref: Optional[Union[SourceReference, str]] = None,
47
- ) -> str:
48
- source_ref_str = f"\n\tat {source_ref}" if source_ref else ""
49
- return (
50
- f"The use of variable '{port_name}' does not conform to its declared modifier: "
51
- f"expected '{expected.name}', but found '{actual.name}'.\n"
52
- f"Tip: If the cumulative use of the variable in the function matches '{expected.name}', "
53
- f"use the `unchecked` flag to instruct the compiler to disregard individual operations."
54
- f"{source_ref_str}\n"
55
- "The deprecation warning will be elevated to an error starting July 23, 2025, at the earliest."
56
- )
57
-
58
-
59
- def _inconsistent_type_modifier_in_binding_error(
60
- expected: TypeModifier,
61
- known_modifiers: dict[str, TypeModifier],
62
- source_ref: Optional[Union[SourceReference, str]] = None,
63
- ) -> str:
64
- actual = ", ".join(
65
- f"{name}: {modifier.name}" for name, modifier in known_modifiers.items()
66
- )
67
- source_ref_str = f"\n\tat {source_ref}" if source_ref else ""
68
- return (
69
- f"Inconsistent modifiers in variable binding: "
70
- f"Expected modifier: {expected.name}, Actual modifiers: {actual}"
71
- f"{source_ref_str}\n"
72
- "The deprecation warning will be elevated to an error starting July 23, 2025, at the earliest."
73
- )
74
-
75
-
76
- class TypeModifierValidation(ModelVisitor):
77
- """
78
- This class assumes that function calls are topologically sorted, so it traverses
79
- the list of function calls and infers the type modifiers for each function call
80
- without going recursively into the function calls.
81
- The function definition ports are modified inplace.
82
- """
83
-
84
- def __init__(
85
- self, *, skip_validation: bool = False, support_unused_ports: bool = True
86
- ) -> None:
87
- self._signature_ports: dict[str, PortDeclaration] = dict()
88
- self._inferred_ports: dict[str, PortDeclaration] = dict()
89
- self._unchecked: set[str] = set()
90
-
91
- self._initialized_vars: dict[str, TypeModifier] = dict()
92
- self._bound_vars: list[set[str]] = []
93
-
94
- self._conjugation_context: bool = False
95
- self._support_unused_ports = (
96
- support_unused_ports # could be turned off for debugging
97
- )
98
- self._skip_validation = skip_validation
99
- self._source_ref: Optional[Union[SourceReference, str]] = None
100
-
101
- @contextmanager
102
- def validate_ports(
103
- self, ports: Collection[PortDeclaration], unchecked: Collection[str]
104
- ) -> Iterator[bool]:
105
- for port in ports:
106
- if port.type_modifier is TypeModifier.Inferred:
107
- self._inferred_ports[port.name] = port
108
- else:
109
- self._signature_ports[port.name] = port
110
- self._unchecked.update(unchecked)
111
-
112
- yield len(self._inferred_ports) > 0 or (
113
- any(
114
- port.type_modifier is not TypeModifier.Mutable
115
- for port in self._signature_ports.values()
116
- )
117
- and not self._skip_validation
118
- )
119
-
120
- self._set_unused_as_const()
121
- self._signature_ports.clear()
122
- self._inferred_ports.clear()
123
- self._unchecked.clear()
124
-
125
- @contextmanager
126
- def conjugation_context(self) -> Iterator[None]:
127
- previous_context = self._conjugation_context
128
- self._conjugation_context = True
129
- try:
130
- yield
131
- finally:
132
- self._conjugation_context = previous_context
133
-
134
- @contextmanager
135
- def source_reference_context(
136
- self, source_ref: Optional[Union[SourceReference, str]]
137
- ) -> Iterator[None]:
138
- previous_source_ref = self._source_ref
139
- self._source_ref = source_ref
140
- try:
141
- yield
142
- finally:
143
- self._source_ref = previous_source_ref
144
-
145
- def _set_unused_as_const(self) -> None:
146
- unresolved_ports = [
147
- port
148
- for port in self._inferred_ports.values()
149
- if port.type_modifier is TypeModifier.Inferred
150
- ]
151
- if not self._support_unused_ports and len(unresolved_ports) > 0:
152
- raise ClassiqInternalExpansionError(
153
- f"Unresolved inferred ports detected: {', '.join(port.name for port in unresolved_ports)}. "
154
- "All ports must have their type modifiers resolved."
155
- )
156
- for port in unresolved_ports:
157
- port.type_modifier = TypeModifier.Const
158
-
159
- def _validate_modifier(self, candidate: str, modifier: TypeModifier) -> None:
160
- if self._conjugation_context and modifier is TypeModifier.Permutable:
161
- modifier = TypeModifier.Const
162
-
163
- if candidate in self._inferred_ports:
164
- self._inferred_ports[candidate].type_modifier = TypeModifier.and_(
165
- self._inferred_ports[candidate].type_modifier, modifier
166
- )
167
- return
168
-
169
- if self._skip_validation or candidate in self._unchecked:
170
- return
171
-
172
- if candidate in self._signature_ports:
173
- self._validate_signature_modifier(candidate, modifier)
174
-
175
- elif candidate in self._initialized_vars:
176
- self._initialized_vars[candidate] = TypeModifier.and_(
177
- self._initialized_vars[candidate], modifier
178
- )
179
-
180
- def _validate_signature_modifier(
181
- self, candidate: str, modifier: TypeModifier
182
- ) -> None:
183
- signature_modifier = self._signature_ports[candidate].type_modifier
184
- if signature_modifier is not TypeModifier.and_(signature_modifier, modifier):
185
- warnings.warn(
186
- _inconsistent_type_modifier_error(
187
- candidate, signature_modifier, modifier, self._source_ref
188
- ),
189
- ClassiqDeprecationWarning,
190
- stacklevel=1,
191
- )
192
-
193
- def _add_initialized_modifier(self, var: str, modifier: TypeModifier) -> None:
194
- if var in self._inferred_ports or var in self._signature_ports:
195
- return
196
- if self._conjugation_context and modifier is TypeModifier.Permutable:
197
- modifier = TypeModifier.Const
198
- self._initialized_vars[var] = modifier
199
-
200
- def run(
201
- self,
202
- func_def: NativeFunctionDefinition,
203
- unchecked: Collection[str],
204
- ) -> None:
205
- with (
206
- self.validate_ports(
207
- func_def.port_declarations, unchecked
208
- ) as should_validate,
209
- self.source_reference_context(f"function '{func_def.name}'"),
210
- ):
211
- if should_validate:
212
- self.visit(func_def.body)
213
- self._update_bound_vars()
214
-
215
- def _update_bound_vars(self) -> None:
216
- merged_bound_vars = _merge_overlapping(self._bound_vars)
217
- for bound_vars in merged_bound_vars:
218
- reduced_modifier = self._get_reduced_modifier(bound_vars)
219
- for var in bound_vars:
220
- self._validate_modifier(var, reduced_modifier)
221
-
222
- def visit_QuantumFunctionCall(self, call: QuantumFunctionCall) -> None:
223
- with self.source_reference_context(call.source_ref):
224
- for handle, port in call.handles_with_params:
225
- self._validate_modifier(handle.name, port.type_modifier)
226
- if port.direction is PortDeclarationDirection.Output:
227
- self._add_initialized_modifier(handle.name, port.type_modifier)
228
-
229
- if self._has_inputs(call):
230
- bound_vars = {
231
- handle.name
232
- for handle, port in call.handles_with_params
233
- if port.direction is not PortDeclarationDirection.Inout
234
- and handle.name not in self._unchecked
235
- }
236
- self._bound_vars.append(bound_vars)
237
-
238
- @staticmethod
239
- def _has_inputs(call: QuantumFunctionCall) -> bool:
240
- return any(
241
- port.direction is PortDeclarationDirection.Input
242
- for _, port in call.handles_with_params
243
- )
244
-
245
- def visit_Allocate(self, alloc: Allocate) -> None:
246
- with self.source_reference_context(alloc.source_ref):
247
- self._validate_modifier(alloc.target.name, TypeModifier.Permutable)
248
- self._add_initialized_modifier(alloc.target.name, TypeModifier.Permutable)
249
-
250
- def visit_BindOperation(self, bind_op: BindOperation) -> None:
251
- var_names = {
252
- handle.name
253
- for handle in itertools.chain(bind_op.in_handles, bind_op.out_handles)
254
- if handle.name not in self._unchecked
255
- }
256
- self._bound_vars.append(var_names)
257
- for handle in bind_op.out_handles:
258
- self._add_initialized_modifier(handle.name, TypeModifier.Inferred)
259
-
260
- def _get_reduced_modifier(self, bound_vars: set[str]) -> TypeModifier:
261
- signature_modifiers = {
262
- name: self._signature_ports[name].type_modifier
263
- for name in bound_vars.intersection(self._signature_ports)
264
- }
265
- known_inferred_modifiers = {
266
- name: self._inferred_ports[name].type_modifier
267
- for name in bound_vars.intersection(self._inferred_ports)
268
- if self._inferred_ports[name].type_modifier is not TypeModifier.Inferred
269
- }
270
- known_initialized_modifiers = {
271
- name: self._initialized_vars[name]
272
- for name in bound_vars.intersection(self._initialized_vars)
273
- if self._initialized_vars[name] is not TypeModifier.Inferred
274
- }
275
- known_modifiers = (
276
- signature_modifiers | known_inferred_modifiers | known_initialized_modifiers
277
- )
278
- min_modifier = self._get_min_modifier(list(known_modifiers.values()))
279
- if not all(
280
- type_modifier is min_modifier
281
- for type_modifier in signature_modifiers.values()
282
- ):
283
- warnings.warn(
284
- _inconsistent_type_modifier_in_binding_error(
285
- min_modifier, known_modifiers, self._source_ref
286
- ),
287
- ClassiqDeprecationWarning,
288
- stacklevel=1,
289
- )
290
-
291
- return min_modifier
292
-
293
- @staticmethod
294
- def _get_min_modifier(modifiers: list[TypeModifier]) -> TypeModifier:
295
- if len(modifiers) == 0:
296
- return TypeModifier.Const
297
- elif len(modifiers) == 1:
298
- return modifiers[0]
299
- else:
300
- return functools.reduce(TypeModifier.and_, modifiers)
301
-
302
- @staticmethod
303
- def _extract_expr_vars(expr_op: QuantumExpressionOperation) -> list[str]:
304
- expr_val = expr_op.expression.value.value
305
- if not isinstance(expr_val, QmodAnnotatedExpression):
306
- return []
307
- return list(
308
- dict.fromkeys(var.name for var in expr_val.get_quantum_vars().values())
309
- )
310
-
311
- def visit_ArithmeticOperation(self, arith: ArithmeticOperation) -> None:
312
- with self.source_reference_context(arith.source_ref):
313
- result_var = arith.result_var.name
314
- self._validate_modifier(result_var, TypeModifier.Permutable)
315
- for expr_var in self._extract_expr_vars(arith):
316
- self._validate_modifier(expr_var, TypeModifier.Const)
317
- if not arith.is_inplace:
318
- self._add_initialized_modifier(result_var, TypeModifier.Permutable)
319
-
320
- def visit_AmplitudeLoadingOperation(
321
- self, amp_load: AmplitudeLoadingOperation
322
- ) -> None:
323
- with self.source_reference_context(amp_load.source_ref):
324
- result_var = amp_load.result_var.name
325
- self._validate_modifier(result_var, TypeModifier.Mutable)
326
- for expr_var in self._extract_expr_vars(amp_load):
327
- self._validate_modifier(expr_var, TypeModifier.Const)
328
-
329
- def visit_PhaseOperation(self, phase_op: PhaseOperation) -> None:
330
- with self.source_reference_context(phase_op.source_ref):
331
- for expr_var in self._extract_expr_vars(phase_op):
332
- self._validate_modifier(expr_var, TypeModifier.Const)
333
-
334
- def visit_Control(self, control: Control) -> None:
335
- with self.source_reference_context(control.source_ref):
336
- for control_var in self._extract_expr_vars(control):
337
- self._validate_modifier(control_var, TypeModifier.Const)
338
- self.visit(control.body)
339
- if control.else_block is not None:
340
- self.visit(control.else_block)
341
-
342
- def visit_Invert(self, invert: Invert) -> None:
343
- with self.source_reference_context(invert.source_ref):
344
- self.visit(invert.body)
345
-
346
- def visit_Power(self, power: Power) -> None:
347
- with self.source_reference_context(power.source_ref):
348
- self.visit(power.body)
349
-
350
- def visit_WithinApply(self, within_apply: WithinApply) -> None:
351
- with self.source_reference_context(within_apply.source_ref):
352
- with self.conjugation_context():
353
- self.visit(within_apply.compute)
354
- self.visit(within_apply.action)
355
-
356
- def visit_Block(self, block: Block) -> None:
357
- with self.source_reference_context(block.source_ref):
358
- self.visit(block.statements)
359
-
360
-
361
- def _merge_overlapping(bound_vars: Sequence[Collection[str]]) -> list[set[str]]:
362
- """
363
- Merges overlapping sets of bound variables.
364
- Two sets overlap if they share at least one variable.
365
- """
366
- all_bound_vars = bound_vars
367
- merged_bound_vars: list[set[str]] = []
368
- loop_guard: int = 10
369
- idx: int = 0
370
-
371
- for _ in range(loop_guard):
372
- idx += 1
373
-
374
- merged_bound_vars = []
375
- modified: bool = False
376
- for current_bound_vars in all_bound_vars:
377
- for existing in merged_bound_vars:
378
- if existing.intersection(current_bound_vars):
379
- existing.update(current_bound_vars)
380
- modified = True
381
- break
382
- else:
383
- merged_bound_vars.append(set(current_bound_vars))
384
-
385
- if not modified:
386
- break
387
- all_bound_vars = merged_bound_vars
388
-
389
- if idx == loop_guard - 1:
390
- raise ClassiqInternalExpansionError
391
-
392
- return merged_bound_vars
@@ -1,123 +0,0 @@
1
- import warnings
2
-
3
- from classiq.interface.exceptions import ClassiqDeprecationWarning
4
-
5
- from classiq.qmod.builtins.structs import (
6
- FockHamiltonianProblem,
7
- MoleculeProblem,
8
- )
9
- from classiq.qmod.qfunc import qfunc
10
- from classiq.qmod.qmod_parameter import CArray, CInt
11
- from classiq.qmod.qmod_variable import QArray, QBit
12
-
13
-
14
- @qfunc(external=True)
15
- def molecule_ucc(
16
- molecule_problem: MoleculeProblem,
17
- excitations: CArray[CInt],
18
- qbv: QArray[QBit],
19
- ) -> None:
20
- warnings.warn(
21
- (
22
- "The function `molecule_ucc` is deprecated and will no "
23
- "longer be supported starting on 2025-09-18 at the earliest. "
24
- "For more information on Classiq's chemistry application, see "
25
- "https://docs.classiq.io/latest/explore/applications/chemistry/classiq_chemistry_application/classiq_chemistry_application/."
26
- ),
27
- category=ClassiqDeprecationWarning,
28
- stacklevel=2,
29
- )
30
- pass
31
-
32
-
33
- @qfunc(external=True)
34
- def molecule_hva(
35
- molecule_problem: MoleculeProblem,
36
- reps: CInt,
37
- qbv: QArray[QBit],
38
- ) -> None:
39
- warnings.warn(
40
- (
41
- "The function `molecule_hva` is deprecated and will no "
42
- "longer be supported starting on 2025-09-18 at the earliest. "
43
- "For more information on Classiq's chemistry application, see "
44
- "https://docs.classiq.io/latest/explore/applications/chemistry/classiq_chemistry_application/classiq_chemistry_application/."
45
- ),
46
- category=ClassiqDeprecationWarning,
47
- stacklevel=2,
48
- )
49
- pass
50
-
51
-
52
- @qfunc(external=True)
53
- def molecule_hartree_fock(
54
- molecule_problem: MoleculeProblem,
55
- qbv: QArray[QBit],
56
- ) -> None:
57
- warnings.warn(
58
- (
59
- "The function `molecule_hartree_fock` is deprecated and will no "
60
- "longer be supported starting on 2025-09-18 at the earliest. "
61
- "For more information on Classiq's chemistry application, see "
62
- "https://docs.classiq.io/latest/explore/applications/chemistry/classiq_chemistry_application/classiq_chemistry_application/."
63
- ),
64
- category=ClassiqDeprecationWarning,
65
- stacklevel=2,
66
- )
67
- pass
68
-
69
-
70
- @qfunc(external=True)
71
- def fock_hamiltonian_ucc(
72
- fock_hamiltonian_problem: FockHamiltonianProblem,
73
- excitations: CArray[CInt],
74
- qbv: QArray[QBit],
75
- ) -> None:
76
- warnings.warn(
77
- (
78
- "The function `fock_hamiltonian_ucc` is deprecated and will no "
79
- "longer be supported starting on 2025-09-18 at the earliest. "
80
- "For more information on Classiq's chemistry application, see "
81
- "https://docs.classiq.io/latest/explore/applications/chemistry/classiq_chemistry_application/classiq_chemistry_application/."
82
- ),
83
- category=ClassiqDeprecationWarning,
84
- stacklevel=2,
85
- )
86
- pass
87
-
88
-
89
- @qfunc(external=True)
90
- def fock_hamiltonian_hva(
91
- fock_hamiltonian_problem: FockHamiltonianProblem,
92
- reps: CInt,
93
- qbv: QArray[QBit],
94
- ) -> None:
95
- warnings.warn(
96
- (
97
- "The function `fock_hamiltonian_hva` is deprecated and will no "
98
- "longer be supported starting on 2025-09-18 at the earliest. "
99
- "For more information on Classiq's chemistry application, see "
100
- "https://docs.classiq.io/latest/explore/applications/chemistry/classiq_chemistry_application/classiq_chemistry_application/."
101
- ),
102
- category=ClassiqDeprecationWarning,
103
- stacklevel=2,
104
- )
105
- pass
106
-
107
-
108
- @qfunc(external=True)
109
- def fock_hamiltonian_hartree_fock(
110
- fock_hamiltonian_problem: FockHamiltonianProblem,
111
- qbv: QArray[QBit],
112
- ) -> None:
113
- warnings.warn(
114
- (
115
- "The function `fock_hamiltonian_hartree_fock` is deprecated and will no "
116
- "longer be supported starting on 2025-09-18 at the earliest. "
117
- "For more information on Classiq's chemistry application, see "
118
- "https://docs.classiq.io/latest/explore/applications/chemistry/classiq_chemistry_application/classiq_chemistry_application/."
119
- ),
120
- category=ClassiqDeprecationWarning,
121
- stacklevel=2,
122
- )
123
- pass