classiq 0.53.0__py3-none-any.whl → 0.54.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.
- classiq/__init__.py +1 -3
- classiq/_analyzer_extras/_ipywidgets_async_extension.py +2 -1
- classiq/_internals/__init__.py +0 -20
- classiq/_internals/api_wrapper.py +8 -8
- classiq/_internals/async_utils.py +1 -3
- classiq/_internals/authentication/auth0.py +5 -5
- classiq/_internals/authentication/device.py +5 -4
- classiq/_internals/authentication/password_manager.py +3 -3
- classiq/_internals/authentication/token_manager.py +3 -2
- classiq/_internals/client.py +10 -12
- classiq/_internals/config.py +2 -2
- classiq/_internals/jobs.py +7 -6
- classiq/_internals/type_validation.py +9 -9
- classiq/analyzer/__init__.py +1 -3
- classiq/analyzer/analyzer.py +8 -7
- classiq/analyzer/analyzer_utilities.py +8 -8
- classiq/analyzer/rb.py +11 -11
- classiq/applications/__init__.py +1 -3
- classiq/applications/chemistry/__init__.py +1 -3
- classiq/applications/chemistry/ansatz_parameters.py +4 -4
- classiq/applications/chemistry/chemistry_model_constructor.py +10 -9
- classiq/applications/combinatorial_helpers/combinatorial_problem_utils.py +26 -9
- classiq/applications/combinatorial_helpers/encoding_mapping.py +10 -10
- classiq/applications/combinatorial_helpers/encoding_utils.py +4 -4
- classiq/applications/combinatorial_helpers/memory.py +5 -7
- classiq/applications/combinatorial_helpers/optimization_model.py +43 -24
- classiq/applications/combinatorial_helpers/pauli_helpers/pauli_utils.py +4 -6
- classiq/applications/combinatorial_helpers/pyomo_utils.py +95 -24
- classiq/applications/combinatorial_helpers/sympy_utils.py +2 -2
- classiq/applications/combinatorial_helpers/transformations/encoding.py +8 -8
- classiq/applications/combinatorial_helpers/transformations/fixed_variables.py +5 -5
- classiq/applications/combinatorial_helpers/transformations/ising_converter.py +7 -9
- classiq/applications/combinatorial_helpers/transformations/penalty.py +1 -2
- classiq/applications/combinatorial_helpers/transformations/sign_seperation.py +1 -2
- classiq/applications/combinatorial_helpers/transformations/slack_variables.py +1 -2
- classiq/applications/combinatorial_optimization/__init__.py +1 -3
- classiq/applications/combinatorial_optimization/combinatorial_optimization_config.py +2 -2
- classiq/applications/combinatorial_optimization/examples/__init__.py +1 -3
- classiq/applications/finance/__init__.py +1 -3
- classiq/applications/grover/__init__.py +1 -3
- classiq/applications/grover/grover_model_constructor.py +7 -9
- classiq/applications/hamiltonian/pauli_decomposition.py +6 -6
- classiq/applications/qnn/__init__.py +1 -3
- classiq/applications/qnn/circuit_utils.py +5 -5
- classiq/applications/qnn/datasets/__init__.py +1 -3
- classiq/applications/qnn/datasets/dataset_base_classes.py +5 -4
- classiq/applications/qnn/datasets/dataset_parity.py +2 -2
- classiq/applications/qnn/gradients/simple_quantum_gradient.py +2 -1
- classiq/applications/qnn/qlayer.py +3 -3
- classiq/applications/qnn/torch_utils.py +2 -2
- classiq/applications/qnn/types.py +5 -5
- classiq/applications/qsvm/qsvm.py +1 -3
- classiq/applications/qsvm/qsvm_data_generation.py +3 -3
- classiq/applications/qsvm/qsvm_model_constructor.py +5 -5
- classiq/execution/__init__.py +1 -3
- classiq/execution/all_hardware_devices.py +1 -3
- classiq/execution/execution_session.py +16 -16
- classiq/execution/jobs.py +4 -4
- classiq/execution/qaoa.py +3 -3
- classiq/execution/qnn.py +3 -3
- classiq/executor.py +3 -3
- classiq/interface/_version.py +1 -1
- classiq/interface/analyzer/analysis_params.py +9 -10
- classiq/interface/analyzer/cytoscape_graph.py +5 -5
- classiq/interface/analyzer/result.py +17 -17
- classiq/interface/applications/qsvm.py +6 -10
- classiq/interface/backend/backend_preferences.py +4 -3
- classiq/interface/backend/ionq/ionq_quantum_program.py +4 -5
- classiq/interface/backend/pydantic_backend.py +1 -2
- classiq/interface/chemistry/fermionic_operator.py +5 -5
- classiq/interface/chemistry/ground_state_problem.py +7 -8
- classiq/interface/chemistry/molecule.py +4 -4
- classiq/interface/chemistry/operator.py +11 -13
- classiq/interface/combinatorial_optimization/examples/ascending_sequence.py +1 -3
- classiq/interface/combinatorial_optimization/examples/integer_portfolio_optimization.py +2 -4
- classiq/interface/combinatorial_optimization/examples/knapsack.py +3 -3
- classiq/interface/combinatorial_optimization/examples/mht.py +2 -3
- classiq/interface/combinatorial_optimization/examples/portfolio_variations.py +2 -2
- classiq/interface/combinatorial_optimization/examples/set_cover.py +1 -2
- classiq/interface/combinatorial_optimization/mht_qaoa_input.py +5 -7
- classiq/interface/combinatorial_optimization/optimization_problem.py +2 -2
- classiq/interface/combinatorial_optimization/result.py +1 -3
- classiq/interface/debug_info/debug_info.py +8 -7
- classiq/interface/exceptions.py +8 -6
- classiq/interface/execution/jobs.py +2 -2
- classiq/interface/execution/primitives.py +3 -3
- classiq/interface/executor/aws_execution_cost.py +4 -4
- classiq/interface/executor/execution_request.py +2 -3
- classiq/interface/executor/execution_result.py +3 -3
- classiq/interface/executor/iqae_result.py +3 -5
- classiq/interface/executor/optimizer_preferences.py +2 -2
- classiq/interface/executor/quantum_code.py +6 -6
- classiq/interface/executor/register_initialization.py +2 -4
- classiq/interface/executor/result.py +23 -27
- classiq/interface/executor/vqe_result.py +8 -8
- classiq/interface/finance/function_input.py +2 -2
- classiq/interface/finance/gaussian_model_input.py +5 -5
- classiq/interface/finance/log_normal_model_input.py +2 -2
- classiq/interface/finance/model_input.py +1 -2
- classiq/interface/generator/adjacency.py +1 -3
- classiq/interface/generator/ansatz_library.py +4 -4
- classiq/interface/generator/application_apis/finance_declarations.py +1 -1
- classiq/interface/generator/arith/argument_utils.py +3 -3
- classiq/interface/generator/arith/arithmetic.py +7 -7
- classiq/interface/generator/arith/arithmetic_arg_type_validator.py +5 -5
- classiq/interface/generator/arith/arithmetic_expression_abc.py +11 -11
- classiq/interface/generator/arith/arithmetic_expression_parser.py +8 -7
- classiq/interface/generator/arith/arithmetic_expression_validator.py +8 -8
- classiq/interface/generator/arith/arithmetic_operations.py +4 -3
- classiq/interface/generator/arith/arithmetic_param_getters.py +6 -6
- classiq/interface/generator/arith/arithmetic_result_builder.py +9 -9
- classiq/interface/generator/arith/ast_node_rewrite.py +2 -1
- classiq/interface/generator/arith/binary_ops.py +10 -13
- classiq/interface/generator/arith/extremum_operations.py +3 -2
- classiq/interface/generator/arith/logical_ops.py +7 -6
- classiq/interface/generator/arith/number_utils.py +4 -4
- classiq/interface/generator/arith/register_user_input.py +4 -4
- classiq/interface/generator/arith/unary_ops.py +2 -1
- classiq/interface/generator/builtin_api_builder.py +2 -1
- classiq/interface/generator/circuit_code/circuit_code.py +4 -4
- classiq/interface/generator/circuit_code/types_and_constants.py +3 -5
- classiq/interface/generator/complex_type.py +1 -2
- classiq/interface/generator/control_state.py +2 -2
- classiq/interface/generator/custom_ansatz.py +1 -3
- classiq/interface/generator/distance.py +3 -5
- classiq/interface/generator/excitations.py +3 -2
- classiq/interface/generator/expressions/enums/finance_functions.py +1 -3
- classiq/interface/generator/expressions/evaluated_expression.py +4 -3
- classiq/interface/generator/expressions/expression.py +4 -5
- classiq/interface/generator/expressions/expression_constants.py +4 -4
- classiq/interface/generator/expressions/qmod_qarray_proxy.py +2 -1
- classiq/interface/generator/expressions/qmod_qscalar_proxy.py +2 -1
- classiq/interface/generator/expressions/qmod_qstruct_proxy.py +2 -1
- classiq/interface/generator/expressions/qmod_sized_proxy.py +2 -1
- classiq/interface/generator/expressions/qmod_struct_instance.py +2 -1
- classiq/interface/generator/expressions/sympy_supported_expressions.py +11 -13
- classiq/interface/generator/finance.py +2 -2
- classiq/interface/generator/function_param_library.py +6 -6
- classiq/interface/generator/function_params.py +13 -19
- classiq/interface/generator/functions/classical_function_declaration.py +4 -3
- classiq/interface/generator/functions/classical_type.py +13 -13
- classiq/interface/generator/functions/concrete_types.py +1 -2
- classiq/interface/generator/functions/function_declaration.py +1 -1
- classiq/interface/generator/functions/qmod_python_interface.py +2 -1
- classiq/interface/generator/functions/type_name.py +3 -2
- classiq/interface/generator/generated_circuit_data.py +34 -22
- classiq/interface/generator/grover_diffuser.py +7 -7
- classiq/interface/generator/grover_operator.py +2 -2
- classiq/interface/generator/hardware/hardware_data.py +7 -6
- classiq/interface/generator/hardware_efficient_ansatz.py +8 -8
- classiq/interface/generator/identity.py +5 -6
- classiq/interface/generator/linear_pauli_rotations.py +6 -6
- classiq/interface/generator/mcu.py +2 -2
- classiq/interface/generator/mcx.py +6 -6
- classiq/interface/generator/model/__init__.py +1 -3
- classiq/interface/generator/model/constraints.py +2 -2
- classiq/interface/generator/model/model.py +5 -6
- classiq/interface/generator/model/preferences/preferences.py +7 -6
- classiq/interface/generator/model/quantum_register.py +6 -11
- classiq/interface/generator/oracles/arithmetic_oracle.py +1 -2
- classiq/interface/generator/oracles/custom_oracle.py +2 -2
- classiq/interface/generator/oracles/oracle_abc.py +6 -5
- classiq/interface/generator/partitioned_register.py +6 -5
- classiq/interface/generator/piecewise_linear_amplitude_loading.py +8 -7
- classiq/interface/generator/qpe.py +4 -4
- classiq/interface/generator/qsvm.py +3 -3
- classiq/interface/generator/quantum_function_call.py +24 -29
- classiq/interface/generator/quantum_program.py +9 -9
- classiq/interface/generator/register_role.py +2 -4
- classiq/interface/generator/slice_parsing_utils.py +4 -3
- classiq/interface/generator/standard_gates/standard_gates.py +3 -3
- classiq/interface/generator/state_preparation/bell_state_preparation.py +3 -3
- classiq/interface/generator/state_preparation/distributions.py +6 -5
- classiq/interface/generator/state_preparation/metrics.py +2 -4
- classiq/interface/generator/state_preparation/state_preparation.py +4 -4
- classiq/interface/generator/synthesis_metadata/synthesis_execution_data.py +3 -3
- classiq/interface/generator/transpiler_basis_gates.py +2 -2
- classiq/interface/generator/types/enum_declaration.py +2 -3
- classiq/interface/generator/types/qstruct_declaration.py +2 -1
- classiq/interface/generator/types/struct_declaration.py +3 -2
- classiq/interface/generator/ucc.py +2 -1
- classiq/interface/generator/unitary_gate.py +2 -2
- classiq/interface/generator/user_defined_function_params.py +1 -1
- classiq/interface/generator/validations/flow_graph.py +6 -5
- classiq/interface/generator/validations/validator_functions.py +3 -2
- classiq/interface/generator/visitor.py +9 -14
- classiq/interface/hardware.py +5 -6
- classiq/interface/helpers/custom_encoders.py +2 -2
- classiq/interface/helpers/custom_pydantic_types.py +8 -9
- classiq/interface/helpers/hashable_mixin.py +3 -2
- classiq/interface/helpers/hashable_pydantic_base_model.py +2 -1
- classiq/interface/helpers/pydantic_model_helpers.py +4 -3
- classiq/interface/helpers/validation_helpers.py +2 -2
- classiq/interface/ide/ide_data.py +11 -15
- classiq/interface/ide/visual_model.py +20 -22
- classiq/interface/jobs.py +2 -2
- classiq/interface/model/bind_operation.py +5 -4
- classiq/interface/model/classical_parameter_declaration.py +2 -2
- classiq/interface/model/handle_binding.py +3 -2
- classiq/interface/model/inplace_binary_operation.py +2 -1
- classiq/interface/model/model.py +12 -11
- classiq/interface/model/port_declaration.py +2 -2
- classiq/interface/model/quantum_expressions/amplitude_loading_operation.py +3 -2
- classiq/interface/model/quantum_expressions/arithmetic_operation.py +3 -2
- classiq/interface/model/quantum_expressions/quantum_expression.py +8 -7
- classiq/interface/model/quantum_function_call.py +9 -14
- classiq/interface/model/quantum_function_declaration.py +10 -12
- classiq/interface/model/quantum_lambda_function.py +3 -16
- classiq/interface/model/quantum_statement.py +4 -3
- classiq/interface/model/quantum_type.py +5 -5
- classiq/interface/model/statement_block.py +2 -3
- classiq/interface/model/validation_handle.py +5 -4
- classiq/interface/server/global_versions.py +3 -3
- classiq/model_expansions/atomic_expression_functions_defs.py +3 -2
- classiq/model_expansions/call_to_model_converter.py +190 -0
- classiq/model_expansions/capturing/captured_var_manager.py +4 -6
- classiq/model_expansions/capturing/propagated_var_stack.py +7 -7
- classiq/model_expansions/closure.py +17 -9
- classiq/model_expansions/evaluators/arg_type_match.py +3 -2
- classiq/model_expansions/evaluators/argument_types.py +3 -3
- classiq/model_expansions/evaluators/control.py +3 -3
- classiq/model_expansions/evaluators/parameter_types.py +7 -7
- classiq/model_expansions/evaluators/quantum_type_utils.py +2 -1
- classiq/model_expansions/evaluators/type_type_match.py +1 -1
- classiq/model_expansions/expression_evaluator.py +10 -9
- classiq/model_expansions/expression_renamer.py +6 -6
- classiq/model_expansions/function_builder.py +19 -12
- classiq/model_expansions/generative_functions.py +3 -2
- classiq/model_expansions/interpreter.py +31 -19
- classiq/model_expansions/model_tables.py +14 -14
- classiq/model_expansions/quantum_operations/bind.py +2 -4
- classiq/model_expansions/quantum_operations/classicalif.py +1 -1
- classiq/model_expansions/quantum_operations/control.py +2 -4
- classiq/model_expansions/quantum_operations/emitter.py +10 -13
- classiq/model_expansions/quantum_operations/expression_operation.py +23 -16
- classiq/model_expansions/quantum_operations/inplace_binary_operation.py +160 -35
- classiq/model_expansions/quantum_operations/phase.py +6 -6
- classiq/model_expansions/quantum_operations/quantum_assignment_operation.py +25 -5
- classiq/model_expansions/quantum_operations/quantum_function_call.py +41 -2
- classiq/model_expansions/quantum_operations/repeat.py +1 -3
- classiq/model_expansions/scope.py +11 -10
- classiq/model_expansions/scope_initialization.py +6 -5
- classiq/model_expansions/sympy_conversion/expression_to_sympy.py +6 -6
- classiq/model_expansions/sympy_conversion/sympy_to_python.py +2 -2
- classiq/model_expansions/visitors/variable_references.py +5 -4
- classiq/qmod/builtins/classical_execution_primitives.py +9 -9
- classiq/qmod/builtins/functions/__init__.py +72 -55
- classiq/qmod/builtins/functions/amplitude_estimation.py +4 -1
- classiq/qmod/builtins/functions/arithmetic.py +14 -1
- classiq/qmod/builtins/functions/discrete_sine_cosine_transform.py +86 -6
- classiq/qmod/builtins/functions/grover.py +41 -45
- classiq/qmod/builtins/functions/hea.py +60 -4
- classiq/qmod/builtins/functions/linear_pauli_rotation.py +26 -4
- classiq/qmod/builtins/functions/modular_exponentiation.py +90 -29
- classiq/qmod/builtins/functions/operators.py +1 -1
- classiq/qmod/builtins/functions/qaoa_penalty.py +14 -5
- classiq/qmod/builtins/functions/qft_functions.py +57 -0
- classiq/qmod/builtins/functions/qpe.py +20 -4
- classiq/qmod/builtins/functions/qsvt.py +49 -4
- classiq/qmod/builtins/functions/standard_gates.py +4 -4
- classiq/qmod/builtins/functions/state_preparation.py +92 -10
- classiq/qmod/builtins/functions/swap_test.py +7 -1
- classiq/qmod/builtins/functions/utility_functions.py +43 -0
- classiq/qmod/builtins/functions/variational.py +18 -2
- classiq/qmod/builtins/operations.py +4 -5
- classiq/qmod/cfunc.py +2 -2
- classiq/qmod/classical_function.py +3 -7
- classiq/qmod/create_model_function.py +7 -6
- classiq/qmod/declaration_inferrer.py +7 -10
- classiq/qmod/expression_query.py +3 -3
- classiq/qmod/generative.py +2 -1
- classiq/qmod/model_state_container.py +5 -7
- classiq/qmod/native/__init__.py +1 -3
- classiq/qmod/native/expression_to_qmod.py +9 -8
- classiq/qmod/native/pretty_printer.py +6 -5
- classiq/qmod/pretty_print/__init__.py +1 -3
- classiq/qmod/pretty_print/expression_to_python.py +13 -12
- classiq/qmod/pretty_print/pretty_printer.py +13 -12
- classiq/qmod/python_classical_type.py +8 -4
- classiq/qmod/qfunc.py +4 -4
- classiq/qmod/qmod_variable.py +11 -10
- classiq/qmod/quantum_expandable.py +12 -15
- classiq/qmod/quantum_function.py +10 -3
- classiq/qmod/semantics/annotation.py +1 -1
- classiq/qmod/semantics/error_manager.py +8 -7
- classiq/qmod/semantics/static_semantics_visitor.py +19 -24
- classiq/qmod/semantics/validation/constants_validation.py +1 -1
- classiq/qmod/semantics/validation/func_call_validation.py +2 -2
- classiq/qmod/semantics/validation/main_validation.py +33 -0
- classiq/qmod/semantics/validation/types_validation.py +2 -1
- classiq/qmod/symbolic.py +5 -8
- classiq/qmod/symbolic_type.py +2 -2
- {classiq-0.53.0.dist-info → classiq-0.54.0.dist-info}/METADATA +1 -1
- {classiq-0.53.0.dist-info → classiq-0.54.0.dist-info}/RECORD +295 -292
- classiq/qmod/builtins/functions/qft.py +0 -23
- {classiq-0.53.0.dist-info → classiq-0.54.0.dist-info}/WHEEL +0 -0
@@ -1,7 +1,6 @@
|
|
1
|
-
from typing import
|
1
|
+
from typing import Annotated, Union
|
2
2
|
|
3
3
|
from pydantic import Field
|
4
|
-
from typing_extensions import Annotated
|
5
4
|
|
6
5
|
from classiq.interface.model.bind_operation import BindOperation
|
7
6
|
from classiq.interface.model.classical_if import ClassicalIf
|
@@ -44,7 +43,7 @@ ConcreteQuantumStatement = Annotated[
|
|
44
43
|
Field(..., discriminator="kind"),
|
45
44
|
]
|
46
45
|
|
47
|
-
StatementBlock =
|
46
|
+
StatementBlock = list[ConcreteQuantumStatement]
|
48
47
|
|
49
48
|
Control.model_rebuild()
|
50
49
|
QuantumLambdaFunction.model_rebuild()
|
@@ -1,6 +1,7 @@
|
|
1
1
|
import dataclasses
|
2
|
+
from collections.abc import Mapping
|
2
3
|
from enum import Enum
|
3
|
-
from typing import
|
4
|
+
from typing import Optional
|
4
5
|
|
5
6
|
from classiq.interface.exceptions import ClassiqError
|
6
7
|
from classiq.interface.model.handle_binding import HandleBinding
|
@@ -22,12 +23,12 @@ class HandleState(Enum):
|
|
22
23
|
@dataclasses.dataclass
|
23
24
|
class ValidationHandle:
|
24
25
|
_state: HandleState
|
25
|
-
errors:
|
26
|
+
errors: list[str] = dataclasses.field(default_factory=list)
|
26
27
|
|
27
28
|
def __init__(
|
28
29
|
self,
|
29
30
|
initial_state: Optional[HandleState] = None,
|
30
|
-
errors: Optional[
|
31
|
+
errors: Optional[list[str]] = None,
|
31
32
|
) -> None:
|
32
33
|
if initial_state is None and not errors:
|
33
34
|
raise ClassiqError("Missing initial state for ValidationHandle")
|
@@ -50,5 +51,5 @@ class ValidationHandle:
|
|
50
51
|
self._state = HandleState.UNINITIALIZED
|
51
52
|
|
52
53
|
|
53
|
-
def get_unique_handle_names(io_dict: Mapping[str, HandleBinding]) ->
|
54
|
+
def get_unique_handle_names(io_dict: Mapping[str, HandleBinding]) -> set[str]:
|
54
55
|
return {handle_binding.name for handle_binding in io_dict.values()}
|
@@ -1,5 +1,5 @@
|
|
1
1
|
from datetime import date
|
2
|
-
from typing import Any
|
2
|
+
from typing import Any
|
3
3
|
|
4
4
|
from pydantic import BaseModel
|
5
5
|
|
@@ -10,5 +10,5 @@ class DeprecationInfo(BaseModel):
|
|
10
10
|
|
11
11
|
|
12
12
|
class GlobalVersions(BaseModel):
|
13
|
-
deprecated:
|
14
|
-
deployed:
|
13
|
+
deprecated: dict[str, DeprecationInfo]
|
14
|
+
deployed: dict[str, Any]
|
@@ -1,5 +1,6 @@
|
|
1
|
+
from collections.abc import Mapping
|
1
2
|
from enum import Enum
|
2
|
-
from typing import Any, Callable,
|
3
|
+
from typing import Any, Callable, Union
|
3
4
|
|
4
5
|
from sympy import Eq, Expr, Number, Piecewise, Symbol
|
5
6
|
|
@@ -229,7 +230,7 @@ def do_slice(value: Any, lower: Any, upper: Any) -> Any:
|
|
229
230
|
return do_subscript(value, slice(lower, upper))
|
230
231
|
|
231
232
|
|
232
|
-
CORE_LIB_FUNCTIONS_LIST:
|
233
|
+
CORE_LIB_FUNCTIONS_LIST: list[Callable] = [
|
233
234
|
print,
|
234
235
|
sum,
|
235
236
|
struct_literal,
|
@@ -0,0 +1,190 @@
|
|
1
|
+
import dataclasses
|
2
|
+
import json
|
3
|
+
from collections.abc import Iterator, Sequence
|
4
|
+
from functools import cached_property
|
5
|
+
from typing import Any, Union
|
6
|
+
|
7
|
+
from typing_extensions import Self
|
8
|
+
|
9
|
+
from classiq.interface.exceptions import ClassiqExpansionError
|
10
|
+
from classiq.interface.generator.expressions.expression import Expression
|
11
|
+
from classiq.interface.generator.functions.port_declaration import (
|
12
|
+
PortDeclarationDirection,
|
13
|
+
)
|
14
|
+
from classiq.interface.model.handle_binding import HandleBinding
|
15
|
+
from classiq.interface.model.model import MAIN_FUNCTION_NAME, Model
|
16
|
+
from classiq.interface.model.native_function_definition import NativeFunctionDefinition
|
17
|
+
from classiq.interface.model.port_declaration import PortDeclaration
|
18
|
+
from classiq.interface.model.quantum_function_call import ArgValue, QuantumFunctionCall
|
19
|
+
from classiq.interface.model.quantum_function_declaration import (
|
20
|
+
PositionalArg,
|
21
|
+
QuantumOperandDeclaration,
|
22
|
+
)
|
23
|
+
from classiq.interface.model.quantum_type import QuantumType
|
24
|
+
|
25
|
+
from classiq import ClassicalParameterDeclaration
|
26
|
+
from classiq.model_expansions.scope import Evaluated, QuantumSymbol, evaluated_to_str
|
27
|
+
|
28
|
+
|
29
|
+
@dataclasses.dataclass(frozen=False)
|
30
|
+
class BlockFunctionInfo:
|
31
|
+
block_id: str
|
32
|
+
model: Model
|
33
|
+
inputs: set[str]
|
34
|
+
outputs: set[str]
|
35
|
+
inouts: set[str]
|
36
|
+
calls: set[str] = dataclasses.field(default_factory=set)
|
37
|
+
|
38
|
+
@classmethod
|
39
|
+
def from_call_converter(cls, call_converter: "CallToModelConverter") -> Self:
|
40
|
+
return cls(
|
41
|
+
block_id=call_converter.block_id,
|
42
|
+
model=call_converter.convert(),
|
43
|
+
inputs=set(call_converter.call.wiring_inputs),
|
44
|
+
outputs=set(call_converter.call.wiring_outputs),
|
45
|
+
inouts=set(call_converter.call.wiring_inouts),
|
46
|
+
)
|
47
|
+
|
48
|
+
|
49
|
+
class CallToModelConverter:
|
50
|
+
|
51
|
+
def __init__(
|
52
|
+
self,
|
53
|
+
call: QuantumFunctionCall,
|
54
|
+
positional_arg_declarations: Sequence[PositionalArg],
|
55
|
+
evaluated_arg: dict[str, Evaluated],
|
56
|
+
model: Model,
|
57
|
+
) -> None:
|
58
|
+
self.call = call
|
59
|
+
self._positional_arg_declarations = positional_arg_declarations
|
60
|
+
self._evaluated_arg = evaluated_arg
|
61
|
+
|
62
|
+
self._model = model
|
63
|
+
|
64
|
+
@cached_property
|
65
|
+
def block_id(self) -> str:
|
66
|
+
args_signature: dict = {}
|
67
|
+
for arg_declaration, evaluated_arg in zip(
|
68
|
+
self._positional_arg_declarations,
|
69
|
+
self._evaluated_arg.values(),
|
70
|
+
):
|
71
|
+
args_signature |= _get_arg_signature(arg_declaration, evaluated_arg)
|
72
|
+
return f"{self.call.func_name}__{json.dumps(args_signature)}"
|
73
|
+
|
74
|
+
def convert(self) -> Model:
|
75
|
+
return self._model.model_copy(
|
76
|
+
update={"functions": self._update_model_functions()}
|
77
|
+
)
|
78
|
+
|
79
|
+
def _update_model_functions(self) -> list[NativeFunctionDefinition]:
|
80
|
+
return [
|
81
|
+
(
|
82
|
+
self._create_new_main_function()
|
83
|
+
if function.name == MAIN_FUNCTION_NAME
|
84
|
+
else (
|
85
|
+
function.model_copy(update={"synthesis_data": None})
|
86
|
+
if function.name == self.call.function
|
87
|
+
else function
|
88
|
+
)
|
89
|
+
)
|
90
|
+
for function in self._model.functions
|
91
|
+
]
|
92
|
+
|
93
|
+
def _create_new_main_function(self) -> NativeFunctionDefinition:
|
94
|
+
return NativeFunctionDefinition(
|
95
|
+
name=MAIN_FUNCTION_NAME,
|
96
|
+
positional_arg_declarations=self._make_all_ports_outputs(),
|
97
|
+
body=[*self._allocate_ports(), self._update_call()],
|
98
|
+
)
|
99
|
+
|
100
|
+
def _make_all_ports_outputs(self) -> list[PortDeclaration]:
|
101
|
+
return [
|
102
|
+
_convert_port_to_output(port_declaration)
|
103
|
+
for port_declaration in self._positional_arg_declarations
|
104
|
+
if isinstance(port_declaration, PortDeclaration)
|
105
|
+
]
|
106
|
+
|
107
|
+
def _allocate_ports(self) -> Iterator[QuantumFunctionCall]:
|
108
|
+
return (
|
109
|
+
QuantumFunctionCall(
|
110
|
+
function="allocate",
|
111
|
+
positional_args=[
|
112
|
+
self._get_allocation_size(port_declaration.name),
|
113
|
+
HandleBinding(name=port_declaration.name),
|
114
|
+
],
|
115
|
+
)
|
116
|
+
for port_declaration in self._positional_arg_declarations
|
117
|
+
if isinstance(port_declaration, PortDeclaration)
|
118
|
+
and port_declaration.direction != PortDeclarationDirection.Output
|
119
|
+
)
|
120
|
+
|
121
|
+
def _get_allocation_size(self, port_declara_name: str) -> Expression:
|
122
|
+
port_value = self._evaluated_arg[port_declara_name].value
|
123
|
+
return Expression(expr=_get_reg_size(port_value, port_declara_name))
|
124
|
+
|
125
|
+
def _update_call(self) -> QuantumFunctionCall:
|
126
|
+
return self.call.model_copy(
|
127
|
+
update={"positional_args": self._evaluate_positional_args()}
|
128
|
+
)
|
129
|
+
|
130
|
+
def _evaluate_positional_args(self) -> list[ArgValue]:
|
131
|
+
return [
|
132
|
+
_get_positional_arg(arg, evaluated_arg)
|
133
|
+
for arg, evaluated_arg in zip(
|
134
|
+
self._positional_arg_declarations,
|
135
|
+
self._evaluated_arg.values(),
|
136
|
+
)
|
137
|
+
]
|
138
|
+
|
139
|
+
|
140
|
+
def _validate_quantum_type(port: Any, port_declara_name: str) -> QuantumType:
|
141
|
+
if not isinstance(port, QuantumSymbol):
|
142
|
+
raise ClassiqExpansionError(f"Port {port_declara_name!r} has incorrect type")
|
143
|
+
return port.quantum_type
|
144
|
+
|
145
|
+
|
146
|
+
def _get_reg_size(port: Any, port_declara_name: str) -> str:
|
147
|
+
quantum_type = _validate_quantum_type(port, port_declara_name)
|
148
|
+
return str(quantum_type.size_in_bits)
|
149
|
+
|
150
|
+
|
151
|
+
def _get_arg_signature(
|
152
|
+
arg_declaration: PositionalArg, evaluated_arg: Evaluated
|
153
|
+
) -> dict[str, str]:
|
154
|
+
arg_value = evaluated_arg.value
|
155
|
+
arg_name = arg_declaration.name
|
156
|
+
if isinstance(arg_declaration, ClassicalParameterDeclaration):
|
157
|
+
return {arg_name: evaluated_to_str(arg_value)}
|
158
|
+
if isinstance(arg_declaration, PortDeclaration):
|
159
|
+
quantum_type = _validate_quantum_type(arg_value, arg_name)
|
160
|
+
return {
|
161
|
+
arg_name: quantum_type.model_dump_json(exclude_none=True, exclude={"name"})
|
162
|
+
}
|
163
|
+
if isinstance(arg_declaration, QuantumOperandDeclaration):
|
164
|
+
raise NotImplementedError(
|
165
|
+
f"Synthesize separately does not support input operand: {arg_declaration.name!r}"
|
166
|
+
)
|
167
|
+
|
168
|
+
|
169
|
+
def _get_positional_arg(
|
170
|
+
arg_declaration: PositionalArg, evaluated_arg: Evaluated
|
171
|
+
) -> Union[Expression, HandleBinding]:
|
172
|
+
if isinstance(arg_declaration, ClassicalParameterDeclaration):
|
173
|
+
return Expression(expr=evaluated_to_str(evaluated_arg.value))
|
174
|
+
if isinstance(arg_declaration, PortDeclaration):
|
175
|
+
return HandleBinding(name=arg_declaration.name)
|
176
|
+
if isinstance(arg_declaration, QuantumOperandDeclaration):
|
177
|
+
raise NotImplementedError(
|
178
|
+
f"Synthesize separately does not support input operand: {arg_declaration.name!r}"
|
179
|
+
)
|
180
|
+
|
181
|
+
|
182
|
+
def _convert_port_to_output(port: PortDeclaration) -> PortDeclaration:
|
183
|
+
if port.direction == PortDeclarationDirection.Output:
|
184
|
+
return port
|
185
|
+
elif port.direction == PortDeclarationDirection.Inout:
|
186
|
+
return port.model_copy(update={"direction": PortDeclarationDirection.Output})
|
187
|
+
else:
|
188
|
+
raise NotImplementedError(
|
189
|
+
f"Synthesize separately does not support input ports: {port.name!r}"
|
190
|
+
)
|
@@ -1,21 +1,19 @@
|
|
1
|
-
from typing import Dict, List
|
2
|
-
|
3
1
|
from classiq.interface.generator.functions.port_declaration import (
|
4
2
|
PortDeclarationDirection,
|
5
3
|
)
|
6
4
|
from classiq.interface.model.port_declaration import PortDeclaration
|
7
5
|
|
8
6
|
|
9
|
-
def update_captured_vars(captured_vars:
|
7
|
+
def update_captured_vars(captured_vars: list[PortDeclaration]) -> list[PortDeclaration]:
|
10
8
|
if not captured_vars:
|
11
9
|
return []
|
12
10
|
return _update_declarations(captured_vars)
|
13
11
|
|
14
12
|
|
15
13
|
def _update_declarations(
|
16
|
-
captured_vars:
|
17
|
-
) ->
|
18
|
-
updated_vars:
|
14
|
+
captured_vars: list[PortDeclaration],
|
15
|
+
) -> list[PortDeclaration]:
|
16
|
+
updated_vars: dict[str, PortDeclaration] = {
|
19
17
|
var.name: PortDeclaration(
|
20
18
|
name=var.name,
|
21
19
|
quantum_type=var.quantum_type,
|
@@ -1,6 +1,6 @@
|
|
1
|
+
from collections.abc import Iterable, Iterator, Sequence
|
1
2
|
from contextlib import contextmanager
|
2
3
|
from dataclasses import dataclass
|
3
|
-
from typing import Dict, Iterable, Iterator, List, Sequence
|
4
4
|
|
5
5
|
from classiq.interface.exceptions import (
|
6
6
|
ClassiqExpansionError,
|
@@ -34,10 +34,10 @@ class PropagatedVariable:
|
|
34
34
|
class PropagatedVarStack:
|
35
35
|
def __init__(self, scope: Scope, builder: OperationBuilder) -> None:
|
36
36
|
# We use dictionary instead of set to maintain the order of insertion
|
37
|
-
self._stack:
|
37
|
+
self._stack: list[dict[PropagatedVariable, None]] = [dict()]
|
38
38
|
self._current_scope = scope
|
39
39
|
self._builder = builder
|
40
|
-
self._to_mangle:
|
40
|
+
self._to_mangle: dict[PropagatedVariable, str] = dict()
|
41
41
|
|
42
42
|
def set_scope(self, scope: Scope) -> None:
|
43
43
|
self._current_scope = scope
|
@@ -71,7 +71,7 @@ class PropagatedVarStack:
|
|
71
71
|
|
72
72
|
def _get_captured_vars(
|
73
73
|
self, qop: QuantumOperation
|
74
|
-
) ->
|
74
|
+
) -> dict[PropagatedVariable, None]:
|
75
75
|
input_captured = self._get_captured_vars_with_direction(
|
76
76
|
qop.inputs,
|
77
77
|
(
|
@@ -97,7 +97,7 @@ class PropagatedVarStack:
|
|
97
97
|
self,
|
98
98
|
variables: Iterable[HandleBinding],
|
99
99
|
direction: PortDeclarationDirection,
|
100
|
-
) ->
|
100
|
+
) -> dict[PropagatedVariable, None]:
|
101
101
|
return {
|
102
102
|
self._get_captured_var_with_direction(var.name, direction): None
|
103
103
|
for var in variables
|
@@ -133,8 +133,8 @@ class PropagatedVarStack:
|
|
133
133
|
for var in self._stack[-1]
|
134
134
|
)
|
135
135
|
|
136
|
-
def get_propagated_variables(self) ->
|
137
|
-
propagated_var_names:
|
136
|
+
def get_propagated_variables(self) -> list[HandleBinding]:
|
137
|
+
propagated_var_names: list[str] = [
|
138
138
|
self._get_propagated_var_name(var) for var in self._stack[-1]
|
139
139
|
]
|
140
140
|
return [
|
@@ -1,12 +1,14 @@
|
|
1
1
|
from collections import defaultdict
|
2
|
+
from collections.abc import Sequence
|
2
3
|
from dataclasses import dataclass, field
|
3
4
|
from functools import cached_property
|
4
|
-
from typing import Any,
|
5
|
+
from typing import Any, Optional, Union
|
5
6
|
|
6
7
|
from typing_extensions import Self
|
7
8
|
|
8
9
|
from classiq.interface.exceptions import ClassiqInternalExpansionError
|
9
10
|
from classiq.interface.generator.visitor import Visitor
|
11
|
+
from classiq.interface.model.native_function_definition import FunctionSynthesisData
|
10
12
|
from classiq.interface.model.port_declaration import PortDeclaration
|
11
13
|
from classiq.interface.model.quantum_function_call import QuantumFunctionCall
|
12
14
|
from classiq.interface.model.quantum_function_declaration import (
|
@@ -27,12 +29,12 @@ from classiq.qmod.quantum_function import GenerativeQFunc
|
|
27
29
|
@dataclass(frozen=True)
|
28
30
|
class Closure:
|
29
31
|
name: str
|
30
|
-
blocks:
|
32
|
+
blocks: dict[str, Sequence[QuantumStatement]]
|
31
33
|
scope: Scope
|
32
34
|
positional_arg_declarations: Sequence[PositionalArg] = tuple()
|
33
35
|
|
34
|
-
@
|
35
|
-
def port_declarations(self) ->
|
36
|
+
@property
|
37
|
+
def port_declarations(self) -> dict[str, PortDeclaration]:
|
36
38
|
return {
|
37
39
|
param.name: param
|
38
40
|
for param in self.positional_arg_declarations
|
@@ -42,7 +44,7 @@ class Closure:
|
|
42
44
|
|
43
45
|
@dataclass(frozen=True)
|
44
46
|
class GenerativeClosure(Closure):
|
45
|
-
generative_blocks:
|
47
|
+
generative_blocks: dict[str, GenerativeQFunc] = None # type:ignore[assignment]
|
46
48
|
|
47
49
|
|
48
50
|
@dataclass(frozen=True)
|
@@ -50,6 +52,7 @@ class FunctionClosure(Closure):
|
|
50
52
|
is_lambda: bool = False
|
51
53
|
is_atomic: bool = False
|
52
54
|
signature_scope: Scope = field(default_factory=Scope)
|
55
|
+
synthesis_data: FunctionSynthesisData = field(default_factory=FunctionSynthesisData)
|
53
56
|
|
54
57
|
@property
|
55
58
|
def body(self) -> Sequence[QuantumStatement]:
|
@@ -59,7 +62,7 @@ class FunctionClosure(Closure):
|
|
59
62
|
return self.blocks["body"]
|
60
63
|
|
61
64
|
@cached_property
|
62
|
-
def colliding_variables(self) ->
|
65
|
+
def colliding_variables(self) -> set[str]:
|
63
66
|
# Note that this has to be accessed after adding the parameters from the signature and not during
|
64
67
|
# initialization
|
65
68
|
return VariableCollector(self.scope).get_colliding_variables(self.body)
|
@@ -74,6 +77,7 @@ class FunctionClosure(Closure):
|
|
74
77
|
expr_renamer: Optional[ExpressionRenamer] = None,
|
75
78
|
is_lambda: bool = False,
|
76
79
|
is_atomic: bool = False,
|
80
|
+
synthesis_data: Optional[FunctionSynthesisData] = None,
|
77
81
|
**kwargs: Any,
|
78
82
|
) -> Self:
|
79
83
|
if expr_renamer:
|
@@ -86,6 +90,9 @@ class FunctionClosure(Closure):
|
|
86
90
|
body = expr_renamer.visit(body)
|
87
91
|
|
88
92
|
blocks = {"body": body} if body is not None else {}
|
93
|
+
synthesis_data = (
|
94
|
+
synthesis_data if synthesis_data is not None else FunctionSynthesisData()
|
95
|
+
)
|
89
96
|
return cls(
|
90
97
|
name,
|
91
98
|
blocks,
|
@@ -93,6 +100,7 @@ class FunctionClosure(Closure):
|
|
93
100
|
positional_arg_declarations,
|
94
101
|
is_lambda,
|
95
102
|
is_atomic,
|
103
|
+
synthesis_data=synthesis_data,
|
96
104
|
**kwargs,
|
97
105
|
)
|
98
106
|
|
@@ -110,19 +118,19 @@ class GenerativeFunctionClosure(GenerativeClosure, FunctionClosure):
|
|
110
118
|
pass
|
111
119
|
|
112
120
|
|
113
|
-
NestedFunctionClosureT = Union[FunctionClosure,
|
121
|
+
NestedFunctionClosureT = Union[FunctionClosure, list["NestedFunctionClosureT"]]
|
114
122
|
|
115
123
|
|
116
124
|
class VariableCollector(Visitor):
|
117
125
|
def __init__(self, function_scope: Scope) -> None:
|
118
126
|
self._function_scope = function_scope
|
119
|
-
self._variables: defaultdict[str,
|
127
|
+
self._variables: defaultdict[str, set[Optional[str]]] = defaultdict(set)
|
120
128
|
for var in self._function_scope.data:
|
121
129
|
defining_function = self._function_scope[var].defining_function
|
122
130
|
if defining_function is not None:
|
123
131
|
self._variables[var].add(defining_function.name)
|
124
132
|
|
125
|
-
def get_colliding_variables(self, body: Sequence[QuantumStatement]) ->
|
133
|
+
def get_colliding_variables(self, body: Sequence[QuantumStatement]) -> set[str]:
|
126
134
|
self.visit(body)
|
127
135
|
return {
|
128
136
|
var
|
@@ -1,5 +1,6 @@
|
|
1
|
+
from collections.abc import Sequence
|
1
2
|
from enum import Enum
|
2
|
-
from typing import Any
|
3
|
+
from typing import Any
|
3
4
|
|
4
5
|
from classiq.interface.exceptions import ClassiqExpansionError
|
5
6
|
from classiq.interface.generator.expressions.qmod_sized_proxy import QmodSizedProxy
|
@@ -31,7 +32,7 @@ from classiq.qmod.qmod_parameter import CInt, get_qmod_type
|
|
31
32
|
|
32
33
|
def check_type_match(
|
33
34
|
parameters: Sequence[AnonPositionalArg],
|
34
|
-
arguments:
|
35
|
+
arguments: list[Evaluated],
|
35
36
|
function_name: str,
|
36
37
|
) -> None:
|
37
38
|
if len(parameters) != len(arguments):
|
@@ -1,4 +1,4 @@
|
|
1
|
-
from
|
1
|
+
from collections.abc import Sequence
|
2
2
|
|
3
3
|
from classiq.interface.generator.functions.port_declaration import (
|
4
4
|
PortDeclarationDirection,
|
@@ -12,8 +12,8 @@ from classiq.model_expansions.scope import Evaluated, QuantumSymbol
|
|
12
12
|
|
13
13
|
def add_information_from_output_arguments(
|
14
14
|
parameters: Sequence[AnonPositionalArg],
|
15
|
-
args:
|
16
|
-
) ->
|
15
|
+
args: list[Evaluated],
|
16
|
+
) -> list[Evaluated]:
|
17
17
|
"""
|
18
18
|
This function propagates the quantum type information from the output arguments
|
19
19
|
to the arguments that were passed to it.
|
@@ -1,4 +1,4 @@
|
|
1
|
-
from typing import Any
|
1
|
+
from typing import Any
|
2
2
|
|
3
3
|
from sympy import Equality
|
4
4
|
from sympy.core.numbers import Number
|
@@ -19,7 +19,7 @@ def type_name(obj: Any) -> str:
|
|
19
19
|
return type(obj).__name__
|
20
20
|
|
21
21
|
|
22
|
-
def resolve_num_condition(condition: Equality) ->
|
22
|
+
def resolve_num_condition(condition: Equality) -> tuple[QmodSizedProxy, str]:
|
23
23
|
ctrl, ctrl_val = condition.args
|
24
24
|
if isinstance(ctrl, Number) and isinstance(ctrl_val, QmodQScalarProxy):
|
25
25
|
ctrl, ctrl_val = ctrl_val, ctrl
|
@@ -41,7 +41,7 @@ def _calculate_ctrl_state(ctrl: QmodSizedProxy, ctrl_val: float) -> str:
|
|
41
41
|
return _to_twos_complement(integer_ctrl_val, ctrl.size)
|
42
42
|
|
43
43
|
|
44
|
-
def _get_numeric_attributes(ctrl: QmodSizedProxy) ->
|
44
|
+
def _get_numeric_attributes(ctrl: QmodSizedProxy) -> tuple[bool, int]:
|
45
45
|
return (
|
46
46
|
(ctrl.is_signed, ctrl.fraction_digits)
|
47
47
|
if isinstance(ctrl, QmodQNumProxy)
|
@@ -1,4 +1,4 @@
|
|
1
|
-
from typing import
|
1
|
+
from typing import Union
|
2
2
|
|
3
3
|
from classiq.interface.exceptions import (
|
4
4
|
ClassiqExpansionError,
|
@@ -41,8 +41,8 @@ from classiq.model_expansions.scope import Evaluated, QuantumSymbol, Scope
|
|
41
41
|
|
42
42
|
|
43
43
|
def evaluate_parameter_types_from_args(
|
44
|
-
closure: FunctionClosure, signature_scope: Scope, arguments:
|
45
|
-
) ->
|
44
|
+
closure: FunctionClosure, signature_scope: Scope, arguments: list[Evaluated]
|
45
|
+
) -> list[PositionalArg]:
|
46
46
|
parameters = closure.positional_arg_declarations
|
47
47
|
function_name = closure.name
|
48
48
|
check_type_match(parameters, arguments, function_name)
|
@@ -90,12 +90,12 @@ def _update_scope(
|
|
90
90
|
)
|
91
91
|
|
92
92
|
|
93
|
-
NestedFunctionClosureT = Union[FunctionClosure,
|
93
|
+
NestedFunctionClosureT = Union[FunctionClosure, list["NestedFunctionClosureT"]]
|
94
94
|
|
95
95
|
|
96
96
|
def _update_operand_signature_environment(
|
97
97
|
operand_val: NestedFunctionClosureT,
|
98
|
-
parameter_names:
|
98
|
+
parameter_names: set[str],
|
99
99
|
closure: FunctionClosure,
|
100
100
|
) -> None:
|
101
101
|
# We update the environment (parent) of the operand by adding closure.scope.data,
|
@@ -203,8 +203,8 @@ def _evaluate_qstruct_in_quantum_symbol(
|
|
203
203
|
|
204
204
|
|
205
205
|
def evaluate_types_in_quantum_symbols(
|
206
|
-
symbols:
|
207
|
-
) ->
|
206
|
+
symbols: list[QuantumSymbol], scope: Scope
|
207
|
+
) -> list[QuantumSymbol]:
|
208
208
|
return [
|
209
209
|
QuantumSymbol(
|
210
210
|
handle=symbol.handle,
|
@@ -1,6 +1,7 @@
|
|
1
1
|
import ast
|
2
|
+
from collections.abc import Mapping
|
2
3
|
from enum import EnumMeta
|
3
|
-
from typing import Any,
|
4
|
+
from typing import Any, Optional
|
4
5
|
|
5
6
|
from sympy import sympify
|
6
7
|
|
@@ -30,14 +31,14 @@ from classiq.model_expansions.sympy_conversion.sympy_to_python import sympy_to_p
|
|
30
31
|
from classiq.qmod import symbolic
|
31
32
|
|
32
33
|
|
33
|
-
def evaluate_constants(constants:
|
34
|
-
result:
|
34
|
+
def evaluate_constants(constants: list[Constant]) -> dict[str, EvaluatedExpression]:
|
35
|
+
result: dict[str, EvaluatedExpression] = {}
|
35
36
|
for constant in constants:
|
36
37
|
result[constant.name] = evaluate(constant.value, result)
|
37
38
|
return result
|
38
39
|
|
39
40
|
|
40
|
-
def evaluate_constants_as_python(constants:
|
41
|
+
def evaluate_constants_as_python(constants: list[Constant]) -> dict[str, Any]:
|
41
42
|
evaluated = evaluate_constants(constants)
|
42
43
|
return {
|
43
44
|
constant.name: qmod_val_to_python(
|
@@ -50,9 +51,9 @@ def evaluate_constants_as_python(constants: List[Constant]) -> Dict[str, Any]:
|
|
50
51
|
def evaluate(
|
51
52
|
expr: Expression,
|
52
53
|
locals_dict: Mapping[str, EvaluatedExpression],
|
53
|
-
uninitialized_locals: Optional[
|
54
|
+
uninitialized_locals: Optional[set[str]] = None,
|
54
55
|
) -> EvaluatedExpression:
|
55
|
-
model_locals:
|
56
|
+
model_locals: dict[str, ExpressionValue] = {}
|
56
57
|
model_locals.update(ATOMIC_EXPRESSION_FUNCTIONS)
|
57
58
|
model_locals.update(SymbolTable.enum_table.enums)
|
58
59
|
# locals override builtin-functions
|
@@ -81,8 +82,8 @@ def evaluate(
|
|
81
82
|
|
82
83
|
def _validate_undefined_vars(
|
83
84
|
expr: str,
|
84
|
-
model_locals:
|
85
|
-
uninitialized_locals: Optional[
|
85
|
+
model_locals: dict[str, ExpressionValue],
|
86
|
+
uninitialized_locals: Optional[set[str]],
|
86
87
|
) -> None:
|
87
88
|
uninitialized_locals = uninitialized_locals or set()
|
88
89
|
id_visitor = _VarsCollector()
|
@@ -110,7 +111,7 @@ def _validate_undefined_vars(
|
|
110
111
|
|
111
112
|
class _VarsCollector(ast.NodeTransformer):
|
112
113
|
def __init__(self) -> None:
|
113
|
-
self.vars:
|
114
|
+
self.vars: set[str] = set()
|
114
115
|
|
115
116
|
def visit_Name(self, node: ast.Name) -> None:
|
116
117
|
self.vars.add(node.id)
|
@@ -1,5 +1,5 @@
|
|
1
1
|
import ast
|
2
|
-
from
|
2
|
+
from collections.abc import Sequence
|
3
3
|
|
4
4
|
from classiq.interface.generator.expressions.expression import Expression
|
5
5
|
from classiq.interface.generator.expressions.expression_constants import (
|
@@ -17,11 +17,11 @@ from classiq.model_expansions.visitors.variable_references import VarRefTransfor
|
|
17
17
|
|
18
18
|
class ExpressionRenamer(Transformer):
|
19
19
|
|
20
|
-
def __init__(self, var_mapping:
|
20
|
+
def __init__(self, var_mapping: dict[str, str]) -> None:
|
21
21
|
self.var_ref_transformer = VarRefTransformer(var_mapping)
|
22
22
|
|
23
23
|
@property
|
24
|
-
def var_mapping(self) ->
|
24
|
+
def var_mapping(self) -> dict[str, str]:
|
25
25
|
return self.var_ref_transformer.var_mapping
|
26
26
|
|
27
27
|
def visit_QuantumFunctionCall(
|
@@ -41,8 +41,8 @@ class ExpressionRenamer(Transformer):
|
|
41
41
|
return self.var_mapping.get(name, name)
|
42
42
|
|
43
43
|
def rename_expression_dict(
|
44
|
-
self, expr_dict:
|
45
|
-
) ->
|
44
|
+
self, expr_dict: dict[str, Expression]
|
45
|
+
) -> dict[str, Expression]:
|
46
46
|
return {
|
47
47
|
self.rename_string(key): self.visit(val) for key, val in expr_dict.items()
|
48
48
|
}
|
@@ -51,7 +51,7 @@ class ExpressionRenamer(Transformer):
|
|
51
51
|
def from_positional_arg_declarations(
|
52
52
|
cls, positional_arg_declarations: Sequence[PositionalArg], suffix: str
|
53
53
|
) -> "ExpressionRenamer":
|
54
|
-
var_mapping:
|
54
|
+
var_mapping: dict[str, str] = dict()
|
55
55
|
for arg in positional_arg_declarations:
|
56
56
|
if not isinstance(arg, ClassicalParameterDeclaration):
|
57
57
|
continue
|