Skip to content

Quantum types

euqalyptus.types.quantum exposes three qubit-flavored classes plus a small factory function. All inherit from Qubit (which is the shared base that defines the gate methods).

Source: euqalyptus/types/quantum/qubit.py.

LocalQubit

Represents a qubit allocated locally in the current node. Constructing a LocalQubit() inside a Qoala program records the equivalent of qnet.new_qubit.

from euqalyptus.types.quantum import LocalQubit

q = LocalQubit()
q.X()                    # records qnet.x %q
q.H()                    # records qnet.hadamard
m = q.measure()          # records qnet.measure, returns a Bit AST

See Qubit operations for the full method list.

EntangledQubit

Represents a qubit that has been entangled with a remote node. You typically don't instantiate this directly — use the Entangle() factory below.

EntangledQubit carries the same gate methods as LocalQubit. The lowering treats them slightly differently: an EntangledQubit corresponds to a qnet.eprs-produced value rather than a qnet.new_qubit result.

Entangle("Name", n=1) — the factory

from euqalyptus.types.quantum import Entangle
from euqalyptus.operations import Remote

Remote("Bob")
q = Entangle("Bob")           # one entangled qubit shared with Bob
qs = Entangle("Bob", n=3)     # tuple of three entangled qubits

Entangle raises UnknownRemoteError if the named remote has not been declared with Remote(...) first.

When n == 1, returns a single EntangledQubit. When n > 1, returns a tuple of EntangledQubits. Only the first element triggers the remote declaration in the AST.

ScopedQubit

ScopedQubit is a thin wrapper used in branching constructs to express that a qubit is being conditionally manipulated and "yielded" back out of the conditional region. It accepts a Qubit, an EntangledQubit, or a tuple of EntangledQubits.

from euqalyptus.types.quantum import ScopedQubit

cond_q = ScopedQubit(qubit)

You typically reach for ScopedQubit only inside branching blocks. You can check branching for more information about these statements.

Where qnet.qubit comes from

In the emitted HIR, every qubit-typed value is !qnet.qubit. The mapping:

SDK class Recorded HIR op
LocalQubit() %q = qnet.new_qubit : !qnet.qubit
Entangle("Bob") %q = qnet.eprs { remote = @Bob } : !qnet.qubit
Entangle("Bob", n=3) three qnet.eprs ops sharing the same remote

After the HIR→MIR lowering in qoala-mlir, each !qnet.qubit value is rewritten to an i32 qubit pointer. From the user's perspective, that's invisible.

API reference

qubit

LocalQubit

LocalQubit()

Bases: Qubit

A locally-allocated qubit.

Constructing LocalQubit() inside a @QoalaProgram body records a qnet.new_qubit op, allocating and initializing a fresh local qubit on the current node. The returned value is a full :class:Qubit — all the gate, rotation, and measurement methods inherited from the base class are available on it.

Returns:

Name Type Description
A

class:Qubit SSA value for the freshly allocated qubit.

EntangledQubit

EntangledQubit(name: str)

Bases: Qubit

The local half of an EPR pair shared with a remote node.

Constructing EntangledQubit("Alice") inside a @QoalaProgram body records a qnet.eprs { remote = @Alice } op, requesting an entangled pair with the named remote. The returned value is the local half of that pair, exposed as a regular :class:Qubit.

Most users should prefer the :func:Entangle factory, which also handles the n > 1 case of requesting several pairs in one go.

Parameters:

Name Type Description Default
name str

The symbolic name of the remote peer with which to entangle. The remote must have been declared via :class:~euqalyptus.operations.Remote earlier in the program.

required

ScopedQubit

ScopedQubit(qubit: Qubit | EntangledQubit | Tuple[EntangledQubit, ...])

Bases: Qubit

A recording-time proxy for a qubit that must survive a branching region.

ScopedQubit is used inside with if_cond(...) blocks to wrap a qubit whose post-branch identity must be the scf.if-yielded SSA result rather than an in-region SSA value. Calling ScopedQubit(q) captures q and exposes the same qubit-method surface (X, Y, measure, …) on the wrapper; while the branch is open, calls on the wrapper are routed to the captured original, and the chain of operations applied through the wrapper is tracked so the front-end can emit a well-formed scf.yield. After the branch exits, the wrapper rebinds to the SCF result and subsequent operations are recorded on that.

See the implementation section of the accompanying paper for the full rationale; the test fixtures in tests/bindings/test_branching.py exercise the mechanism.

Parameters:

Name Type Description Default
qubit Qubit | EntangledQubit | Tuple[EntangledQubit, ...]

The qubit value to capture. Must already be a :class:Qubit (typically a :class:LocalQubit or :class:EntangledQubit) recorded earlier in the program.

required

Raises:

Type Description
RuntimeError

If called without a qubit argument.

assign
assign(value: Any)

Re-assign the captured value of this scoped qubit.

Used internally by the branching machinery to rebind a :class:ScopedQubit after a branch arm has been recorded; not typically called by user code.

Parameters:

Name Type Description Default
value Any

The new captured value.

required

Entangle

Entangle(name: str, n: int = 1) -> EntangledQubit | Tuple[EntangledQubit, ...]

Generate n entangled qubits with a remote peer.

Records the appropriate number of qnet.eprs ops against the named remote and returns the local halves. With n = 1 (the default), the function returns a single :class:EntangledQubit; with n > 1, it returns a tuple of them.

Parameters:

Name Type Description Default
name str

The symbolic name of the remote peer. The remote must have been declared via :class:~euqalyptus.operations.Remote earlier in the program; passing an unknown name raises :class:UnknownRemoteError.

required
n int

The number of entangled pairs to request. Defaults to 1.

1

Returns:

Type Description
EntangledQubit | Tuple[EntangledQubit, ...]

A single :class:EntangledQubit if n == 1, otherwise a

EntangledQubit | Tuple[EntangledQubit, ...]

tuple of n :class:EntangledQubit values, each

EntangledQubit | Tuple[EntangledQubit, ...]

representing the local half of one of the requested pairs.

Raises:

Type Description
UnknownRemoteError

If name was not previously declared with :class:~euqalyptus.operations.Remote.