classiq 0.38.0__py3-none-any.whl → 0.65.4__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 +47 -32
- classiq/_analyzer_extras/_ipywidgets_async_extension.py +2 -1
- classiq/_internals/api_wrapper.py +235 -97
- classiq/_internals/async_utils.py +1 -3
- classiq/_internals/authentication/auth0.py +26 -10
- classiq/_internals/authentication/authentication.py +11 -0
- classiq/_internals/authentication/device.py +10 -5
- classiq/_internals/authentication/password_manager.py +18 -6
- classiq/_internals/authentication/token_manager.py +10 -5
- classiq/_internals/client.py +94 -33
- classiq/_internals/config.py +3 -4
- classiq/_internals/host_checker.py +38 -15
- classiq/_internals/jobs.py +60 -57
- classiq/_internals/type_validation.py +9 -9
- classiq/analyzer/__init__.py +1 -3
- classiq/analyzer/analyzer.py +24 -19
- classiq/analyzer/analyzer_utilities.py +10 -10
- classiq/analyzer/rb.py +15 -15
- classiq/analyzer/show_interactive_hack.py +27 -4
- classiq/analyzer/url_utils.py +2 -3
- classiq/applications/__init__.py +3 -12
- classiq/applications/chemistry/__init__.py +14 -10
- classiq/applications/chemistry/ansatz_parameters.py +4 -4
- classiq/{applications_model_constructors → applications/chemistry}/chemistry_model_constructor.py +165 -158
- classiq/applications/chemistry/ground_state_problem.py +1 -1
- classiq/{applications_model_constructors → applications}/combinatorial_helpers/allowed_constraints.py +4 -1
- classiq/{applications_model_constructors → applications}/combinatorial_helpers/arithmetic/arithmetic_expression.py +1 -1
- classiq/{applications_model_constructors → applications}/combinatorial_helpers/arithmetic/isolation.py +1 -1
- classiq/{applications_model_constructors → applications}/combinatorial_helpers/combinatorial_problem_utils.py +51 -15
- classiq/{applications_model_constructors → applications}/combinatorial_helpers/encoding_mapping.py +12 -12
- classiq/{applications_model_constructors → applications}/combinatorial_helpers/encoding_utils.py +8 -6
- classiq/{applications_model_constructors → applications}/combinatorial_helpers/memory.py +7 -11
- classiq/{applications_model_constructors → applications}/combinatorial_helpers/optimization_model.py +67 -40
- classiq/applications/combinatorial_helpers/pauli_helpers/pauli_utils.py +46 -0
- classiq/applications/combinatorial_helpers/pyomo_utils.py +447 -0
- classiq/{applications_model_constructors → applications}/combinatorial_helpers/sympy_utils.py +2 -2
- classiq/{applications_model_constructors → applications}/combinatorial_helpers/transformations/encoding.py +15 -20
- classiq/{applications_model_constructors → applications}/combinatorial_helpers/transformations/fixed_variables.py +14 -15
- classiq/{applications_model_constructors → applications}/combinatorial_helpers/transformations/ising_converter.py +11 -15
- classiq/{applications_model_constructors → applications}/combinatorial_helpers/transformations/penalty.py +1 -2
- classiq/{applications_model_constructors → applications}/combinatorial_helpers/transformations/penalty_support.py +3 -7
- classiq/{applications_model_constructors → applications}/combinatorial_helpers/transformations/sign_seperation.py +2 -3
- classiq/{applications_model_constructors → applications}/combinatorial_helpers/transformations/slack_variables.py +5 -8
- classiq/applications/combinatorial_optimization/__init__.py +20 -6
- classiq/applications/combinatorial_optimization/combinatorial_optimization_config.py +2 -2
- classiq/{applications_model_constructors → applications/combinatorial_optimization}/combinatorial_optimization_model_constructor.py +35 -33
- classiq/applications/combinatorial_optimization/combinatorial_problem.py +229 -0
- classiq/applications/combinatorial_optimization/examples/__init__.py +1 -3
- classiq/applications/finance/__init__.py +4 -5
- classiq/{applications_model_constructors → applications/finance}/finance_model_constructor.py +48 -42
- classiq/applications/grover/__init__.py +9 -0
- classiq/{applications_model_constructors → applications/grover}/grover_model_constructor.py +52 -51
- classiq/applications/hamiltonian/pauli_decomposition.py +113 -0
- classiq/applications/libraries/qmci_library.py +22 -0
- classiq/applications/qnn/__init__.py +2 -4
- classiq/applications/qnn/circuit_utils.py +6 -6
- classiq/applications/qnn/datasets/__init__.py +9 -11
- classiq/applications/qnn/datasets/dataset_base_classes.py +7 -5
- classiq/applications/qnn/datasets/dataset_not.py +2 -1
- classiq/applications/qnn/datasets/dataset_parity.py +2 -2
- classiq/applications/qnn/gradients/quantum_gradient.py +1 -1
- classiq/applications/qnn/gradients/simple_quantum_gradient.py +2 -1
- classiq/applications/qnn/qlayer.py +30 -10
- classiq/applications/qnn/torch_utils.py +4 -3
- classiq/applications/qnn/types.py +5 -5
- classiq/applications/qsvm/__init__.py +6 -4
- classiq/applications/qsvm/qsvm.py +3 -6
- classiq/applications/qsvm/qsvm_data_generation.py +3 -3
- classiq/{applications_model_constructors → applications/qsvm}/qsvm_model_constructor.py +30 -28
- classiq/execution/__init__.py +8 -3
- classiq/execution/all_hardware_devices.py +11 -0
- classiq/execution/execution_session.py +400 -0
- classiq/execution/iqcc.py +63 -0
- classiq/execution/jobs.py +197 -25
- classiq/execution/qnn.py +79 -0
- classiq/executor.py +20 -115
- classiq/interface/_version.py +1 -1
- classiq/interface/analyzer/analysis_params.py +43 -13
- classiq/interface/analyzer/cytoscape_graph.py +15 -9
- classiq/interface/analyzer/result.py +28 -32
- classiq/interface/applications/qsvm.py +20 -29
- classiq/interface/ast_node.py +16 -0
- classiq/interface/backend/backend_preferences.py +390 -121
- classiq/interface/backend/ionq/ionq_quantum_program.py +15 -23
- classiq/interface/backend/pydantic_backend.py +25 -22
- classiq/interface/backend/quantum_backend_providers.py +69 -16
- classiq/interface/chemistry/fermionic_operator.py +30 -21
- classiq/interface/chemistry/ground_state_problem.py +28 -25
- classiq/interface/chemistry/molecule.py +14 -10
- classiq/interface/chemistry/operator.py +64 -231
- classiq/interface/combinatorial_optimization/encoding_types.py +1 -1
- 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 +10 -6
- 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 +8 -9
- classiq/interface/combinatorial_optimization/optimization_problem.py +2 -2
- classiq/interface/combinatorial_optimization/result.py +1 -3
- classiq/interface/combinatorial_optimization/solver_types.py +1 -1
- classiq/interface/debug_info/debug_info.py +86 -0
- classiq/{exceptions.py → interface/exceptions.py} +37 -9
- classiq/interface/execution/iqcc.py +19 -0
- classiq/interface/execution/jobs.py +15 -12
- classiq/interface/execution/primitives.py +18 -0
- classiq/interface/executor/constants.py +1 -0
- classiq/interface/executor/execution_preferences.py +26 -114
- classiq/interface/executor/execution_request.py +24 -46
- classiq/interface/executor/execution_result.py +30 -8
- classiq/interface/executor/iqae_result.py +4 -6
- classiq/interface/executor/optimizer_preferences.py +17 -14
- classiq/interface/executor/quantum_code.py +28 -24
- classiq/interface/executor/quantum_instruction_set.py +2 -2
- classiq/interface/executor/register_initialization.py +11 -14
- classiq/interface/executor/result.py +83 -56
- classiq/interface/executor/vqe_result.py +10 -10
- classiq/interface/finance/function_input.py +35 -25
- classiq/interface/finance/gaussian_model_input.py +5 -5
- classiq/interface/finance/log_normal_model_input.py +4 -4
- classiq/interface/finance/model_input.py +4 -4
- classiq/interface/generator/adjacency.py +1 -3
- classiq/interface/generator/amplitude_loading.py +22 -12
- classiq/interface/generator/ansatz_library.py +5 -5
- classiq/interface/generator/application_apis/arithmetic_declarations.py +8 -5
- classiq/interface/generator/application_apis/chemistry_declarations.py +27 -187
- classiq/interface/generator/application_apis/combinatorial_optimization_declarations.py +18 -21
- classiq/interface/generator/application_apis/entangler_declarations.py +11 -6
- classiq/interface/generator/application_apis/finance_declarations.py +48 -69
- classiq/interface/generator/application_apis/qsvm_declarations.py +0 -70
- classiq/interface/generator/arith/argument_utils.py +46 -5
- classiq/interface/generator/arith/arithmetic.py +35 -16
- classiq/interface/generator/arith/arithmetic_arg_type_validator.py +6 -7
- classiq/interface/generator/arith/arithmetic_expression_abc.py +66 -25
- classiq/interface/generator/arith/arithmetic_expression_parser.py +11 -11
- classiq/interface/generator/arith/arithmetic_expression_validator.py +47 -43
- classiq/interface/generator/arith/arithmetic_operations.py +14 -6
- classiq/interface/generator/arith/arithmetic_param_getters.py +7 -8
- classiq/interface/generator/arith/arithmetic_result_builder.py +21 -17
- classiq/interface/generator/arith/ast_node_rewrite.py +3 -2
- classiq/interface/generator/arith/binary_ops.py +218 -130
- classiq/interface/generator/arith/endianness.py +1 -1
- classiq/interface/generator/arith/extremum_operations.py +96 -25
- classiq/interface/generator/arith/logical_ops.py +14 -12
- classiq/interface/generator/arith/number_utils.py +12 -6
- classiq/interface/generator/arith/register_user_input.py +60 -37
- classiq/interface/generator/arith/unary_ops.py +49 -29
- classiq/interface/generator/arith/uncomputation_methods.py +1 -1
- classiq/interface/generator/builtin_api_builder.py +2 -9
- classiq/interface/generator/chemistry_function_params.py +3 -3
- classiq/interface/generator/circuit_code/circuit_code.py +7 -7
- classiq/interface/generator/circuit_code/types_and_constants.py +4 -7
- classiq/interface/generator/commuting_pauli_exponentiation.py +7 -7
- classiq/interface/generator/compiler_keywords.py +5 -1
- classiq/interface/generator/complex_type.py +13 -18
- classiq/interface/generator/constant.py +3 -4
- classiq/interface/generator/control_state.py +34 -29
- classiq/interface/generator/copy.py +47 -0
- classiq/interface/generator/custom_ansatz.py +2 -5
- classiq/interface/generator/distance.py +3 -5
- classiq/interface/generator/excitations.py +3 -2
- classiq/interface/generator/expressions/atomic_expression_functions.py +21 -5
- classiq/interface/generator/expressions/enums/__init__.py +0 -10
- classiq/interface/generator/expressions/enums/finance_functions.py +12 -22
- classiq/interface/generator/expressions/evaluated_expression.py +5 -5
- classiq/interface/generator/expressions/expression.py +26 -14
- classiq/interface/generator/expressions/expression_constants.py +9 -3
- classiq/interface/generator/expressions/non_symbolic_expr.py +119 -0
- classiq/interface/generator/expressions/qmod_qarray_proxy.py +99 -0
- classiq/interface/generator/expressions/qmod_qscalar_proxy.py +34 -8
- classiq/interface/generator/expressions/qmod_qstruct_proxy.py +36 -0
- classiq/interface/generator/expressions/qmod_sized_proxy.py +30 -2
- classiq/interface/generator/expressions/qmod_struct_instance.py +14 -2
- classiq/interface/generator/expressions/sympy_supported_expressions.py +19 -11
- classiq/interface/generator/finance.py +2 -2
- classiq/interface/generator/function_param_library.py +6 -6
- classiq/interface/generator/function_param_list_without_self_reference.py +2 -10
- classiq/interface/generator/function_params.py +36 -64
- classiq/interface/generator/functions/__init__.py +0 -22
- classiq/interface/generator/functions/builtins/internal_operators.py +16 -0
- classiq/interface/generator/functions/classical_function_declaration.py +18 -9
- classiq/interface/generator/functions/classical_type.py +47 -166
- classiq/interface/generator/functions/concrete_types.py +55 -0
- classiq/interface/generator/functions/function_declaration.py +13 -14
- classiq/interface/generator/functions/port_declaration.py +1 -13
- classiq/interface/generator/functions/qmod_python_interface.py +2 -1
- classiq/interface/generator/functions/type_name.py +90 -0
- classiq/interface/generator/generated_circuit_data.py +153 -20
- classiq/interface/generator/grover_diffuser.py +32 -25
- classiq/interface/generator/grover_operator.py +34 -25
- classiq/interface/generator/hamiltonian_evolution/exponentiation.py +4 -6
- classiq/interface/generator/hamiltonian_evolution/qdrift.py +4 -4
- classiq/interface/generator/hamiltonian_evolution/suzuki_trotter.py +9 -9
- classiq/interface/generator/hardware/hardware_data.py +72 -34
- classiq/interface/generator/hardware_efficient_ansatz.py +20 -16
- classiq/interface/generator/hartree_fock.py +13 -5
- classiq/interface/generator/identity.py +10 -6
- classiq/interface/generator/linear_pauli_rotations.py +32 -20
- classiq/interface/generator/mcmt_method.py +1 -1
- classiq/interface/generator/mcu.py +17 -15
- classiq/interface/generator/mcx.py +24 -17
- classiq/interface/generator/model/__init__.py +2 -5
- classiq/interface/generator/model/constraints.py +26 -8
- classiq/interface/generator/model/model.py +27 -190
- classiq/interface/generator/model/preferences/preferences.py +115 -41
- classiq/{quantum_register.py → interface/generator/model/quantum_register.py} +14 -17
- classiq/interface/generator/oracles/arithmetic_oracle.py +2 -4
- classiq/interface/generator/oracles/custom_oracle.py +15 -13
- classiq/interface/generator/oracles/oracle_abc.py +7 -7
- classiq/interface/generator/partitioned_register.py +7 -7
- classiq/interface/generator/piecewise_linear_amplitude_loading.py +45 -29
- classiq/interface/generator/preferences/optimization.py +1 -2
- classiq/interface/generator/qpe.py +41 -30
- classiq/interface/generator/qsvm.py +9 -10
- classiq/interface/generator/quantum_function_call.py +88 -73
- classiq/interface/generator/quantum_program.py +41 -24
- classiq/interface/generator/range_types.py +11 -12
- classiq/interface/generator/register_role.py +18 -6
- classiq/interface/generator/slice_parsing_utils.py +5 -5
- classiq/interface/generator/standard_gates/controlled_standard_gates.py +30 -39
- classiq/interface/generator/standard_gates/standard_angle_metaclass.py +2 -6
- classiq/interface/generator/standard_gates/standard_gates.py +3 -3
- classiq/interface/generator/standard_gates/u_gate.py +7 -10
- classiq/interface/generator/state_preparation/bell_state_preparation.py +3 -3
- classiq/interface/generator/state_preparation/computational_basis_state_preparation.py +2 -1
- classiq/interface/generator/state_preparation/distributions.py +16 -15
- classiq/interface/generator/state_preparation/metrics.py +4 -7
- classiq/interface/generator/state_preparation/state_preparation.py +25 -20
- classiq/interface/generator/synthesis_metadata/synthesis_duration.py +0 -4
- classiq/interface/generator/synthesis_metadata/synthesis_execution_data.py +20 -6
- classiq/interface/generator/transpiler_basis_gates.py +7 -3
- classiq/interface/generator/types/builtin_enum_declarations.py +178 -0
- classiq/interface/generator/types/compilation_metadata.py +6 -0
- classiq/interface/generator/types/enum_declaration.py +54 -0
- classiq/interface/generator/types/qstruct_declaration.py +18 -0
- classiq/interface/generator/types/struct_declaration.py +7 -11
- classiq/interface/generator/ucc.py +5 -4
- classiq/interface/generator/unitary_gate.py +5 -5
- classiq/interface/generator/user_defined_function_params.py +4 -1
- classiq/interface/generator/validations/flow_graph.py +7 -7
- classiq/interface/generator/validations/validator_functions.py +4 -4
- classiq/interface/generator/visitor.py +23 -16
- classiq/interface/hardware.py +29 -8
- classiq/interface/helpers/classproperty.py +8 -0
- classiq/interface/helpers/custom_encoders.py +2 -2
- classiq/interface/helpers/custom_pydantic_types.py +40 -50
- classiq/interface/helpers/datastructures.py +26 -0
- 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 +7 -5
- classiq/interface/helpers/validation_helpers.py +3 -20
- classiq/interface/helpers/versioned_model.py +1 -4
- classiq/interface/ide/ide_data.py +16 -20
- classiq/interface/ide/visual_model.py +130 -0
- classiq/interface/interface_version.py +1 -0
- classiq/interface/jobs.py +29 -69
- classiq/interface/model/allocate.py +16 -0
- classiq/interface/model/bind_operation.py +32 -9
- classiq/interface/model/classical_if.py +15 -0
- classiq/interface/model/classical_parameter_declaration.py +33 -3
- classiq/interface/model/control.py +45 -0
- classiq/interface/model/handle_binding.py +298 -20
- classiq/interface/model/inplace_binary_operation.py +29 -24
- classiq/interface/model/invert.py +12 -0
- classiq/interface/model/model.py +69 -61
- classiq/interface/model/native_function_definition.py +17 -20
- classiq/interface/model/parameter.py +13 -0
- classiq/interface/model/phase_operation.py +11 -0
- classiq/interface/model/port_declaration.py +27 -9
- classiq/interface/model/power.py +14 -0
- classiq/interface/model/quantum_expressions/amplitude_loading_operation.py +30 -18
- classiq/interface/model/quantum_expressions/arithmetic_operation.py +51 -14
- classiq/interface/model/quantum_expressions/quantum_expression.py +12 -35
- classiq/interface/model/quantum_function_call.py +141 -343
- classiq/interface/model/quantum_function_declaration.py +190 -157
- classiq/interface/model/quantum_lambda_function.py +33 -32
- classiq/interface/model/quantum_statement.py +71 -12
- classiq/interface/model/quantum_type.py +177 -40
- classiq/interface/model/quantum_variable_declaration.py +3 -25
- classiq/interface/model/repeat.py +15 -0
- classiq/interface/model/statement_block.py +40 -14
- classiq/interface/model/validation_handle.py +13 -6
- classiq/interface/model/variable_declaration_statement.py +3 -1
- classiq/interface/model/within_apply_operation.py +7 -5
- classiq/interface/server/global_versions.py +6 -7
- classiq/interface/server/routes.py +17 -21
- classiq/interface/source_reference.py +59 -0
- classiq/model_expansions/atomic_expression_functions_defs.py +253 -0
- classiq/model_expansions/capturing/__init__.py +0 -0
- classiq/model_expansions/capturing/captured_vars.py +435 -0
- classiq/model_expansions/capturing/mangling_utils.py +56 -0
- classiq/model_expansions/closure.py +171 -0
- classiq/model_expansions/debug_flag.py +3 -0
- classiq/model_expansions/evaluators/__init__.py +0 -0
- classiq/model_expansions/evaluators/arg_type_match.py +158 -0
- classiq/model_expansions/evaluators/argument_types.py +42 -0
- classiq/model_expansions/evaluators/classical_expression.py +36 -0
- classiq/model_expansions/evaluators/control.py +144 -0
- classiq/model_expansions/evaluators/parameter_types.py +226 -0
- classiq/model_expansions/evaluators/quantum_type_utils.py +239 -0
- classiq/model_expansions/evaluators/type_type_match.py +90 -0
- classiq/model_expansions/expression_evaluator.py +135 -0
- classiq/model_expansions/expression_renamer.py +76 -0
- classiq/model_expansions/function_builder.py +247 -0
- classiq/model_expansions/generative_functions.py +158 -0
- classiq/model_expansions/interpreters/__init__.py +0 -0
- classiq/model_expansions/interpreters/base_interpreter.py +263 -0
- classiq/model_expansions/interpreters/frontend_generative_interpreter.py +28 -0
- classiq/model_expansions/interpreters/generative_interpreter.py +249 -0
- classiq/model_expansions/model_tables.py +18 -0
- classiq/model_expansions/quantum_operations/__init__.py +9 -0
- classiq/model_expansions/quantum_operations/bind.py +60 -0
- classiq/model_expansions/quantum_operations/call_emitter.py +266 -0
- classiq/model_expansions/quantum_operations/classicalif.py +53 -0
- classiq/model_expansions/quantum_operations/declarative_call_emitter.py +87 -0
- classiq/model_expansions/quantum_operations/emitter.py +181 -0
- classiq/model_expansions/quantum_operations/quantum_function_call.py +33 -0
- classiq/model_expansions/quantum_operations/repeat.py +56 -0
- classiq/model_expansions/quantum_operations/shallow_emitter.py +180 -0
- classiq/model_expansions/quantum_operations/variable_decleration.py +28 -0
- classiq/model_expansions/scope.py +240 -0
- classiq/model_expansions/scope_initialization.py +150 -0
- classiq/model_expansions/sympy_conversion/__init__.py +0 -0
- classiq/model_expansions/sympy_conversion/arithmetics.py +49 -0
- classiq/model_expansions/sympy_conversion/expression_to_sympy.py +179 -0
- classiq/model_expansions/sympy_conversion/sympy_to_python.py +123 -0
- classiq/model_expansions/transformers/__init__.py +0 -0
- classiq/model_expansions/transformers/ast_renamer.py +26 -0
- classiq/model_expansions/transformers/var_splitter.py +299 -0
- classiq/model_expansions/utils/__init__.py +0 -0
- classiq/model_expansions/utils/counted_name_allocator.py +11 -0
- classiq/model_expansions/utils/handles_collector.py +33 -0
- classiq/model_expansions/visitors/__init__.py +0 -0
- classiq/model_expansions/visitors/boolean_expression_transformers.py +214 -0
- classiq/model_expansions/visitors/variable_references.py +144 -0
- classiq/open_library/__init__.py +4 -0
- classiq/open_library/functions/__init__.py +130 -0
- classiq/open_library/functions/amplitude_estimation.py +30 -0
- classiq/open_library/functions/discrete_sine_cosine_transform.py +181 -0
- classiq/open_library/functions/grover.py +157 -0
- classiq/open_library/functions/hea.py +115 -0
- classiq/open_library/functions/linear_pauli_rotation.py +82 -0
- classiq/open_library/functions/modular_exponentiation.py +201 -0
- classiq/open_library/functions/qaoa_penalty.py +117 -0
- classiq/open_library/functions/qft_functions.py +54 -0
- classiq/open_library/functions/qpe.py +46 -0
- classiq/open_library/functions/qsvt.py +331 -0
- classiq/open_library/functions/state_preparation.py +301 -0
- classiq/open_library/functions/swap_test.py +27 -0
- classiq/open_library/functions/utility_functions.py +81 -0
- classiq/open_library/functions/variational.py +52 -0
- classiq/qmod/__init__.py +10 -10
- classiq/qmod/builtins/__init__.py +19 -2
- classiq/qmod/builtins/classical_execution_primitives.py +36 -14
- classiq/qmod/builtins/classical_functions.py +39 -43
- classiq/qmod/builtins/constants.py +10 -0
- classiq/qmod/builtins/enums.py +208 -0
- classiq/qmod/builtins/functions/__init__.py +137 -0
- classiq/qmod/builtins/functions/allocation.py +150 -0
- classiq/qmod/builtins/functions/arithmetic.py +55 -0
- classiq/qmod/builtins/functions/benchmarking.py +8 -0
- classiq/qmod/builtins/functions/chemistry.py +91 -0
- classiq/qmod/builtins/functions/exponentiation.py +105 -0
- classiq/qmod/builtins/functions/finance.py +34 -0
- classiq/qmod/builtins/functions/operators.py +16 -0
- classiq/qmod/builtins/functions/qsvm.py +24 -0
- classiq/qmod/builtins/functions/standard_gates.py +651 -0
- classiq/qmod/builtins/operations.py +373 -40
- classiq/qmod/builtins/structs.py +103 -80
- classiq/qmod/cfunc.py +2 -2
- classiq/qmod/classical_function.py +4 -8
- classiq/qmod/cparam.py +64 -0
- classiq/qmod/create_model_function.py +56 -0
- classiq/qmod/declaration_inferrer.py +143 -101
- classiq/qmod/expression_query.py +20 -4
- classiq/qmod/generative.py +42 -0
- classiq/qmod/model_state_container.py +18 -6
- classiq/qmod/native/__init__.py +7 -0
- classiq/qmod/native/expression_to_qmod.py +16 -11
- classiq/qmod/native/pretty_printer.py +187 -97
- classiq/qmod/pretty_print/__init__.py +7 -0
- classiq/qmod/pretty_print/expression_to_python.py +222 -0
- classiq/qmod/pretty_print/pretty_printer.py +572 -0
- classiq/qmod/python_classical_type.py +67 -0
- classiq/qmod/qfunc.py +60 -8
- classiq/qmod/qmod_constant.py +93 -26
- classiq/qmod/qmod_parameter.py +68 -59
- classiq/qmod/qmod_variable.py +468 -155
- classiq/qmod/quantum_callable.py +17 -7
- classiq/qmod/quantum_expandable.py +269 -96
- classiq/qmod/quantum_function.py +196 -41
- classiq/qmod/semantics/__init__.py +0 -0
- classiq/qmod/semantics/annotation/__init__.py +0 -0
- classiq/qmod/semantics/annotation/call_annotation.py +92 -0
- classiq/qmod/semantics/annotation/qstruct_annotator.py +23 -0
- classiq/qmod/semantics/error_manager.py +88 -0
- classiq/qmod/semantics/lambdas.py +25 -0
- classiq/qmod/semantics/static_semantics_visitor.py +384 -0
- classiq/qmod/semantics/validation/__init__.py +0 -0
- classiq/qmod/semantics/validation/constants_validation.py +16 -0
- classiq/qmod/semantics/validation/func_call_validation.py +99 -0
- classiq/qmod/semantics/validation/function_name_collisions_validation.py +23 -0
- classiq/qmod/semantics/validation/handle_validation.py +85 -0
- classiq/qmod/semantics/validation/main_validation.py +33 -0
- classiq/qmod/semantics/validation/types_validation.py +128 -0
- classiq/qmod/symbolic.py +147 -123
- classiq/qmod/symbolic_expr.py +27 -12
- classiq/qmod/symbolic_type.py +2 -5
- classiq/qmod/type_attribute_remover.py +32 -0
- classiq/qmod/utilities.py +98 -4
- classiq/qmod/write_qmod.py +17 -3
- classiq/synthesis.py +210 -22
- {classiq-0.38.0.dist-info → classiq-0.65.4.dist-info}/METADATA +16 -9
- classiq-0.65.4.dist-info/RECORD +521 -0
- classiq/_internals/_qfunc_ext.py +0 -6
- classiq/applications/benchmarking/__init__.py +0 -9
- classiq/applications/benchmarking/mirror_benchmarking.py +0 -70
- classiq/applications/numpy_utils.py +0 -37
- classiq/applications_model_constructors/__init__.py +0 -25
- classiq/applications_model_constructors/combinatorial_helpers/multiple_comp_basis_sp.py +0 -34
- classiq/applications_model_constructors/combinatorial_helpers/pauli_helpers/pauli_utils.py +0 -65
- classiq/applications_model_constructors/combinatorial_helpers/pyomo_utils.py +0 -243
- classiq/applications_model_constructors/libraries/ampltitude_estimation_library.py +0 -11
- classiq/applications_model_constructors/libraries/qmci_library.py +0 -107
- classiq/builtin_functions/__init__.py +0 -43
- classiq/builtin_functions/amplitude_loading.py +0 -3
- classiq/builtin_functions/binary_ops.py +0 -1
- classiq/builtin_functions/exponentiation.py +0 -5
- classiq/builtin_functions/qpe.py +0 -4
- classiq/builtin_functions/qsvm.py +0 -7
- classiq/builtin_functions/range_types.py +0 -5
- classiq/builtin_functions/standard_gates.py +0 -1
- classiq/builtin_functions/state_preparation.py +0 -6
- classiq/builtin_functions/suzuki_trotter.py +0 -3
- classiq/interface/executor/aws_execution_cost.py +0 -73
- classiq/interface/executor/error_mitigation.py +0 -6
- classiq/interface/generator/credit_risk_example/linear_gci.py +0 -122
- classiq/interface/generator/credit_risk_example/weighted_adder.py +0 -69
- classiq/interface/generator/expressions/enums/chemistry.py +0 -28
- classiq/interface/generator/expressions/enums/classical_enum.py +0 -5
- classiq/interface/generator/expressions/enums/ladder_operator.py +0 -16
- classiq/interface/generator/expressions/enums/optimizers.py +0 -9
- classiq/interface/generator/expressions/enums/pauli.py +0 -8
- classiq/interface/generator/expressions/enums/qsvm_feature_map_entanglement.py +0 -9
- classiq/interface/generator/functions/core_lib_declarations/quantum_functions/__init__.py +0 -18
- classiq/interface/generator/functions/core_lib_declarations/quantum_functions/atomic_quantum_functions.py +0 -641
- classiq/interface/generator/functions/core_lib_declarations/quantum_functions/exponentiation_functions.py +0 -89
- classiq/interface/generator/functions/core_lib_declarations/quantum_functions/std_lib_functions.py +0 -1229
- classiq/interface/generator/functions/core_lib_declarations/quantum_operators.py +0 -95
- classiq/interface/generator/functions/foreign_function_definition.py +0 -114
- classiq/interface/generator/functions/function_implementation.py +0 -107
- classiq/interface/generator/functions/native_function_definition.py +0 -155
- classiq/interface/generator/functions/quantum_function_declaration.py +0 -69
- classiq/interface/generator/functions/register.py +0 -44
- classiq/interface/generator/functions/register_mapping_data.py +0 -106
- classiq/interface/generator/inequality_mixer.py +0 -51
- classiq/interface/generator/model/classical_main_validator.py +0 -106
- classiq/interface/generator/range_mixer.py +0 -56
- classiq/interface/generator/state_propagator.py +0 -74
- classiq/interface/generator/types/builtin_struct_declarations/__init__.py +0 -1
- classiq/interface/generator/types/builtin_struct_declarations/pauli_struct_declarations.py +0 -22
- classiq/interface/ide/show.py +0 -34
- classiq/interface/model/call_synthesis_data.py +0 -68
- classiq/interface/model/common_model_types.py +0 -23
- classiq/interface/model/quantum_expressions/control_state.py +0 -38
- classiq/interface/model/quantum_if_operation.py +0 -94
- classiq/interface/model/resolvers/function_call_resolver.py +0 -43
- classiq/interface/model/validations/handle_validation_base.py +0 -55
- classiq/interface/model/validations/handles_validator.py +0 -156
- classiq/interface/model/validations/port_to_wire_name_generator.py +0 -12
- classiq/model/__init__.py +0 -14
- classiq/model/composite_function_generator.py +0 -33
- classiq/model/function_handler.py +0 -462
- classiq/model/logic_flow.py +0 -149
- classiq/model/logic_flow_change_handler.py +0 -71
- classiq/model/model.py +0 -229
- classiq/qmod/builtins/functions.py +0 -913
- classiq/qmod/qmod_struct.py +0 -37
- classiq/quantum_functions/__init__.py +0 -17
- classiq/quantum_functions/annotation_parser.py +0 -205
- classiq/quantum_functions/decorators.py +0 -22
- classiq/quantum_functions/function_library.py +0 -181
- classiq/quantum_functions/function_parser.py +0 -74
- classiq/quantum_functions/quantum_function.py +0 -236
- classiq-0.38.0.dist-info/RECORD +0 -454
- /classiq/{applications_model_constructors → applications}/combinatorial_helpers/__init__.py +0 -0
- /classiq/{applications_model_constructors → applications}/combinatorial_helpers/arithmetic/__init__.py +0 -0
- /classiq/{applications_model_constructors → applications}/combinatorial_helpers/pauli_helpers/__init__.py +0 -0
- /classiq/{applications_model_constructors → applications}/combinatorial_helpers/pauli_helpers/pauli_sparsing.py +0 -0
- /classiq/{applications_model_constructors → applications}/combinatorial_helpers/py.typed +0 -0
- /classiq/{applications_model_constructors/combinatorial_helpers/transformations → applications/combinatorial_helpers/solvers}/__init__.py +0 -0
- /classiq/{applications_model_constructors/libraries → applications/combinatorial_helpers/transformations}/__init__.py +0 -0
- /classiq/{interface/generator/credit_risk_example → applications/hamiltonian}/__init__.py +0 -0
- /classiq/{interface/generator/functions/core_lib_declarations → applications/libraries}/__init__.py +0 -0
- /classiq/interface/{model/resolvers → debug_info}/__init__.py +0 -0
- /classiq/{_internals → interface}/enum_utils.py +0 -0
- /classiq/interface/{model/validations → generator/functions/builtins}/__init__.py +0 -0
- /classiq/{interface/generator/functions/core_lib_declarations/quantum_functions/chemistry_functions.py → model_expansions/__init__.py} +0 -0
- {classiq-0.38.0.dist-info → classiq-0.65.4.dist-info}/WHEEL +0 -0
classiq/qmod/quantum_callable.py
CHANGED
@@ -14,12 +14,14 @@ from typing_extensions import ParamSpec
|
|
14
14
|
|
15
15
|
from classiq.interface.model.quantum_function_call import QuantumFunctionCall
|
16
16
|
from classiq.interface.model.quantum_function_declaration import (
|
17
|
-
|
17
|
+
AnonQuantumFunctionDeclaration,
|
18
18
|
)
|
19
19
|
from classiq.interface.model.quantum_statement import QuantumStatement
|
20
20
|
from classiq.interface.model.quantum_type import QuantumType
|
21
|
+
from classiq.interface.source_reference import SourceReference
|
21
22
|
|
22
|
-
from classiq.qmod.
|
23
|
+
from classiq.qmod.cparam import CInt
|
24
|
+
from classiq.qmod.utilities import get_source_ref
|
23
25
|
|
24
26
|
if TYPE_CHECKING:
|
25
27
|
from classiq.qmod.quantum_expandable import QTerminalCallable
|
@@ -33,23 +35,30 @@ class QExpandableInterface(ABC):
|
|
33
35
|
raise NotImplementedError()
|
34
36
|
|
35
37
|
@abstractmethod
|
36
|
-
def add_local_handle(
|
38
|
+
def add_local_handle(
|
39
|
+
self,
|
40
|
+
name: str,
|
41
|
+
qtype: QuantumType,
|
42
|
+
source_ref: Optional[SourceReference] = None,
|
43
|
+
) -> None:
|
37
44
|
raise NotImplementedError()
|
38
45
|
|
39
46
|
|
40
47
|
class QCallable(Generic[P], ABC):
|
41
48
|
CURRENT_EXPANDABLE: ClassVar[Optional[QExpandableInterface]] = None
|
49
|
+
FRAME_DEPTH = 1
|
42
50
|
|
43
51
|
def __call__(self, *args: Any, **kwargs: Any) -> None:
|
44
52
|
assert QCallable.CURRENT_EXPANDABLE is not None
|
53
|
+
source_ref = get_source_ref(sys._getframe(self.FRAME_DEPTH))
|
45
54
|
QCallable.CURRENT_EXPANDABLE.append_statement_to_body(
|
46
|
-
self.create_quantum_function_call(*args, **kwargs)
|
55
|
+
self.create_quantum_function_call(source_ref, *args, **kwargs)
|
47
56
|
)
|
48
57
|
return
|
49
58
|
|
50
59
|
@property
|
51
60
|
@abstractmethod
|
52
|
-
def func_decl(self) ->
|
61
|
+
def func_decl(self) -> AnonQuantumFunctionDeclaration:
|
53
62
|
raise NotImplementedError
|
54
63
|
|
55
64
|
# Support comma-separated generic args in older Python versions
|
@@ -60,7 +69,7 @@ class QCallable(Generic[P], ABC):
|
|
60
69
|
|
61
70
|
@abstractmethod
|
62
71
|
def create_quantum_function_call(
|
63
|
-
self, *args: Any, **kwargs: Any
|
72
|
+
self, source_ref_: SourceReference, *args: Any, **kwargs: Any
|
64
73
|
) -> QuantumFunctionCall:
|
65
74
|
raise NotImplementedError()
|
66
75
|
|
@@ -68,7 +77,8 @@ class QCallable(Generic[P], ABC):
|
|
68
77
|
class QCallableList(QCallable, Generic[P], ABC):
|
69
78
|
if TYPE_CHECKING:
|
70
79
|
|
80
|
+
@property
|
71
81
|
def len(self) -> int: ...
|
72
82
|
|
73
|
-
def __getitem__(self, key: Union[slice, int,
|
83
|
+
def __getitem__(self, key: Union[slice, int, CInt]) -> "QTerminalCallable":
|
74
84
|
raise NotImplementedError()
|
@@ -1,68 +1,87 @@
|
|
1
1
|
import inspect
|
2
2
|
from abc import ABC
|
3
|
+
from dataclasses import is_dataclass
|
4
|
+
from enum import Enum as PythonEnum
|
3
5
|
from types import TracebackType
|
4
6
|
from typing import (
|
5
7
|
TYPE_CHECKING,
|
6
8
|
Any,
|
7
9
|
Callable,
|
8
10
|
ClassVar,
|
9
|
-
Dict,
|
10
|
-
List,
|
11
11
|
Optional,
|
12
|
-
Type,
|
13
12
|
Union,
|
14
13
|
cast,
|
15
14
|
overload,
|
16
15
|
)
|
17
16
|
|
17
|
+
import pydantic
|
18
|
+
from sympy import Basic
|
18
19
|
from typing_extensions import Self
|
19
20
|
|
21
|
+
from classiq.interface.exceptions import ClassiqInternalError, ClassiqValueError
|
20
22
|
from classiq.interface.generator.expressions.expression import Expression
|
23
|
+
from classiq.interface.generator.functions.concrete_types import (
|
24
|
+
NativePythonClassicalTypes,
|
25
|
+
PythonClassicalPydanticTypes,
|
26
|
+
)
|
21
27
|
from classiq.interface.model.classical_parameter_declaration import (
|
22
|
-
|
28
|
+
AnonClassicalParameterDeclaration,
|
23
29
|
)
|
24
|
-
from classiq.interface.model.port_declaration import
|
30
|
+
from classiq.interface.model.port_declaration import AnonPortDeclaration
|
25
31
|
from classiq.interface.model.quantum_function_call import (
|
26
32
|
ArgValue,
|
27
|
-
OperandIdentifier,
|
28
33
|
QuantumFunctionCall,
|
29
34
|
)
|
30
35
|
from classiq.interface.model.quantum_function_declaration import (
|
31
|
-
|
36
|
+
AnonPositionalArg,
|
37
|
+
AnonQuantumFunctionDeclaration,
|
38
|
+
AnonQuantumOperandDeclaration,
|
32
39
|
QuantumFunctionDeclaration,
|
33
|
-
QuantumOperandDeclaration,
|
34
40
|
)
|
35
41
|
from classiq.interface.model.quantum_lambda_function import (
|
42
|
+
OperandIdentifier,
|
43
|
+
QuantumCallable,
|
36
44
|
QuantumLambdaFunction,
|
37
|
-
QuantumOperand,
|
38
45
|
)
|
39
46
|
from classiq.interface.model.quantum_statement import QuantumStatement
|
40
47
|
from classiq.interface.model.quantum_type import QuantumType
|
41
48
|
from classiq.interface.model.variable_declaration_statement import (
|
42
49
|
VariableDeclarationStatement,
|
43
50
|
)
|
51
|
+
from classiq.interface.source_reference import SourceReference
|
44
52
|
|
45
|
-
from classiq.
|
53
|
+
from classiq.qmod.generative import generative_mode_context, is_generative_mode
|
46
54
|
from classiq.qmod.model_state_container import QMODULE, ModelStateContainer
|
47
55
|
from classiq.qmod.qmod_constant import QConstant
|
48
|
-
from classiq.qmod.qmod_parameter import
|
49
|
-
|
56
|
+
from classiq.qmod.qmod_parameter import (
|
57
|
+
CInt,
|
58
|
+
CParam,
|
59
|
+
CParamScalar,
|
60
|
+
create_param,
|
61
|
+
get_qmod_type,
|
62
|
+
)
|
63
|
+
from classiq.qmod.qmod_variable import (
|
64
|
+
QVar,
|
65
|
+
create_qvar_for_port_decl,
|
66
|
+
)
|
50
67
|
from classiq.qmod.quantum_callable import QCallable, QExpandableInterface
|
51
|
-
from classiq.qmod.
|
68
|
+
from classiq.qmod.symbolic_expr import SymbolicExpr
|
69
|
+
from classiq.qmod.type_attribute_remover import decl_without_type_attributes
|
70
|
+
from classiq.qmod.utilities import mangle_keyword, qmod_val_to_expr_str
|
52
71
|
|
53
|
-
ArgType = Union[
|
72
|
+
ArgType = Union[CParam, QVar, QCallable]
|
54
73
|
|
55
74
|
|
56
75
|
class QExpandable(QCallable, QExpandableInterface, ABC):
|
57
|
-
STACK: ClassVar[
|
76
|
+
STACK: ClassVar[list["QExpandable"]] = list()
|
58
77
|
|
59
78
|
def __init__(self, py_callable: Callable) -> None:
|
60
79
|
self._qmodule: ModelStateContainer = QMODULE
|
61
80
|
self._py_callable: Callable = py_callable
|
62
|
-
self._body:
|
81
|
+
self._body: list[QuantumStatement] = list()
|
63
82
|
|
64
83
|
@property
|
65
|
-
def body(self) ->
|
84
|
+
def body(self) -> list[QuantumStatement]:
|
66
85
|
return self._body
|
67
86
|
|
68
87
|
def __enter__(self) -> Self:
|
@@ -73,7 +92,7 @@ class QExpandable(QCallable, QExpandableInterface, ABC):
|
|
73
92
|
|
74
93
|
def __exit__(
|
75
94
|
self,
|
76
|
-
exc_type: Optional[
|
95
|
+
exc_type: Optional[type[BaseException]],
|
77
96
|
exc_val: Optional[BaseException],
|
78
97
|
exc_tb: Optional[TracebackType],
|
79
98
|
) -> None:
|
@@ -82,156 +101,303 @@ class QExpandable(QCallable, QExpandableInterface, ABC):
|
|
82
101
|
QExpandable.STACK[-1] if QExpandable.STACK else None
|
83
102
|
)
|
84
103
|
|
104
|
+
def __call__(self, *args: Any, **kwargs: Any) -> None:
|
105
|
+
super().__call__(*args, **kwargs)
|
106
|
+
self.add_function_dependencies()
|
107
|
+
|
85
108
|
def expand(self) -> None:
|
86
|
-
|
87
|
-
self
|
109
|
+
if self not in QExpandable.STACK:
|
110
|
+
with self, generative_mode_context(False):
|
111
|
+
self._py_callable(*self._get_positional_args())
|
88
112
|
|
89
|
-
def infer_rename_params(self) ->
|
90
|
-
return
|
113
|
+
def infer_rename_params(self) -> Optional[list[str]]:
|
114
|
+
return None
|
91
115
|
|
92
|
-
def add_local_handle(
|
93
|
-
self
|
116
|
+
def add_local_handle(
|
117
|
+
self,
|
118
|
+
name: str,
|
119
|
+
qtype: QuantumType,
|
120
|
+
source_ref: Optional[SourceReference] = None,
|
121
|
+
) -> None:
|
122
|
+
self.append_statement_to_body(
|
123
|
+
VariableDeclarationStatement(
|
124
|
+
name=name, quantum_type=qtype, source_ref=source_ref
|
125
|
+
)
|
126
|
+
)
|
94
127
|
|
95
128
|
def append_statement_to_body(self, stmt: QuantumStatement) -> None:
|
96
129
|
self._body.append(stmt)
|
97
130
|
|
98
|
-
def _get_positional_args(self) ->
|
99
|
-
result:
|
100
|
-
|
101
|
-
|
102
|
-
|
103
|
-
|
131
|
+
def _get_positional_args(self) -> list[ArgType]:
|
132
|
+
result: list[ArgType] = []
|
133
|
+
rename_params = self.infer_rename_params()
|
134
|
+
if rename_params is not None and len(rename_params) != len(
|
135
|
+
self.func_decl.positional_arg_declarations
|
136
|
+
):
|
137
|
+
op_name = (
|
138
|
+
f" {self.func_decl.name!r}" if self.func_decl.name is not None else ""
|
139
|
+
)
|
140
|
+
raise ClassiqValueError(
|
141
|
+
f"Operand{op_name} takes {len(self.func_decl.positional_arg_declarations)} arguments but the received function takes {len(rename_params)} argument"
|
142
|
+
)
|
143
|
+
for idx, arg in enumerate(self.func_decl.positional_arg_declarations):
|
144
|
+
actual_name = (
|
145
|
+
rename_params[idx] if rename_params is not None else arg.get_name()
|
146
|
+
)
|
147
|
+
if isinstance(arg, AnonClassicalParameterDeclaration):
|
104
148
|
result.append(
|
105
149
|
create_param(actual_name, arg.classical_type, self._qmodule)
|
106
150
|
)
|
107
|
-
elif isinstance(arg,
|
108
|
-
result.append(create_qvar_for_port_decl(arg))
|
151
|
+
elif isinstance(arg, AnonPortDeclaration):
|
152
|
+
result.append(create_qvar_for_port_decl(arg, actual_name))
|
109
153
|
else:
|
110
|
-
assert isinstance(arg,
|
111
|
-
result.append(QTerminalCallable(arg))
|
154
|
+
assert isinstance(arg, AnonQuantumOperandDeclaration)
|
155
|
+
result.append(QTerminalCallable(arg, idx))
|
112
156
|
return result
|
113
157
|
|
114
158
|
def create_quantum_function_call(
|
115
|
-
self, *args: Any, **kwargs: Any
|
159
|
+
self, source_ref_: SourceReference, *args: Any, **kwargs: Any
|
116
160
|
) -> QuantumFunctionCall:
|
117
|
-
|
161
|
+
func_decl = self.func_decl
|
162
|
+
if not isinstance(func_decl, QuantumFunctionDeclaration):
|
163
|
+
raise NotImplementedError
|
164
|
+
return _create_quantum_function_call(
|
165
|
+
func_decl, None, source_ref_, *args, **kwargs
|
166
|
+
)
|
167
|
+
|
168
|
+
def add_function_dependencies(self) -> None:
|
169
|
+
called_name = self.func_decl.name
|
170
|
+
if called_name is None:
|
171
|
+
return
|
172
|
+
for expandable in QExpandable.STACK:
|
173
|
+
caller_name = expandable.func_decl.name
|
174
|
+
if caller_name is not None:
|
175
|
+
caller_deps = self._qmodule.function_dependencies[caller_name]
|
176
|
+
if called_name not in caller_deps:
|
177
|
+
caller_deps.append(called_name)
|
118
178
|
|
119
179
|
|
120
180
|
class QLambdaFunction(QExpandable):
|
121
|
-
def __init__(
|
181
|
+
def __init__(
|
182
|
+
self, decl: AnonQuantumFunctionDeclaration, py_callable: Callable
|
183
|
+
) -> None:
|
122
184
|
py_callable.__annotations__.pop("return", None)
|
123
185
|
super().__init__(py_callable)
|
124
186
|
self._decl = decl
|
125
187
|
|
126
188
|
@property
|
127
|
-
def func_decl(self) ->
|
189
|
+
def func_decl(self) -> AnonQuantumFunctionDeclaration:
|
128
190
|
return self._decl
|
129
191
|
|
130
|
-
def
|
131
|
-
|
132
|
-
|
133
|
-
|
134
|
-
|
135
|
-
|
136
|
-
if decl_param != py_param
|
137
|
-
}
|
192
|
+
def expand(self) -> None:
|
193
|
+
if not is_generative_mode():
|
194
|
+
super().expand()
|
195
|
+
|
196
|
+
def infer_rename_params(self) -> list[str]:
|
197
|
+
return inspect.getfullargspec(self._py_callable).args
|
138
198
|
|
139
199
|
|
140
200
|
class QTerminalCallable(QCallable):
|
201
|
+
@overload
|
141
202
|
def __init__(
|
142
203
|
self,
|
143
204
|
decl: QuantumFunctionDeclaration,
|
144
|
-
|
205
|
+
param_idx: Optional[int] = None,
|
206
|
+
index_: Optional[Union[int, CParamScalar]] = None,
|
145
207
|
) -> None:
|
146
|
-
|
208
|
+
pass
|
209
|
+
|
210
|
+
@overload
|
211
|
+
def __init__(
|
212
|
+
self,
|
213
|
+
decl: AnonQuantumFunctionDeclaration,
|
214
|
+
param_idx: int,
|
215
|
+
index_: Optional[Union[int, CParamScalar]] = None,
|
216
|
+
) -> None:
|
217
|
+
pass
|
218
|
+
|
219
|
+
def __init__(
|
220
|
+
self,
|
221
|
+
decl: AnonQuantumFunctionDeclaration,
|
222
|
+
param_idx: Optional[int] = None,
|
223
|
+
index_: Optional[Union[int, CParamScalar]] = None,
|
224
|
+
) -> None:
|
225
|
+
self._decl = self._override_decl_name(decl, param_idx)
|
147
226
|
self._index = index_
|
148
227
|
|
228
|
+
@staticmethod
|
229
|
+
def _override_decl_name(
|
230
|
+
decl: AnonQuantumFunctionDeclaration, param_idx: Optional[int]
|
231
|
+
) -> QuantumFunctionDeclaration:
|
232
|
+
if (
|
233
|
+
not isinstance(QCallable.CURRENT_EXPANDABLE, QLambdaFunction)
|
234
|
+
or param_idx is None
|
235
|
+
):
|
236
|
+
return decl.rename(decl.get_name())
|
237
|
+
rename_params = QCallable.CURRENT_EXPANDABLE.infer_rename_params()
|
238
|
+
return decl.rename(new_name=rename_params[param_idx])
|
239
|
+
|
149
240
|
@property
|
150
241
|
def is_list(self) -> bool:
|
151
|
-
return
|
242
|
+
return (
|
243
|
+
isinstance(self._decl, AnonQuantumOperandDeclaration) and self._decl.is_list
|
244
|
+
)
|
152
245
|
|
153
|
-
def __getitem__(self, key: Union[slice, int,
|
246
|
+
def __getitem__(self, key: Union[slice, int, CInt]) -> "QTerminalCallable":
|
154
247
|
if not self.is_list:
|
155
248
|
raise ClassiqValueError("Cannot index a non-list operand")
|
156
249
|
if isinstance(key, slice):
|
157
250
|
raise NotImplementedError("Operand lists don't support slicing")
|
158
|
-
if isinstance(key,
|
251
|
+
if isinstance(key, CParam) and not isinstance(key, CParamScalar):
|
159
252
|
raise ClassiqValueError("Non-classical parameter for slicing")
|
160
|
-
|
253
|
+
if not isinstance(self._decl, AnonQuantumOperandDeclaration):
|
254
|
+
raise ClassiqInternalError
|
255
|
+
return QTerminalCallable(self._decl.element_declaration, index_=key)
|
161
256
|
|
162
257
|
def __len__(self) -> int:
|
163
258
|
raise ClassiqValueError(
|
164
|
-
"len(<func>) is not supported for quantum callables - use <func>.len
|
259
|
+
"len(<func>) is not supported for quantum callables - use <func>.len instead (Only if it is an operand list)"
|
165
260
|
)
|
166
261
|
|
167
262
|
if TYPE_CHECKING:
|
168
263
|
|
264
|
+
@property
|
169
265
|
def len(self) -> int: ...
|
170
266
|
|
171
267
|
else:
|
172
268
|
|
173
|
-
|
269
|
+
@property
|
270
|
+
def len(self) -> CParamScalar:
|
174
271
|
if not self.is_list:
|
175
272
|
raise ClassiqValueError("Cannot get length of a non-list operand")
|
176
|
-
return
|
273
|
+
return CParamScalar(f"get_field({self.func_decl.name}, 'len')")
|
177
274
|
|
178
275
|
@property
|
179
276
|
def func_decl(self) -> QuantumFunctionDeclaration:
|
180
277
|
return self._decl
|
181
278
|
|
182
279
|
def create_quantum_function_call(
|
183
|
-
self, *args: Any, **kwargs: Any
|
280
|
+
self, source_ref_: SourceReference, *args: Any, **kwargs: Any
|
184
281
|
) -> QuantumFunctionCall:
|
185
282
|
if self.is_list and self._index is None:
|
186
283
|
raise ClassiqValueError(
|
187
284
|
f"Quantum operand {self.func_decl.name!r} is a list and must be indexed"
|
188
285
|
)
|
189
286
|
return _create_quantum_function_call(
|
190
|
-
self.func_decl, self._index, *args, **kwargs
|
287
|
+
self.func_decl, self._index, source_ref_, *args, **kwargs
|
288
|
+
)
|
289
|
+
|
290
|
+
def get_arg(self) -> QuantumCallable:
|
291
|
+
if self._index is None:
|
292
|
+
return self._decl.name
|
293
|
+
return OperandIdentifier(
|
294
|
+
name=self._decl.name, index=Expression(expr=str(self._index))
|
191
295
|
)
|
192
296
|
|
193
297
|
|
194
298
|
@overload
|
195
299
|
def prepare_arg(
|
196
|
-
arg_decl:
|
197
|
-
|
300
|
+
arg_decl: AnonPositionalArg,
|
301
|
+
val: Union[QCallable, Callable[..., None]],
|
302
|
+
func_name: Optional[str],
|
303
|
+
param_name: str,
|
304
|
+
) -> QuantumLambdaFunction: ...
|
198
305
|
|
199
306
|
|
200
307
|
@overload
|
201
|
-
def prepare_arg(
|
308
|
+
def prepare_arg(
|
309
|
+
arg_decl: AnonPositionalArg, val: Any, func_name: Optional[str], param_name: str
|
310
|
+
) -> ArgValue: ...
|
202
311
|
|
203
312
|
|
204
|
-
def prepare_arg(
|
313
|
+
def prepare_arg(
|
314
|
+
arg_decl: AnonPositionalArg, val: Any, func_name: Optional[str], param_name: str
|
315
|
+
) -> ArgValue:
|
316
|
+
from classiq.qmod.quantum_function import BaseQFunc, GenerativeQFunc
|
317
|
+
|
318
|
+
if isinstance(val, BaseQFunc):
|
319
|
+
val.add_function_dependencies()
|
320
|
+
if isinstance(val, GenerativeQFunc):
|
321
|
+
QMODULE.generative_functions[val.func_decl.name] = val
|
205
322
|
if isinstance(val, QConstant):
|
206
323
|
val.add_to_model()
|
207
324
|
return Expression(expr=str(val.name))
|
208
|
-
if isinstance(arg_decl,
|
209
|
-
|
210
|
-
|
325
|
+
if isinstance(arg_decl, AnonClassicalParameterDeclaration):
|
326
|
+
_validate_classical_arg(val, arg_decl, func_name)
|
327
|
+
return Expression(expr=qmod_val_to_expr_str(val))
|
328
|
+
elif isinstance(arg_decl, AnonPortDeclaration):
|
329
|
+
if not isinstance(val, QVar):
|
330
|
+
func_name_message = (
|
331
|
+
"" if func_name is None else f" of function {func_name!r}"
|
332
|
+
)
|
333
|
+
raise ClassiqValueError(
|
334
|
+
f"Argument {str(val)!r} to parameter {param_name!r}{func_name_message} "
|
335
|
+
f"has incompatible type; expected quantum variable"
|
336
|
+
)
|
211
337
|
return val.get_handle_binding()
|
212
338
|
else:
|
213
339
|
if isinstance(val, list):
|
214
340
|
if not all(isinstance(v, QCallable) or callable(v) for v in val):
|
215
341
|
raise ClassiqValueError(
|
216
|
-
f"Quantum operand {
|
342
|
+
f"Quantum operand {param_name!r} cannot be initialized with a "
|
343
|
+
f"list of non-callables"
|
217
344
|
)
|
218
|
-
val = cast(
|
219
|
-
return [prepare_arg(arg_decl, v) for v in val]
|
345
|
+
val = cast(list[Union[QCallable, Callable[[Any], None]]], val)
|
346
|
+
return [prepare_arg(arg_decl, v, func_name, param_name) for v in val]
|
220
347
|
|
221
348
|
if not isinstance(val, QCallable):
|
222
|
-
|
223
|
-
|
224
|
-
|
225
|
-
|
226
|
-
|
227
|
-
|
228
|
-
|
229
|
-
|
349
|
+
if not callable(val):
|
350
|
+
raise ClassiqValueError(
|
351
|
+
f"Operand argument to {param_name!r} must be a callable object"
|
352
|
+
)
|
353
|
+
new_arg_decl = decl_without_type_attributes(arg_decl)
|
354
|
+
val = QLambdaFunction(new_arg_decl, val)
|
355
|
+
val.expand()
|
356
|
+
qlambda = QuantumLambdaFunction(
|
357
|
+
pos_rename_params=val.infer_rename_params(),
|
358
|
+
body=val.body,
|
359
|
+
)
|
360
|
+
if is_generative_mode():
|
361
|
+
qlambda.set_py_callable(val._py_callable)
|
362
|
+
return qlambda
|
363
|
+
|
364
|
+
if isinstance(val, QExpandable):
|
365
|
+
val.expand()
|
366
|
+
elif isinstance(val, QTerminalCallable):
|
367
|
+
return val.get_arg()
|
368
|
+
return val.func_decl.name
|
369
|
+
|
370
|
+
|
371
|
+
def _validate_classical_arg(
|
372
|
+
arg: Any, arg_decl: AnonClassicalParameterDeclaration, func_name: Optional[str]
|
373
|
+
) -> None:
|
374
|
+
is_native_or_compatible_type = not isinstance(
|
375
|
+
arg, (*NativePythonClassicalTypes, CParam, SymbolicExpr, Basic, PythonEnum)
|
376
|
+
) and not is_dataclass(
|
377
|
+
arg
|
378
|
+
) # type: ignore[unreachable]
|
379
|
+
try:
|
380
|
+
is_pydantic_classical_type = isinstance(
|
381
|
+
arg, pydantic.BaseModel
|
382
|
+
) and not isinstance(arg, PythonClassicalPydanticTypes)
|
383
|
+
except ClassiqValueError:
|
384
|
+
is_pydantic_classical_type = False
|
385
|
+
|
386
|
+
is_incompatible_symbolic_expr = isinstance(arg, SymbolicExpr) and arg.is_quantum
|
387
|
+
|
388
|
+
if (
|
389
|
+
is_native_or_compatible_type or is_pydantic_classical_type
|
390
|
+
) or is_incompatible_symbolic_expr:
|
391
|
+
func_name_message = f" of function {func_name!r}" if func_name else ""
|
392
|
+
raise ClassiqValueError(
|
393
|
+
f"Argument {str(arg)!r} to parameter {arg_decl.name!r}{func_name_message} "
|
394
|
+
f"has incompatible type; expected "
|
395
|
+
f"{get_qmod_type(arg_decl.classical_type).__name__}"
|
230
396
|
)
|
231
397
|
|
232
398
|
|
233
399
|
def _get_operand_hint_args(
|
234
|
-
func:
|
400
|
+
func: AnonQuantumFunctionDeclaration, param: AnonPositionalArg, param_value: str
|
235
401
|
) -> str:
|
236
402
|
return ", ".join(
|
237
403
|
[
|
@@ -240,50 +406,55 @@ def _get_operand_hint_args(
|
|
240
406
|
if decl.name == param.name
|
241
407
|
else f"{decl.name}=..."
|
242
408
|
)
|
243
|
-
for decl in func.
|
409
|
+
for decl in func.positional_arg_declarations
|
244
410
|
]
|
245
411
|
)
|
246
412
|
|
247
413
|
|
248
|
-
def _get_operand_hint(
|
414
|
+
def _get_operand_hint(
|
415
|
+
func: AnonQuantumFunctionDeclaration, param: AnonPositionalArg
|
416
|
+
) -> str:
|
249
417
|
return (
|
250
|
-
f"\nHint: To
|
251
|
-
f"
|
252
|
-
f"
|
253
|
-
f"
|
254
|
-
f"or a quantum function "
|
255
|
-
f"`{func.name}({_get_operand_hint_args(func, param, 'my_func')})`"
|
418
|
+
f"\nHint: To call a function under {func.name!r} use a lambda function as in "
|
419
|
+
f"'{func.name}({_get_operand_hint_args(func, param, 'lambda: f(q)')})' "
|
420
|
+
f"or pass the quantum function directly as in "
|
421
|
+
f"'{func.name}({_get_operand_hint_args(func, param, 'f')})'."
|
256
422
|
)
|
257
423
|
|
258
424
|
|
259
425
|
def _prepare_args(
|
260
|
-
decl:
|
261
|
-
) ->
|
426
|
+
decl: AnonQuantumFunctionDeclaration, arg_list: list[Any], kwargs: dict[str, Any]
|
427
|
+
) -> list[ArgValue]:
|
262
428
|
result = []
|
263
|
-
for arg_decl in decl.
|
429
|
+
for idx, arg_decl in enumerate(decl.positional_arg_declarations):
|
430
|
+
arg = None
|
264
431
|
if arg_list:
|
265
432
|
arg = arg_list.pop(0)
|
266
|
-
|
433
|
+
elif arg_decl.name is not None:
|
267
434
|
arg = kwargs.pop(mangle_keyword(arg_decl.name), None)
|
268
435
|
if arg is None:
|
269
|
-
|
270
|
-
|
271
|
-
|
272
|
-
|
436
|
+
if arg_decl.name is not None:
|
437
|
+
param_name = repr(arg_decl.name)
|
438
|
+
else:
|
439
|
+
param_name = f"#{idx + 1}"
|
440
|
+
error_message = f"Missing required argument for parameter {param_name}"
|
441
|
+
if isinstance(arg_decl, AnonQuantumOperandDeclaration):
|
273
442
|
error_message += _get_operand_hint(decl, arg_decl)
|
274
443
|
raise ClassiqValueError(error_message)
|
275
|
-
|
444
|
+
param_name = arg_decl.name if arg_decl.name is not None else f"#{idx + 1}"
|
445
|
+
result.append(prepare_arg(arg_decl, arg, decl.name, param_name))
|
276
446
|
|
277
447
|
return result
|
278
448
|
|
279
449
|
|
280
450
|
def _create_quantum_function_call(
|
281
451
|
decl_: QuantumFunctionDeclaration,
|
282
|
-
index_: Optional[Union[
|
452
|
+
index_: Optional[Union[CParamScalar, int]] = None,
|
453
|
+
source_ref_: Optional[SourceReference] = None,
|
283
454
|
*args: Any,
|
284
455
|
**kwargs: Any,
|
285
456
|
) -> QuantumFunctionCall:
|
286
|
-
arg_decls = decl_.
|
457
|
+
arg_decls = decl_.positional_arg_declarations
|
287
458
|
arg_list = list(args)
|
288
459
|
prepared_args = _prepare_args(decl_, arg_list, kwargs)
|
289
460
|
|
@@ -307,4 +478,6 @@ def _create_quantum_function_call(
|
|
307
478
|
index=Expression(expr=str(index_)), name=function_ident
|
308
479
|
)
|
309
480
|
|
310
|
-
return QuantumFunctionCall(
|
481
|
+
return QuantumFunctionCall(
|
482
|
+
function=function_ident, positional_args=prepared_args, source_ref=source_ref_
|
483
|
+
)
|