Adjoint#

qualtran.Adjoint

The standard adjoint of subbloq.

Inherits From: GateWithRegisters, Bloq

This metabloq generally delegates all of its protocols (with modifications, read on) to subbloq. This class is used in the default implementation of the adjoint protocol, i.e., in the default implementation of Bloq.adjoint().

This metabloq is appropriate in most cases since there rarely a specialized (one level) decomposition for a bloq’s adjoint. Exceptions can be found for decomposing some low-level primitives, for example And. Even if you use bloqs with specialized adjoints in your decomposition (i.e. you use And), you can still rely on this standard behavior.

This bloq is defined entirely in terms of how it delegates its protocols. The following protocols delegate to subbloq (with appropriate modification):

  • Signature: The signature is the adjoint of subbloqs’s signature. Namely, LEFT and RIGHT registers are swapped.

  • Decomposition: The decomposition is the adjoint of subbloq’s decomposition. Namely, the order of operations in the resultant CompositeBloq is reversed and each bloq is replaced with its adjoint.

  • Adjoint: The adjoint of an Adjoint bloq is the subbloq itself.

  • Call graph: The call graph is the subbloq’s call graph, but each bloq is replaced with its adjoint.

  • Cirq Interop: The default Bloq implementation is used, which goes via BloqAsCirqGate as usual.

  • Wire Symbol: The wire symbols are the adjoint of subbloq’s wire symbols. Namely, left- and right-oriented symbols are flipped.

  • Names: The string names / labels are that of the subbloq with a dagger symbol appended.

Some protocols are impossible to delegate specialized implementations. The Adjoint bloq supports the following protocols with “decompose-only” implementations. This means we always go via the bloq’s decomposition instead of preferring specialized implementations provided by the bloq author. If a specialized implementation of these protocols are required or you are trying to represent an adjoint bloq without a decomposition and need to support these protocols, use a specialized adjoint bloq or attribute instead of this class.

  • Classical simulation is “decompose-only”. It is impossible to invert a generic python function.

  • Tensor simulation is “decompose-only” due to technical details around the Quimb interop.

subbloq

The bloq to wrap.

signature

The input and output names and types for this bloq.

This property can be thought of as analogous to the function signature in ordinary programming. For example, it is analogous to function declarations in a C header (*.h) file.

This is the only mandatory method (property) you must implement to inherit from Bloq. You can optionally implement additional methods to encode more information about this bloq.

subbloq

 

Methods#

decompose_bloq

View source

The decomposition is the adjoint of subbloq’s decomposition.

adjoint

View source

The ‘double adjoint’ brings you back to the original bloq.

build_call_graph

View source

The call graph takes the adjoint of each of the bloqs in subbloq’s call graph.

wire_symbol

View source

On a musical score visualization, use this WireSymbol to represent soq.

By default, we use a “directional text box”, which is a text box that is either rectangular for thru-registers or facing to the left or right for non-thru-registers.

If reg is specified as None, this should return a Text label for the title of the gate. If no title is needed (as the wire_symbols are self-explanatory), this should return Text('').

Override this method to provide a more relevant WireSymbol for the provided soquet. This method can access bloq attributes. For example: you may want to draw either a filled or empty circle for a control register depending on a control value bloq attribute.

num_qubits

The number of qubits this gate acts on.

__ne__

Check equality and either forward a NotImplemented or return the result negated.

__eq__

Method generated by attrs for class Adjoint.