Type checking¶
hybridlane infers the types of wires and measurements through a pass over the quantum circuit’s
operations. This is necessary because PennyLane does not strongly type the wires, in contrast to
other common libraries – a wire can represent a qubit or a qumode. We need types to verify that
gates are used correctly, and to properly dispatch circuits to hardware and simulator devices. The
process is fairly simple and is contained in the function hl.type_check.
Wire type inference¶
The first way hybridlane infers the type of wires is through inspecting the Python type of the operations used in a quantum circuit:
Normal PennyLane gates that subclass
Operationare assumed to be DV gates, meaning that all the input wires are qubits. An exception is the gates underqp.ops.qutrit, which are instead interpreted as qutrit operations.PennyLane and hybridlane gates that subclass
CVOperationare assumed to be CV gates, and therefore all input wires are qumodes.Finally, for hybrid gates, hybridlane provides the
Hybridmixin. TheHybridmixin has a property calledtype_signature, which informs the type checker the types of the different wires.
Tip
Once a wire type is deduced from a gate, it is fixed for the remainder of the circuit, meaning if a subsequent gate treats a wire in a manner differently than its original definition, an error is thrown.
hybridlane can also infer types through the measurements performed on a wire, usually from measuring an observable. This follows a similar set of rules.
Inferring Measurements¶
The type of measurement required in a quantum program is captured by a combination of the WireType and its BasisMap. Qubits are obviously measured in the computational basis (Z), which is represented by ComputationalBasis.Discrete. Qumodes, however, have 3 measurement possibilities:
ComputationalBasis.Discretein conjunction with a qumode means to apply a Fock measurement, sampling \(\hat{n}\). This is often called photon number readout. The result of this measurement should be stored in anintoruinttype.ComputationalBasis.Positionmeasures a qumode in the position basis, sampling \(\hat{x}\). This is commonly referred to as homodyne detection. The result of this measurement requires afloattype.ComputationalBasis.Coherentmeasures the Husimi-Q function of a state, returning a coherent state \(\ket{\alpha}\). This is referred to as heterodyne detection. The result of this measurement requires acomplextype.
For observables, the logic to deduce which measurement to apply works as follows:
Composite operators (subclassing
CompositeOporSymbolicOp) are recursively traversed.If an operator defines
pauli_rep, it is assignedComputationalBasis.Discretebecause it must be a qubit observable.For CV observables that implement the
Spectralmixin, we use that operator’snatural_basis. For observables that can be decomposed to \(\hat{n}\), this becomesComputationalBasis.Discrete, and for observables that can be decomposed to \(\hat{x}\), this becomesComputationalBasis.Position.
There’s almost certainly room to improve this inference logic, so ideas and pull requests welcome!
Tip
Up until now, we haven’t mentioned what the Spectral mixin does. Pennylane assumes that all observables have a finite set of eigenvalues that can be written down in a numpy array. Obviously this doesn’t work for CV observables that have an infinite eigenspectrum.
The Spectral mixin replaces the idea of an eigvals array with a function \(f: \mathcal{B} \rightarrow \mathbb{R}\) taking computational basis states and returning their eigenvalues. For example, we add the Spectral mixin to the hl.QuadX operator with its position_spectrum function looking like \(f(x) = x\) since \(\hat{x}\ket{x} = x\ket{x}\). This is another reason to use the hl versions when available.