Limitation
The power modifier is defined as: "The modifier
pow(k) @ replaces its gate argument U by its kth power U^k for some positive integer
or floating point number k (not necessarily constant)."
pyqasm requires k to be an integer and rejects everything else.
Example QASM failure
OPENQASM 3.0;
include "stdgates.inc";
qubit[1] q;
pow(0.5) @ x q[0];
ValidationError: Power modifier argument must be an integer in gate operation QuantumGate(...)
Integer exponents, including negative ones, work today:
pow(2) @ x q[0]; // OK
pow(-1) @ x q[0]; // OK
so the restriction is specifically on the fractional case — which is the interesting one, since
pow(0.5) @ x is the square root of X.
Change Requested
- Accept a floating-point
k in pow(k) @.
- For a fractional
k, the repeat-the-gate expansion used for integers does not apply. The
unrolled result must be computed from the gate's matrix as U^k via matrix power — the
principal branch, matching the spec's definition.
- Where a fractional power of a gate has a known closed form in the standard library, prefer
emitting that named gate over a synthesised U(θ, φ, λ). For example pow(0.5) @ x is
sx.
- If a fractional power cannot be realised for a given gate, raise a
ValidationError naming
the gate and the exponent — not the current blanket "must be an integer".
Implementation Details
- The rejection is at
src/pyqasm/visitor.py:1627. The surrounding block already handles
negative integers by inverting and repeating, so the integer path is a useful reference for
where the fractional branch belongs.
src/pyqasm/linalg.py and the Cython src/pyqasm/accelerate/linalg.pyx already provide the
matrix machinery used by the decomposer; a matrix power via eigendecomposition fits there
rather than in the visitor.
- The single-qubit result can be routed through the existing ZYZ /
U(θ, φ, λ) decomposition
in src/pyqasm/decomposer.py, so the fractional case reduces to "compute the matrix, then
decompose" and reuses tested code.
- Decide the multi-qubit policy explicitly. A fractional power of a two-qubit gate is well
defined mathematically but expensive to synthesise; rejecting it with a clear message is a
reasonable first increment, provided the message says so.
- The spec's "not necessarily constant" clause implies a runtime-valued exponent. That cannot
be resolved during unrolling and is out of scope here — reject it with a specific message.
- Tests:
tests/qasm3/test_gate.py — pow(0.5) @ x against the sx matrix, pow(0.25) @ x,
pow(1.5) @ z, a fractional power under ctrl @, and a clear error for the unsupported
multi-qubit case.
Limitation
The power modifier is defined as: "The modifier
pow(k) @replaces its gate argument U by its kth power U^k for some positive integeror floating point number k (not necessarily constant)."
pyqasmrequireskto be an integer and rejects everything else.Example QASM failure
Integer exponents, including negative ones, work today:
so the restriction is specifically on the fractional case — which is the interesting one, since
pow(0.5) @ xis the square root of X.Change Requested
kinpow(k) @.k, the repeat-the-gate expansion used for integers does not apply. Theunrolled result must be computed from the gate's matrix as U^k via matrix power — the
principal branch, matching the spec's definition.
emitting that named gate over a synthesised
U(θ, φ, λ). For examplepow(0.5) @ xissx.ValidationErrornamingthe gate and the exponent — not the current blanket "must be an integer".
Implementation Details
src/pyqasm/visitor.py:1627. The surrounding block already handlesnegative integers by inverting and repeating, so the integer path is a useful reference for
where the fractional branch belongs.
src/pyqasm/linalg.pyand the Cythonsrc/pyqasm/accelerate/linalg.pyxalready provide thematrix machinery used by the decomposer; a matrix power via eigendecomposition fits there
rather than in the visitor.
U(θ, φ, λ)decompositionin
src/pyqasm/decomposer.py, so the fractional case reduces to "compute the matrix, thendecompose" and reuses tested code.
defined mathematically but expensive to synthesise; rejecting it with a clear message is a
reasonable first increment, provided the message says so.
be resolved during unrolling and is out of scope here — reject it with a specific message.
tests/qasm3/test_gate.py—pow(0.5) @ xagainst thesxmatrix,pow(0.25) @ x,pow(1.5) @ z, a fractional power underctrl @, and a clear error for the unsupportedmulti-qubit case.