classiq 0.82.1__py3-none-any.whl → 0.84.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/_internals/api_wrapper.py +27 -0
- classiq/applications/chemistry/chemistry_model_constructor.py +2 -4
- classiq/applications/chemistry/hartree_fock.py +68 -0
- classiq/applications/chemistry/mapping.py +85 -0
- classiq/applications/chemistry/op_utils.py +79 -0
- classiq/applications/chemistry/problems.py +195 -0
- classiq/applications/chemistry/ucc.py +109 -0
- classiq/applications/chemistry/z2_symmetries.py +368 -0
- classiq/applications/combinatorial_helpers/pauli_helpers/pauli_utils.py +30 -1
- classiq/applications/combinatorial_optimization/combinatorial_optimization_model_constructor.py +2 -2
- classiq/{model_expansions/evaluators → evaluators}/arg_type_match.py +12 -4
- classiq/{model_expansions/evaluators → evaluators}/argument_types.py +3 -3
- classiq/{model_expansions/evaluators → evaluators}/classical_expression.py +1 -1
- classiq/{model_expansions/evaluators → evaluators}/classical_type_inference.py +3 -4
- classiq/{model_expansions/evaluators → evaluators}/parameter_types.py +17 -15
- classiq/execution/__init__.py +12 -1
- classiq/execution/execution_session.py +189 -43
- classiq/execution/jobs.py +26 -1
- classiq/execution/qnn.py +2 -2
- classiq/execution/user_budgets.py +39 -0
- classiq/interface/_version.py +1 -1
- classiq/interface/constants.py +1 -0
- classiq/interface/execution/primitives.py +29 -1
- classiq/interface/executor/estimate_cost.py +35 -0
- classiq/interface/executor/execution_result.py +13 -0
- classiq/interface/executor/result.py +116 -1
- classiq/interface/executor/user_budget.py +26 -33
- classiq/interface/generator/application_apis/finance_declarations.py +3 -3
- classiq/interface/generator/expressions/atomic_expression_functions.py +11 -3
- classiq/interface/generator/expressions/proxies/classical/any_classical_value.py +0 -6
- classiq/interface/generator/functions/classical_type.py +2 -35
- classiq/interface/generator/functions/concrete_types.py +0 -3
- classiq/interface/generator/functions/type_modifier.py +22 -0
- classiq/interface/generator/generated_circuit_data.py +5 -16
- classiq/interface/generator/model/model.py +8 -0
- classiq/interface/generator/quantum_program.py +0 -13
- classiq/interface/generator/types/compilation_metadata.py +0 -3
- classiq/interface/helpers/model_normalizer.py +2 -2
- classiq/interface/ide/visual_model.py +6 -2
- classiq/interface/model/model.py +12 -7
- classiq/interface/model/port_declaration.py +4 -2
- classiq/interface/pretty_print/__init__.py +0 -0
- classiq/{qmod/native → interface/pretty_print}/expression_to_qmod.py +18 -11
- classiq/interface/server/routes.py +4 -0
- classiq/model_expansions/atomic_expression_functions_defs.py +42 -5
- classiq/model_expansions/capturing/captured_vars.py +21 -8
- classiq/model_expansions/interpreters/base_interpreter.py +3 -3
- classiq/model_expansions/quantum_operations/allocate.py +1 -1
- classiq/model_expansions/quantum_operations/assignment_result_processor.py +1 -1
- classiq/model_expansions/quantum_operations/bind.py +2 -2
- classiq/model_expansions/quantum_operations/call_emitter.py +42 -36
- classiq/model_expansions/quantum_operations/variable_decleration.py +1 -1
- classiq/model_expansions/scope_initialization.py +3 -3
- classiq/model_expansions/transformers/model_renamer.py +16 -5
- classiq/model_expansions/transformers/{type_qualifier_inference.py → type_modifier_inference.py} +134 -100
- classiq/model_expansions/visitors/symbolic_param_inference.py +10 -7
- classiq/open_library/functions/__init__.py +3 -0
- classiq/open_library/functions/amplitude_amplification.py +10 -18
- classiq/open_library/functions/discrete_sine_cosine_transform.py +5 -5
- classiq/open_library/functions/grover.py +14 -6
- classiq/open_library/functions/modular_exponentiation.py +22 -20
- classiq/open_library/functions/state_preparation.py +18 -1
- classiq/qmod/__init__.py +2 -2
- classiq/qmod/builtins/enums.py +23 -0
- classiq/qmod/builtins/functions/__init__.py +2 -0
- classiq/qmod/builtins/functions/allocation.py +2 -2
- classiq/qmod/builtins/functions/arithmetic.py +16 -8
- classiq/qmod/builtins/functions/exponentiation.py +32 -4
- classiq/qmod/builtins/functions/standard_gates.py +7 -7
- classiq/qmod/builtins/structs.py +55 -3
- classiq/qmod/declaration_inferrer.py +8 -7
- classiq/qmod/native/pretty_printer.py +7 -11
- classiq/qmod/pretty_print/expression_to_python.py +2 -1
- classiq/qmod/pretty_print/pretty_printer.py +7 -12
- classiq/qmod/python_classical_type.py +12 -5
- classiq/qmod/qfunc.py +1 -1
- classiq/qmod/qmod_constant.py +2 -5
- classiq/qmod/qmod_parameter.py +2 -5
- classiq/qmod/qmod_variable.py +66 -25
- classiq/qmod/quantum_expandable.py +4 -2
- classiq/qmod/quantum_function.py +7 -2
- classiq/qmod/semantics/annotation/qstruct_annotator.py +1 -1
- classiq/qmod/semantics/validation/main_validation.py +1 -9
- classiq/qmod/semantics/validation/type_hints.py +9 -9
- classiq/qmod/utilities.py +0 -2
- classiq/qmod/write_qmod.py +1 -1
- classiq/synthesis.py +0 -2
- {classiq-0.82.1.dist-info → classiq-0.84.0.dist-info}/METADATA +4 -1
- {classiq-0.82.1.dist-info → classiq-0.84.0.dist-info}/RECORD +95 -86
- classiq/interface/generator/functions/type_qualifier.py +0 -22
- /classiq/{model_expansions/evaluators → evaluators}/__init__.py +0 -0
- /classiq/{model_expansions/evaluators → evaluators}/control.py +0 -0
- /classiq/{model_expansions → evaluators}/expression_evaluator.py +0 -0
- /classiq/{model_expansions/evaluators → evaluators}/quantum_type_utils.py +0 -0
- /classiq/{model_expansions/evaluators → evaluators}/type_type_match.py +0 -0
- {classiq-0.82.1.dist-info → classiq-0.84.0.dist-info}/WHEEL +0 -0
@@ -31,7 +31,9 @@ CARRAY_ERROR_MESSAGE = (
|
|
31
31
|
|
32
32
|
|
33
33
|
class PythonClassicalType:
|
34
|
-
def convert(
|
34
|
+
def convert(
|
35
|
+
self, py_type: type, nested: bool = False
|
36
|
+
) -> Optional[ConcreteClassicalType]:
|
35
37
|
if py_type is int:
|
36
38
|
return Integer().set_generative()
|
37
39
|
elif py_type is CInt:
|
@@ -45,16 +47,18 @@ class PythonClassicalType:
|
|
45
47
|
elif py_type is CBool:
|
46
48
|
return Bool()
|
47
49
|
elif get_origin(py_type) is list:
|
48
|
-
element_type = self.convert(get_args(py_type)[0])
|
50
|
+
element_type = self.convert(get_args(py_type)[0], nested=True)
|
49
51
|
if element_type is not None:
|
50
52
|
return ClassicalArray(element_type=element_type).set_generative()
|
51
53
|
elif get_origin(py_type) is CArray:
|
52
54
|
array_args = version_portable_get_args(py_type)
|
53
55
|
if len(array_args) == 1:
|
54
|
-
return ClassicalArray(
|
56
|
+
return ClassicalArray(
|
57
|
+
element_type=self.convert(array_args[0], nested=True)
|
58
|
+
)
|
55
59
|
elif len(array_args) == 2:
|
56
60
|
return ClassicalArray(
|
57
|
-
element_type=self.convert(array_args[0]),
|
61
|
+
element_type=self.convert(array_args[0], nested=True),
|
58
62
|
length=Expression(expr=get_type_hint_expr(array_args[1])),
|
59
63
|
)
|
60
64
|
raise ClassiqValueError(CARRAY_ERROR_MESSAGE)
|
@@ -62,7 +66,10 @@ class PythonClassicalType:
|
|
62
66
|
return self.register_struct(py_type)
|
63
67
|
elif inspect.isclass(py_type) and isinstance(py_type, EnumMeta):
|
64
68
|
self.register_enum(py_type)
|
65
|
-
|
69
|
+
enum_type = Enum(name=py_type.__name__)
|
70
|
+
if not nested:
|
71
|
+
enum_type.set_generative()
|
72
|
+
return enum_type
|
66
73
|
elif py_type in (CArray, list):
|
67
74
|
raise ClassiqValueError(CARRAY_ERROR_MESSAGE)
|
68
75
|
return None
|
classiq/qmod/qfunc.py
CHANGED
@@ -107,6 +107,6 @@ def _validate_directives(
|
|
107
107
|
if synthesize_separately:
|
108
108
|
error_msg += "External functions can't be marked as synthesized separately. \n"
|
109
109
|
if unchecked is not None and len(unchecked) > 0:
|
110
|
-
error_msg += "External functions can't have unchecked
|
110
|
+
error_msg += "External functions can't have unchecked modifiers."
|
111
111
|
if error_msg:
|
112
112
|
raise ClassiqInternalError(error_msg)
|
classiq/qmod/qmod_constant.py
CHANGED
@@ -5,10 +5,7 @@ from typing import TYPE_CHECKING, Any, Optional, cast, get_origin
|
|
5
5
|
from classiq.interface.exceptions import ClassiqError, ClassiqValueError
|
6
6
|
from classiq.interface.generator.constant import Constant
|
7
7
|
from classiq.interface.generator.expressions.expression import Expression
|
8
|
-
from classiq.interface.generator.functions.classical_type import
|
9
|
-
ClassicalArray,
|
10
|
-
ClassicalList,
|
11
|
-
)
|
8
|
+
from classiq.interface.generator.functions.classical_type import ClassicalArray
|
12
9
|
|
13
10
|
from classiq.qmod.cparam import CArray, CParamScalar
|
14
11
|
from classiq.qmod.declaration_inferrer import python_type_to_qmod
|
@@ -118,7 +115,7 @@ class QConstant(SymbolicExpr):
|
|
118
115
|
if qmod_type is None:
|
119
116
|
raise ClassiqError("Invalid QMOD type")
|
120
117
|
|
121
|
-
if not isinstance(qmod_type,
|
118
|
+
if not isinstance(qmod_type, ClassicalArray):
|
122
119
|
raise ClassiqError("Invalid subscript to non-list constant")
|
123
120
|
|
124
121
|
return CParamList(
|
classiq/qmod/qmod_parameter.py
CHANGED
@@ -4,7 +4,6 @@ from classiq.interface.exceptions import ClassiqInternalError, ClassiqValueError
|
|
4
4
|
from classiq.interface.generator.functions.classical_type import (
|
5
5
|
Bool,
|
6
6
|
ClassicalArray,
|
7
|
-
ClassicalList,
|
8
7
|
ClassicalTuple,
|
9
8
|
ClassicalType,
|
10
9
|
Integer,
|
@@ -42,7 +41,7 @@ class CParamList(CParam):
|
|
42
41
|
def __init__(
|
43
42
|
self,
|
44
43
|
expr: str,
|
45
|
-
list_type: Union[
|
44
|
+
list_type: Union[ClassicalArray, ClassicalTuple],
|
46
45
|
qmodule: ModelStateContainer,
|
47
46
|
) -> None:
|
48
47
|
super().__init__(expr)
|
@@ -149,7 +148,7 @@ def create_param(
|
|
149
148
|
decl = ctype.classical_struct_decl
|
150
149
|
ctype = Struct(name=ctype.name)
|
151
150
|
ctype.set_classical_struct_decl(decl)
|
152
|
-
if isinstance(ctype, (
|
151
|
+
if isinstance(ctype, (ClassicalArray, ClassicalTuple)):
|
153
152
|
return CParamList(expr_str, ctype, qmodule=qmodule)
|
154
153
|
elif isinstance(ctype, Struct):
|
155
154
|
return CParamStruct(expr_str, ctype, qmodule=qmodule)
|
@@ -164,8 +163,6 @@ def get_qmod_type(ctype: ClassicalType) -> type:
|
|
164
163
|
return CReal
|
165
164
|
elif isinstance(ctype, Bool):
|
166
165
|
return CBool
|
167
|
-
elif isinstance(ctype, ClassicalList):
|
168
|
-
return CArray[get_qmod_type(ctype.element_type)] # type: ignore[misc]
|
169
166
|
elif isinstance(ctype, ClassicalArray):
|
170
167
|
if ctype.length is None:
|
171
168
|
return CArray[get_qmod_type(ctype.element_type)] # type: ignore[misc]
|
classiq/qmod/qmod_variable.py
CHANGED
@@ -34,19 +34,20 @@ from classiq.interface.generator.expressions.proxies.quantum.qmod_qarray_proxy i
|
|
34
34
|
ILLEGAL_SLICE_MSG,
|
35
35
|
ILLEGAL_SLICING_STEP_MSG,
|
36
36
|
)
|
37
|
+
from classiq.interface.generator.functions.concrete_types import ConcreteQuantumType
|
37
38
|
from classiq.interface.generator.functions.port_declaration import (
|
38
39
|
PortDeclarationDirection,
|
39
40
|
)
|
40
|
-
from classiq.interface.generator.functions.
|
41
|
-
from classiq.interface.generator.functions.
|
41
|
+
from classiq.interface.generator.functions.type_modifier import TypeModifier
|
42
|
+
from classiq.interface.generator.functions.type_name import Struct, TypeName
|
42
43
|
from classiq.interface.generator.types.qstruct_declaration import QStructDeclaration
|
44
|
+
from classiq.interface.helpers.classproperty import classproperty
|
43
45
|
from classiq.interface.model.handle_binding import (
|
44
46
|
FieldHandleBinding,
|
45
47
|
HandleBinding,
|
46
48
|
SlicedHandleBinding,
|
47
49
|
SubscriptHandleBinding,
|
48
50
|
)
|
49
|
-
from classiq.interface.model.port_declaration import AnonPortDeclaration
|
50
51
|
from classiq.interface.model.quantum_expressions.amplitude_loading_operation import (
|
51
52
|
AmplitudeLoadingOperation,
|
52
53
|
)
|
@@ -136,7 +137,7 @@ class QVar(Symbolic):
|
|
136
137
|
return self._base_handle
|
137
138
|
|
138
139
|
@abc.abstractmethod
|
139
|
-
def get_qmod_type(self) ->
|
140
|
+
def get_qmod_type(self) -> ConcreteQuantumType:
|
140
141
|
raise NotImplementedError()
|
141
142
|
|
142
143
|
@classmethod
|
@@ -164,15 +165,23 @@ class QVar(Symbolic):
|
|
164
165
|
return self.get_qmod_type().type_name
|
165
166
|
|
166
167
|
|
168
|
+
class QmodExpressionCreator(Protocol):
|
169
|
+
"""
|
170
|
+
A callable that creates a Qmod expression from the provided QVars.
|
171
|
+
"""
|
172
|
+
|
173
|
+
def __call__(self, **kwargs: QVar) -> SymbolicExpr: ...
|
174
|
+
|
175
|
+
|
167
176
|
_Q = TypeVar("_Q", bound=QVar)
|
168
177
|
Output = Annotated[_Q, PortDeclarationDirection.Output]
|
169
178
|
Input = Annotated[_Q, PortDeclarationDirection.Input]
|
170
179
|
Const = Annotated[
|
171
|
-
_Q,
|
180
|
+
_Q, TypeModifier.Const
|
172
181
|
] # A constant variable, up to a phase dependent on the computational basis state
|
173
|
-
|
174
|
-
_Q,
|
175
|
-
] # A quantum free variable, up to a phase dependent on the computational basis state
|
182
|
+
Permutable = Annotated[
|
183
|
+
_Q, TypeModifier.Permutable
|
184
|
+
] # A permutable ("quantum free") variable, up to a phase dependent on the computational basis state
|
176
185
|
|
177
186
|
|
178
187
|
class QScalar(QVar, SymbolicExpr):
|
@@ -273,7 +282,7 @@ class QBit(QScalar):
|
|
273
282
|
) -> "QBit":
|
274
283
|
return QBit(origin, _expr_str=expr_str)
|
275
284
|
|
276
|
-
def get_qmod_type(self) ->
|
285
|
+
def get_qmod_type(self) -> ConcreteQuantumType:
|
277
286
|
return QuantumBit()
|
278
287
|
|
279
288
|
|
@@ -329,7 +338,7 @@ class QNum(Generic[_P], QScalar):
|
|
329
338
|
) -> "QNum":
|
330
339
|
return QNum(origin, *_get_qnum_attributes(type_hint), _expr_str=expr_str)
|
331
340
|
|
332
|
-
def get_qmod_type(self) ->
|
341
|
+
def get_qmod_type(self) -> ConcreteQuantumType:
|
333
342
|
return QuantumNumeric(
|
334
343
|
size=self._size,
|
335
344
|
is_signed=self._is_signed,
|
@@ -498,8 +507,15 @@ class QStruct(QVar):
|
|
498
507
|
setattr(self, field_name, var)
|
499
508
|
super().__init__(name, expr_str=_expr_str)
|
500
509
|
|
501
|
-
def get_qmod_type(self) ->
|
502
|
-
|
510
|
+
def get_qmod_type(self) -> ConcreteQuantumType:
|
511
|
+
classical_type = Struct(name=self._struct_name)
|
512
|
+
classical_type.set_fields(
|
513
|
+
{
|
514
|
+
field_name: field_var.get_qmod_type()
|
515
|
+
for field_name, field_var in self._fields.items()
|
516
|
+
}
|
517
|
+
)
|
518
|
+
return classical_type
|
503
519
|
|
504
520
|
@classmethod
|
505
521
|
def to_qvar(
|
@@ -529,9 +545,23 @@ class QStruct(QVar):
|
|
529
545
|
_expr_str=expr_str,
|
530
546
|
)
|
531
547
|
|
548
|
+
@classproperty
|
549
|
+
def num_qubits(cls) -> int: # noqa: N805
|
550
|
+
"""
|
551
|
+
The total number of qubits in this quantum struct.
|
552
|
+
Raises an error if the struct doesn't have a fixed size.
|
553
|
+
"""
|
554
|
+
qvar = cls.to_qvar(HandleBinding(name="dummy"), type_hint=cls, expr_str=None)
|
555
|
+
quantum_type = qvar.get_qmod_type()
|
556
|
+
if not quantum_type.has_size_in_bits:
|
557
|
+
raise ClassiqValueError(
|
558
|
+
f"Could not infer the size of struct {qvar._struct_name!r}"
|
559
|
+
)
|
560
|
+
return quantum_type.size_in_bits
|
561
|
+
|
532
562
|
|
533
|
-
def
|
534
|
-
return _create_qvar_for_qtype(
|
563
|
+
def create_qvar_from_quantum_type(quantum_type: ConcreteQuantumType, name: str) -> QVar:
|
564
|
+
return _create_qvar_for_qtype(quantum_type, HandleBinding(name=name))
|
535
565
|
|
536
566
|
|
537
567
|
def _create_qvar_for_qtype(
|
@@ -592,21 +622,21 @@ def get_qvar(qtype: QuantumType, origin: HandleBinding) -> "QVar":
|
|
592
622
|
|
593
623
|
def get_port_from_type_hint(
|
594
624
|
py_type: Any,
|
595
|
-
) -> tuple[QuantumType, PortDeclarationDirection,
|
625
|
+
) -> tuple[QuantumType, PortDeclarationDirection, TypeModifier]:
|
596
626
|
direction = PortDeclarationDirection.Inout # default
|
597
|
-
|
627
|
+
modifier = TypeModifier.Mutable # default
|
598
628
|
|
599
629
|
if isinstance(py_type, _AnnotatedAlias):
|
600
630
|
quantum_type = _to_quantum_type(py_type.__origin__)
|
601
631
|
for metadata in py_type.__metadata__:
|
602
632
|
if isinstance(metadata, PortDeclarationDirection):
|
603
633
|
direction = metadata
|
604
|
-
elif isinstance(metadata,
|
605
|
-
|
634
|
+
elif isinstance(metadata, TypeModifier):
|
635
|
+
modifier = metadata
|
606
636
|
else:
|
607
637
|
quantum_type = _to_quantum_type(py_type)
|
608
638
|
|
609
|
-
return quantum_type, direction,
|
639
|
+
return quantum_type, direction, modifier
|
610
640
|
|
611
641
|
|
612
642
|
def _to_quantum_type(py_type: Any) -> QuantumType:
|
@@ -689,17 +719,27 @@ def _get_quantum_bit_vector(type_hint: type[QArray]) -> QuantumBitvector:
|
|
689
719
|
return QuantumBitvector(element_type=element_type, length=length_expr)
|
690
720
|
|
691
721
|
|
692
|
-
def _get_quantum_struct(type_hint: type[QStruct]) ->
|
693
|
-
_register_qstruct(type_hint, qmodule=QMODULE)
|
694
|
-
|
722
|
+
def _get_quantum_struct(type_hint: type[QStruct]) -> Struct:
|
723
|
+
decl = _register_qstruct(type_hint, qmodule=QMODULE)
|
724
|
+
classical_type = Struct(name=type_hint.__name__)
|
725
|
+
if decl is not None:
|
726
|
+
classical_type.set_fields(
|
727
|
+
{
|
728
|
+
field_name: field_type.model_copy(deep=True)
|
729
|
+
for field_name, field_type in decl.fields.items()
|
730
|
+
}
|
731
|
+
)
|
732
|
+
return classical_type
|
695
733
|
|
696
734
|
|
697
735
|
def _register_qstruct(
|
698
736
|
type_hint: type[QStruct], *, qmodule: ModelStateContainer
|
699
|
-
) ->
|
737
|
+
) -> Optional[QStructDeclaration]:
|
700
738
|
struct_name = type_hint.__name__
|
701
|
-
if type_hint is QStruct
|
702
|
-
return
|
739
|
+
if type_hint is QStruct:
|
740
|
+
return None
|
741
|
+
if struct_name in qmodule.qstruct_decls:
|
742
|
+
return qmodule.qstruct_decls[struct_name]
|
703
743
|
|
704
744
|
# temp assignment for recursive qstruct definitions
|
705
745
|
qmodule.qstruct_decls[struct_name] = QStructDeclaration(name=struct_name)
|
@@ -714,6 +754,7 @@ def _register_qstruct(
|
|
714
754
|
qmodule.qstruct_decls[struct_name] = struct_decl
|
715
755
|
QStructAnnotator().visit(struct_decl)
|
716
756
|
validate_qstruct(struct_decl)
|
757
|
+
return struct_decl
|
717
758
|
|
718
759
|
|
719
760
|
def _validate_fields(type_hint: type[QStruct]) -> None:
|
@@ -68,7 +68,7 @@ from classiq.qmod.qmod_parameter import (
|
|
68
68
|
)
|
69
69
|
from classiq.qmod.qmod_variable import (
|
70
70
|
QVar,
|
71
|
-
|
71
|
+
create_qvar_from_quantum_type,
|
72
72
|
)
|
73
73
|
from classiq.qmod.quantum_callable import QCallable, QExpandableInterface
|
74
74
|
from classiq.qmod.symbolic_expr import SymbolicExpr
|
@@ -163,7 +163,9 @@ class QExpandable(QCallable, QExpandableInterface, ABC):
|
|
163
163
|
create_param(actual_name, arg.classical_type, self._qmodule)
|
164
164
|
)
|
165
165
|
elif isinstance(arg, AnonPortDeclaration):
|
166
|
-
result.append(
|
166
|
+
result.append(
|
167
|
+
create_qvar_from_quantum_type(arg.quantum_type, actual_name)
|
168
|
+
)
|
167
169
|
else:
|
168
170
|
assert isinstance(arg, AnonQuantumOperandDeclaration)
|
169
171
|
result.append(QTerminalCallable(arg, idx))
|
classiq/qmod/quantum_function.py
CHANGED
@@ -101,7 +101,12 @@ class QFunc(BaseQFunc):
|
|
101
101
|
) -> None:
|
102
102
|
_validate_no_gen_params(py_callable.__annotations__)
|
103
103
|
super().__init__(py_callable, compilation_metadata)
|
104
|
-
|
104
|
+
if compilation_metadata is not None and compilation_metadata.unchecked:
|
105
|
+
self.compilation_metadata: Optional[CompilationMetadata] = (
|
106
|
+
CompilationMetadata(unchecked=compilation_metadata.unchecked)
|
107
|
+
)
|
108
|
+
else:
|
109
|
+
self.compilation_metadata = None
|
105
110
|
|
106
111
|
@property
|
107
112
|
def func_decl(self) -> NamedParamsQuantumFunctionDeclaration:
|
@@ -261,7 +266,7 @@ class GenerativeQFunc(BaseQFunc):
|
|
261
266
|
|
262
267
|
def __call__(self, *args: Any, **kwargs: Any) -> None:
|
263
268
|
if get_global_declarative_switch():
|
264
|
-
return QFunc(self._py_callable)(*args, **kwargs)
|
269
|
+
return QFunc(self._py_callable, self.compilation_metadata)(*args, **kwargs)
|
265
270
|
if self.func_decl.name not in self._qmodule.generative_functions:
|
266
271
|
self._qmodule.generative_functions[self.func_decl.name] = self
|
267
272
|
if self._func_decl is None:
|
@@ -45,7 +45,7 @@ class QStructAnnotator(ModelVisitor):
|
|
45
45
|
return
|
46
46
|
self._visited.add(type_name)
|
47
47
|
new_fields = {
|
48
|
-
field_name: field_type.model_copy()
|
48
|
+
field_name: field_type.model_copy(deep=True)
|
49
49
|
for field_name, field_type in decl.variables.items()
|
50
50
|
}
|
51
51
|
self.visit(new_fields)
|
@@ -1,8 +1,5 @@
|
|
1
1
|
from classiq.interface.exceptions import ClassiqExpansionError, ClassiqValueError
|
2
|
-
from classiq.interface.generator.functions.classical_type import
|
3
|
-
ClassicalArray,
|
4
|
-
ClassicalList,
|
5
|
-
)
|
2
|
+
from classiq.interface.generator.functions.classical_type import ClassicalArray
|
6
3
|
from classiq.interface.generator.functions.concrete_types import ConcreteClassicalType
|
7
4
|
from classiq.interface.generator.functions.port_declaration import (
|
8
5
|
PortDeclarationDirection,
|
@@ -31,11 +28,6 @@ def _validate_main_param(param: PositionalArg) -> None:
|
|
31
28
|
def _validate_main_classical_param_type(
|
32
29
|
param: ConcreteClassicalType, param_name: str
|
33
30
|
) -> None:
|
34
|
-
if isinstance(param, ClassicalList):
|
35
|
-
raise ClassiqExpansionError(
|
36
|
-
f"Classical array parameter {param_name!r} of function 'main' must "
|
37
|
-
f"specify array length",
|
38
|
-
)
|
39
31
|
if isinstance(param, ClassicalArray):
|
40
32
|
if param.length is None:
|
41
33
|
raise ClassiqExpansionError(
|
@@ -6,7 +6,7 @@ from classiq.interface.exceptions import ClassiqValueError
|
|
6
6
|
from classiq.interface.generator.functions.port_declaration import (
|
7
7
|
PortDeclarationDirection,
|
8
8
|
)
|
9
|
-
from classiq.interface.generator.functions.
|
9
|
+
from classiq.interface.generator.functions.type_modifier import TypeModifier
|
10
10
|
|
11
11
|
|
12
12
|
def validate_annotation(type_hint: Any) -> None:
|
@@ -17,12 +17,12 @@ def validate_annotation(type_hint: Any) -> None:
|
|
17
17
|
for direction in type_hint.__metadata__
|
18
18
|
if isinstance(direction, PortDeclarationDirection)
|
19
19
|
]
|
20
|
-
|
21
|
-
|
22
|
-
for
|
23
|
-
if isinstance(
|
20
|
+
modifiers: list[TypeModifier] = [
|
21
|
+
modifier
|
22
|
+
for modifier in type_hint.__metadata__
|
23
|
+
if isinstance(modifier, TypeModifier)
|
24
24
|
]
|
25
|
-
if len(directions) <= 1 and len(
|
25
|
+
if len(directions) <= 1 and len(modifiers) <= 1:
|
26
26
|
return
|
27
27
|
error_message = ""
|
28
28
|
if len(directions) > 1:
|
@@ -30,9 +30,9 @@ def validate_annotation(type_hint: Any) -> None:
|
|
30
30
|
f"Multiple directions are not allowed in a single type hint: "
|
31
31
|
f"[{', '.join(direction.name for direction in reversed(directions))}]\n"
|
32
32
|
)
|
33
|
-
if len(
|
33
|
+
if len(modifiers) > 1:
|
34
34
|
error_message += (
|
35
|
-
f"Multiple
|
36
|
-
f"[{', '.join(
|
35
|
+
f"Multiple modifiers are not allowed in a single type hint: "
|
36
|
+
f"[{', '.join(modifier.name for modifier in reversed(modifiers))}]\n"
|
37
37
|
)
|
38
38
|
raise ClassiqValueError(error_message)
|
classiq/qmod/utilities.py
CHANGED
classiq/qmod/write_qmod.py
CHANGED
@@ -2,12 +2,12 @@ import json
|
|
2
2
|
from pathlib import Path
|
3
3
|
from typing import Optional, Union
|
4
4
|
|
5
|
+
from classiq.interface.constants import DEFAULT_DECIMAL_PRECISION
|
5
6
|
from classiq.interface.model.model import Model, SerializedModel
|
6
7
|
|
7
8
|
from classiq.qmod.global_declarative_switch import set_global_declarative_switch
|
8
9
|
from classiq.qmod.native.pretty_printer import DSLPrettyPrinter
|
9
10
|
from classiq.qmod.quantum_function import GenerativeQFunc, QFunc
|
10
|
-
from classiq.qmod.utilities import DEFAULT_DECIMAL_PRECISION
|
11
11
|
|
12
12
|
_QMOD_SUFFIX = "qmod"
|
13
13
|
_SYNTHESIS_OPTIONS_SUFFIX = "synthesis_options.json"
|
classiq/synthesis.py
CHANGED
@@ -13,8 +13,6 @@ from classiq._internals.api_wrapper import ApiWrapper
|
|
13
13
|
from classiq.qmod.create_model_function import add_entry_point
|
14
14
|
from classiq.qmod.quantum_function import BaseQFunc
|
15
15
|
|
16
|
-
SerializedQuantumProgram = QuantumProgram
|
17
|
-
|
18
16
|
|
19
17
|
def show(quantum_program: QuantumProgram, display_url: bool = True) -> None:
|
20
18
|
"""
|
@@ -1,6 +1,6 @@
|
|
1
1
|
Metadata-Version: 2.3
|
2
2
|
Name: classiq
|
3
|
-
Version: 0.
|
3
|
+
Version: 0.84.0
|
4
4
|
Summary: Classiq's Python SDK for quantum computing
|
5
5
|
License: Proprietary
|
6
6
|
Keywords: quantum computing,quantum circuits,quantum algorithms,QAD,QDL
|
@@ -27,6 +27,7 @@ Classifier: Topic :: Software Development :: Compilers
|
|
27
27
|
Classifier: Topic :: Software Development :: Libraries :: Python Modules
|
28
28
|
Classifier: Typing :: Typed
|
29
29
|
Provides-Extra: analyzer-sdk
|
30
|
+
Provides-Extra: chemistry
|
30
31
|
Provides-Extra: qml
|
31
32
|
Requires-Dist: ConfigArgParse (>=1.5.3,<2.0.0)
|
32
33
|
Requires-Dist: Pyomo (>=6.5,<6.6)
|
@@ -41,6 +42,8 @@ Requires-Dist: notebook ; extra == "analyzer-sdk"
|
|
41
42
|
Requires-Dist: numexpr (>=2.7.3,<3.0.0)
|
42
43
|
Requires-Dist: numpy (>=1.20.1,<2.0.0) ; python_version < "3.12"
|
43
44
|
Requires-Dist: numpy (>=1.26.0,<2.0.0) ; python_version >= "3.12"
|
45
|
+
Requires-Dist: openfermion ; extra == "chemistry"
|
46
|
+
Requires-Dist: openfermionpyscf ; extra == "chemistry"
|
44
47
|
Requires-Dist: packaging (>=23.2,<24.0)
|
45
48
|
Requires-Dist: pandas (>=1.4.0,<3.0.0)
|
46
49
|
Requires-Dist: plotly (>=5.7.0,<6.0.0)
|