qalgora-Q Docs Hub量子文档 ✦ Ask AI✦ 问问文档

The Compute-Action-Uncompute Pattern

A recurring quantum idiom runs, in circuit-execution order, compute → action → compute† (first U, then V, then U†). If you write it with the standard matrix convention where operators act on a state vector with the rightmost applied first, the overall operator is W = U† V U: U first maps the state into a working basis convenient for the action, V does the real work, then U† restores it. qalgora-Q captures this directly so the compiler can both insert the inverse for you and optimise the controlled version.

The pattern

qalgora.compute_action(compute, action) runs compute (U), then action (V), then automatically appends U†. You never write the uncompute step — it is synthesised from compute.

import qalgora

@qalgora.kernel
def kernel():
    q = qalgora.qvector(2)
    theta = 0.5

    def compute():            # U
        h(q[0])
        x.ctrl(q[0], q[1])

    def action():             # V
        rz(theta, q[1])

    # runs compute (U), then action (V), then compute-dagger (U†) automatically
    qalgora.compute_action(compute, action)

Why it pays off

The real win shows up under control. To build a controlled-W you do not need to control all of U, V and U† — controlling V alone suffices, because the U and U† halves cancel on the branch where the control is |0⟩. The compiler knows this and only controls the action, cutting gate count and circuit depth substantially.

This optimisation applies only when compute is a pure quantum subroutine that is reversible — no measurement, no reset, no randomness, and no I/O or host-side side effects.

A worked example
Grover's diffusion operator, phase-estimation rotations, and most oracle constructions are naturally compute-action-uncompute — expressing them this way lets the optimiser shrink the controlled forms it generates downstream.

计算-操作-逆计算模式

量子编程里有个反复出现的惯用写法:按电路执行顺序为 compute → action → compute†(先 U、再 V、最后 U†)。 若以"算符作用在态矢量上、最右者最先作用"的标准矩阵约定书写,整体算符为 W = U† V U。 先用 U 把态变换到便于 action 作用的工作基底,执行 V,再用 U† 还原。qalgora-Q 能直接表达这种结构, 于是编译器既能替你自动补上逆操作,又能优化它的受控版本。

该模式

qalgora.compute_action(compute, action) 先跑 compute(U),再跑 action(V),然后自动接上 U†。逆计算这一步不用你写——它会从 compute 自动综合出来。

import qalgora

@qalgora.kernel
def kernel():
    q = qalgora.qvector(2)
    theta = 0.5

    def compute():            # U
        h(q[0])
        x.ctrl(q[0], q[1])

    def action():             # V
        rz(theta, q[1])

    # 先 compute(U),再 action(V),最后自动接上 compute 的共轭(U†)
    qalgora.compute_action(compute, action)

它的价值所在

真正的好处在受控操作上。要构造受控 W,你用对 U、V、U† 全都加控制—— 只控制 V 就够了,因为在控制位为 |0⟩ 的分支里,U 和 U† 这两半会相互抵消。编译器 懂得这一点,只给 action 部分加控制,从而大幅减少门的数量和电路深度。

该优化仅适用于 compute 是可逆、无测量、无 reset、无随机数、无 I/O 或主机端副作用的纯量子子程序。

一个实例
Grover 扩散算符、相位估计里的旋转,以及大多数 oracle 构造,本质上都是 计算-操作-逆计算结构——这样表达出来,优化器就能在下游把它们的受控形式化简掉。