语义层(L4)¶
qaiji.core.semantics 是 L4 语义授权层:它在同一个 Circuit 之上
回答两个正交问题。分类(枚举、标注和注册表)回答"这个操作对测量统计
做了什么";保持性判决回答"变换后的电路,算符是否仍然(至多
差一个全局相位)等于原来的电路"。两者可以给出不同答案而互不矛盾——例如
RZ(2*pi) 在分类层归为 IDENTITY``(测量统计意义上的恒等),在判决层却判为
``UP_TO_PHASE``(算符差一个 ``-1 因子);这是两个独立坐标轴,不是同一个问题
答错了。本层不导入 qaiji.codec、OpenQASM 解析依赖或 numpy,由双门控的
导入纯度测试守护。本仓已有 L2 原生调度,但尚不生成硬件 ISA;L4 的
保持性判决不认证 L2 展开、资源或时序,后者由 L2 原生调度接口 的独立校验处理。
可运行的分类、摘要与哈希示例见 L4 语义摘要与保持性。
分类枚举与语义标注¶
- class qaiji.core.semantics.MorphismType(*values)[源代码]¶
一个操作施加在量子态上的变换种类。
- UNITARY = 'UNITARY'¶
- PERMUTATION = 'PERMUTATION'¶
- MEASUREMENT = 'MEASUREMENT'¶
- PHASE = 'PHASE'¶
- IDENTITY = 'IDENTITY'¶
- CLASSICAL_CTRL = 'CLASSICAL_CTRL'¶
- class qaiji.core.semantics.EquivLevel(*values)[源代码]¶
保持性裁决可以断言的等价强度。
只有
EXACT与UP_TO_PHASE是可判定的;UP_TO_LOCAL与ENTANGLEMENT是为后续层预留的词汇,会在判定入口处被拒绝。- EXACT = 'EXACT'¶
- UP_TO_PHASE = 'UP_TO_PHASE'¶
- UP_TO_LOCAL = 'UP_TO_LOCAL'¶
- ENTANGLEMENT = 'ENTANGLEMENT'¶
- class qaiji.core.semantics.CartanRole(*values)[源代码]¶
仅供参考的 Cartan 分解角色;绝不作为裁决的输入。
- K = 'K'¶
- A = 'A'¶
- MIXED = 'MIXED'¶
- NONE = 'NONE'¶
- class qaiji.core.semantics.ConditionModel(*values)[源代码]¶
电路的经典条件是如何被求值的。
FPROC_PLACEHOLDER没有任何生产路径 —— 它只是为多条件前馈预留 位置,而不是声称已经支持。- REGISTER_ALU = 'REGISTER_ALU'¶
- FPROC_PLACEHOLDER = 'FPROC_PLACEHOLDER'¶
- class qaiji.core.semantics.SemanticAnnotation(gate_index, morphism, equiv_level=None, cartan=CartanRole.NONE, body_offset=None, notes=())[源代码]¶
一个操作的语义含义,以及它在电路中的位置。
坐标遵循 INV-NUM 不变量:顶层节点是
(index, None);Conditional 体内的门是(父节点 index, offset)。body_offset为None和为0是两个不同的 节点,在序列化传输时绝不可混为一谈。示例
>>> from qaiji.core.semantics.annotation import SemanticAnnotation >>> from qaiji.core.semantics.types import MorphismType >>> SemanticAnnotation(gate_index=0, morphism=MorphismType.UNITARY).cartan <CartanRole.NONE: 'NONE'>
- 参数:
gate_index (int)
morphism (MorphismType)
equiv_level (EquivLevel | None)
cartan (CartanRole)
body_offset (int | None)
操作分类¶
- qaiji.core.semantics.classify_operation(op, *, gate_index=-1)[源代码]¶
将一个操作节点分类为一条或多条标注。
Gate 或 Measure 产出一条标注。Conditional 产出一条节点级的 CLASSICAL_CTRL 裁决,后面跟着体内每个门各一条标注、各自携带该门自身的态射:分支语义归属于 节点本身,因此改写体内标注会导致控制被重复计算,同时丢失分支实际执行的内容。
- 参数:
op (Gate | Measure | Conditional) -- 一个 Gate、Measure 或 Conditional 节点。
gate_index (int) -- 该节点在
Circuit.gates中的位置。默认值 -1 标记这是一次 游离探针;用它产出的结果不得拼接成序列(那种场景请用annotate_circuit)。
- 返回:
按位置顺序排列的标注。
- 抛出:
- 返回类型:
tuple[SemanticAnnotation, ...]
数据流:测量与条件读取¶
这里的边只按寄存器名连接测量与条件,即使条件出现在测量之前也会形成边; 它不证明因果顺序。读前写入与结果就绪时间由 L2 调度校验。
- class qaiji.core.semantics.MeasurementHandle(measurement_id, qubit_index, creg_name, creg_index, source='measure_node')[源代码]¶
指向某次测量的经典目的地的句柄。
- class qaiji.core.semantics.ClassicalEdge(source_handle, target, edge_kind='measurement_to_condition')[源代码]¶
从一次测量指向一个条件节点的声明式数据流边。
- qaiji.core.semantics.build_dataflow_summary(circuit)[源代码]¶
直接读取电路中一等公民的测量节点与条件节点。
只要测量句柄与条件节点共享同一个寄存器名,二者之间就连一条边;寄存器级条件 读取整个寄存器,因此写入该寄存器的每一个句柄都会被连上。这些边表达的是声明式 数据流,而非因果证明:即便某个 Conditional 在门序中排在与之匹配的 Measure 之前,边依然会连上 —— 顺序与因果属于 L2 调度层的议题,不由语义层判定。
- 参数:
circuit (Circuit) -- 待读取的电路。
- 返回:
一个 dict,含
measurement_handles,即MeasurementHandle元组;以及classical_edges,即ClassicalEdge元组 —— 都是带类型的值对象,尚未 JSON 编码;那一步投影是 summary.py 的职责,正如operations的编码也 归它所有。另含condition_model,取值为ConditionModel.REGISTER_ALU.value或None,始终存在;以及unitary_segment_count,即顶层 measure 数量 加一。- 返回类型:
摘要与规范身份哈希¶
- qaiji.core.semantics.SUMMARY_SCHEMA_VERSION = 'qaiji.semantic_summary.v0'¶
str(object='') -> str str(bytes_or_buffer[, encoding[, errors]]) -> str
Create a new string object from the given object. If encoding or errors is specified, then the object must expose a data buffer that will be decoded using the given encoding and error handler. Otherwise, returns the result of object.__str__() (if defined) or repr(object). encoding defaults to 'utf-8'. errors defaults to 'strict'.
- qaiji.core.semantics.GATE_COVERAGE_TOTAL = 19¶
int([x]) -> integer int(x, base=10) -> integer
Convert a number or string to an integer, or return 0 if no arguments are given. If x is a number, return x.__int__(). For floating-point numbers, this truncates towards zero.
If x is not a number or if base is given, then x must be a string, bytes, or bytearray instance representing an integer literal in the given base. The literal can be preceded by '+' or '-' and be surrounded by whitespace. The base defaults to 10. Valid bases are 0 and 2-36. Base 0 means to interpret the base from the string as an integer iteral. >>> int('0b100', base=0) 4
- qaiji.core.semantics.build_semantic_summary(*, circuit, annotations, status_label='available', source_language=None, preservation=None)[源代码]¶
构建一个电路的规范化、JSON 安全的语义摘要。
全部 14 个稳定键都无条件输出,包括空容器和
None:一个时有时无的键会让键的 漂移只能表现为哈希差异,而不是显式的键名差异,从而变得不可见。- 参数:
circuit (Circuit) -- 判别性键(num_qubits、cregs、operations)与 gate_coverage 的来源。
annotations (Sequence[SemanticAnnotation]) -- 该电路的语义标注,按
annotate_circuit的顺序排列。status_label (str) -- 取自
HandleStatus的值(本函数不做校验,按原样写入的 普通 str)。source_language (str | None) -- 可选的溯源标签。生产调用方保持为 None;只有测试会传入 具体值。
preservation (Mapping[str, Any] | None) -- 可选的保持性裁决载荷,给定时原样并入。
- 返回:
一个 JSON 安全的 dict,含 14 个稳定键,外加所有被赋值的可选键。
- 返回类型:
保持性判决与语义句柄¶
- class qaiji.core.semantics.PreservationSummary(stage='unspecified_transform', status='planned', diagnostic_count=0, failed_gate_indices=(), equiv_level=None, original_morphism=None, lowered_morphism=None, pass_trace_ref=None)[源代码]¶
针对一次受检变换的裁决,沿用上游的 8 字段形状。
示例
>>> from qaiji.core.semantics.preservation import PreservationSummary >>> from qaiji.core.semantics.types import EquivLevel >>> PreservationSummary(status="passed", equiv_level=EquivLevel.EXACT).status 'passed'
- 参数:
stage (str)
status (str)
diagnostic_count (int)
equiv_level (EquivLevel | None)
original_morphism (MorphismType | None)
lowered_morphism (MorphismType | None)
pass_trace_ref (str | None)
- qaiji.core.semantics.check_preservation(original, transformed, *, stage='unspecified_transform', requested_level=EquivLevel.UP_TO_PHASE)[源代码]¶
判定
transformed是否保持了original的算符语义。流水线是严格的优先级顺序:测量湮灭(第 1 步)压过判定域前置条件(第 2 步), 后者又压过逐位置的 R1-R4 比对(第 3-4 步)。任何落在可判定集合之外的情况一律 判为
unsupported,绝不给出一个静默错误的passed,见 I-Q4.6。- 参数:
original (Circuit) -- 变换前的电路。
transformed (Circuit) -- 变换后的电路。
stage (str) -- 本次裁决针对的是哪一个受检变换。
requested_level (EquivLevel) -- 调用方能接受的等价上限。
EXACT要求全局相位已抵消;UP_TO_PHASE为默认值,两者皆可接受。
- 返回:
一个
PreservationSummary,在包括failed/unsupported在内的每条 分支上都填好了诊断用的态射字段。- 抛出:
UnsupportedEquivLevelError --
requested_level为UP_TO_LOCAL或ENTANGLEMENT—— 本流水线无法判定。ValueError --
stage不属于已知的 stage 字面量(由本次调用构造的第一个 裁决在PreservationSummary.__post_init__中抛出)。
- 返回类型:
- class qaiji.core.semantics.SemanticIRHandle(schema_version='qaiji.semantic_ir_handle.v0', handle_id=None, producer=None, summary=<factory>, content_hash=None, status=HandleStatus.PLANNED)[源代码]¶
下游坍缩阶段消费的唯一对象:摘要、哈希与状态。
示例
>>> from qaiji.core.semantics.handle import SemanticIRHandle >>> SemanticIRHandle().status <HandleStatus.PLANNED: 'planned'>
- class qaiji.core.semantics.HandleStatus(*values)[源代码]¶
句柄摘要载荷的可用性状态。
只有四个取值,而非上游的五个:qaiji 不存在"不适用"的句柄场景,因此
NOT_APPLICABLE是被有意舍弃的。- AVAILABLE = 'available'¶
- PLANNED = 'planned'¶
- OMITTED = 'omitted'¶
- FAILED = 'failed'¶
- qaiji.core.semantics.freeze_summary(value)[源代码]¶
递归冻结一个 JSON 形状的映射,得到不可变树。
每个
Mapping变成MappingProxyType;每个list/tuple变成tuple。与本实现所借鉴的上游模型不同(上游把嵌套容器重建为新的、仍然可变的 list),这里的冻结是深度不可变的:真正做到这一点的是 tuple 转换,而不是某种 共享引用的取巧手法。
- qaiji.core.semantics.JSONValue¶
Type alias.
Type aliases are created through the type statement:
type Alias = int
In this example, Alias and int will be treated equivalently by static type checkers.
At runtime, Alias is an instance of TypeAliasType. The __name__ attribute holds the name of the type alias. The value of the type alias is stored in the __value__ attribute. It is evaluated lazily, so the value is computed only if the attribute is accessed.
Type aliases can also be generic:
type ListOrSet[T] = list[T] | set[T]
In this case, the type parameters of the alias are stored in the __type_params__ attribute.
See PEP 695 for more information.