CompositeBloq#
qualtran.CompositeBloq
View source on GitHub
|
A bloq defined by a collection of sub-bloqs and dataflows between them
Inherits From: Bloq
qualtran.CompositeBloq(
connections, signature, bloq_instances=NOTHING
)
CompositeBloq represents a quantum subroutine as a dataflow compute graph. The
specific native representation is a list of Connection objects (i.e. a list of
graph edges). This container should be considered immutable. Additional views
of the graph are provided by methods and properties.
Users should generally use BloqBuilder to construct a composite bloq either
directly or by overriding Bloq.build_composite_bloq.
Throughout this library we will often use the variable name cbloq to refer to a
composite bloq.
Args
cxnsA sequence of
Connectionencoding the quantum compute graph.signatureThe registers defining the inputs and outputs of this Bloq. This should correspond to the dangling
Soquetsin thecxns.
Attributes
all_soquetsbloq_instancesconnectionssignatureThe 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.
Methods#
as_cirq_op
as_cirq_op(
qubit_manager: 'cirq.QubitManager', **cirq_quregs
) -> Tuple['cirq.Operation', Dict[str, 'CirqQuregT']]
Return a cirq.CircuitOperation containing a cirq-exported version of this cbloq.
to_cirq_circuit_and_quregs
to_cirq_circuit_and_quregs(
qubit_manager: Optional['cirq.QubitManager'] = None, **cirq_quregs
) -> Tuple['cirq.FrozenCircuit', Dict[str, 'CirqQuregT']]
Convert this CompositeBloq to a cirq.Circuit and output qubit registers.
Args
qubit_managerA
cirq.QubitManagerto allocate new qubits. If not provided, usescirq.SimpleQubitManager()by default.**cirq_quregsMapping from left register names to Cirq qubit arrays.
Returns
circuitThe cirq.FrozenCircuit version of this composite bloq.
cirq_quregsThe output mapping from right register names to Cirq qubit arrays.
to_cirq_circuit
to_cirq_circuit(
*,
qubit_manager: Optional['cirq.QubitManager'] = None,
cirq_quregs: Optional[Mapping[str, 'CirqQuregInT']] = None
) -> 'cirq.FrozenCircuit'
Convert this CompositeBloq to a cirq.Circuit.
Args
qubit_managerA
cirq.QubitManagerto allocate new qubits. If not provided, usescirq.SimpleQubitManager()by default.cirq_quregsMapping from left register names to Cirq qubit arrays. If not provided, uses
get_named_qubits(self.signature.lefts())by default.
Returns
circuitThe cirq.FrozenCircuit version of this composite bloq.
from_cirq_circuit
@classmethodfrom_cirq_circuit( circuit: 'cirq.Circuit' ) -> 'CompositeBloq'
Construct a composite bloq from a Cirq circuit.
Each cirq.Operation will be wrapped into a CirqGate wrapper bloq. The
resultant composite bloq will represent a unitary with one thru-register
named “qubits” of shape (n_qubits,).
on_classical_vals
on_classical_vals(
**vals
) -> Dict[str, 'ClassicalValT']
Support classical data by recursing into the composite bloq.
call_classically
call_classically(
**vals
) -> Tuple['ClassicalValT', ...]
Support classical data by recursing into the composite bloq.
as_composite_bloq
as_composite_bloq() -> 'CompositeBloq'
This override just returns the present composite bloq.
decompose_bloq
decompose_bloq() -> 'CompositeBloq'
Decompose this Bloq into its constituent parts contained in a CompositeBloq.
Bloq users can call this function to delve into the definition of a Bloq. If you’re
trying to define a bloq’s decomposition, consider overriding build_composite_bloq
which provides helpful arguments for implementers.
Returns
Raises
NotImplementedErrorIf there is no decomposition defined; namely: if
build_composite_bloqreturnsNotImplemented.
build_call_graph
build_call_graph(
ssa: Optional['SympySymbolAllocator']
) -> 'BloqCountDictT'
Return the bloq counts by counting up all the subbloqs.
iter_bloqnections
iter_bloqnections() -> Iterator[Tuple[BloqInstance, List[Connection], List[Connection]]]
Iterate over Bloqs and their connections in topological order.
Yields
iter_bloqsoqs
iter_bloqsoqs() -> Iterator[Tuple[BloqInstance, Dict[str, SoquetT], Tuple[SoquetT, ...]]]
Iterate over bloq instances and their input soquets.
This method is helpful for “adding from” this existing composite bloq. You must
use map_soqs to map this cbloq’s soquets to the correct ones for the
new bloq.
>>> bb, _ = BloqBuilder.from_signature(self.signature)
>>> soq_map: List[Tuple[SoquetT, SoquetT]] = []
>>> for binst, in_soqs, old_out_soqs in self.iter_bloqsoqs():
>>> in_soqs = bb.map_soqs(in_soqs, soq_map)
>>> new_out_soqs = bb.add_t(binst.bloq, **in_soqs)
>>> soq_map.extend(zip(old_out_soqs, new_out_soqs))
>>> return bb.finalize(**bb.map_soqs(self.final_soqs(), soq_map))
Yields
binstThe current bloq instance
in_soqsA dictionary mapping the binst’s register names to predecessor soquets. This is suitable for
bb.add(binst.bloq, **in_soqs)out_soqsA tuple of the output soquets of
binst. This can be used to update the mapping from this cbloq’s soquets to a modified copy, see the example code.
final_soqs
final_soqs() -> Dict[str, SoquetT]
Return the final output soquets.
This method is helpful for finalizing an “add from” operation, see iter_bloqsoqs.
copy
copy() -> 'CompositeBloq'
Create a copy of this composite bloq by re-building it.
flatten_once
flatten_once(
pred: Callable[[qualtran.BloqInstance], bool] = (lambda binst: True)
) -> 'CompositeBloq'
Decompose and flatten each subbloq that satisfies pred.
This will only flatten “once”. That is, we will go through the bloq instances
contained in this composite bloq and (optionally) flatten each one but will not
recursively flatten the results. For a recursive version see flatten.
Args
predA predicate that takes a bloq instance and returns True if it should be decomposed and flattened or False if it should remain undecomposed. If the bloq does not have a decomposition, it will remain undecomposed. By default, flatten everything.
Returns
Raises
DidNotFlattenAnythingErrorIf the operation did not actually flatten anything. This could be because none of the bloq instances satisfied
predor none of the bloqs have decompositions.
flatten
flatten(
pred: Callable[[qualtran.BloqInstance], bool] = (lambda binst: True),
max_depth: int = 1000
) -> 'CompositeBloq'
Recursively decompose and flatten subbloqs until none satisfy pred.
This will continue flattening the results of subbloq.decompose_bloq() until
all bloqs which would satisfy pred have been flattened.
Args
predA predicate that takes a bloq instance and returns True if it should be decomposed and flattened or False if it should remain undecomposed. If the bloq does not have a decomposition, it will remain undecomposed. By default, flatten as much as possible.
max_depthTo avoid infinite recursion, give up after this many recursive steps.
Returns
adjoint
adjoint() -> 'CompositeBloq'
Get a composite bloq which is the adjoint of this composite bloq.
The adjoint of a composite bloq is another composite bloq where the order of operations is reversed and each subbloq is replaced with its adjoint.
debug_text
debug_text() -> str
Print connection information to assist in debugging.
The output will be a topologically sorted list of BloqInstances with each topological generation separated by a horizontal line. Each bloq instance is followed by a list of its incoming and outgoing connections. Note that all non-dangling connections are represented twice: once as the output of a binst and again as the input to a subsequent binst.
__ne__
__ne__(
other
)
Check equality and either forward a NotImplemented or return the result negated.
__eq__
__eq__(
other
)
Method generated by attrs for class CompositeBloq.
View source on GitHub