qiskit-documentation/docs/api/qiskit/qiskit.circuit.library.HRSC...

574 lines
22 KiB
Plaintext
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

---
title: HRSCumulativeMultiplier (latest version)
description: API reference for qiskit.circuit.library.HRSCumulativeMultiplier in the latest version of qiskit
in_page_toc_min_heading_level: 1
python_api_type: class
python_api_name: qiskit.circuit.library.HRSCumulativeMultiplier
---
# HRSCumulativeMultiplier
<Class id="qiskit.circuit.library.HRSCumulativeMultiplier" isDedicatedPage={true} github="https://github.com/Qiskit/qiskit/tree/stable/2.0/qiskit/circuit/library/arithmetic/multipliers/hrs_cumulative_multiplier.py#L21-L145" signature="qiskit.circuit.library.HRSCumulativeMultiplier(num_state_qubits, num_result_qubits=None, adder=None, name='HRSCumulativeMultiplier')" modifiers="class">
Bases: `Multiplier`
A multiplication circuit to store product of two input registers out-of-place.
Circuit uses the approach from \[1]. As an example, a multiplier circuit that performs a non-modular multiplication on two 3-qubit sized registers with the default adder is as follows (where `Adder` denotes the `CDKMRippleCarryAdder`):
```text
a_0: ────■─────────────────────────
a_1: ────┼─────────■───────────────
│ │
a_2: ────┼─────────┼─────────■─────
┌───┴────┐┌───┴────┐┌───┴────┐
b_0: ┤0 ├┤0 ├┤0 ├
│ ││ ││ │
b_1: ┤1 ├┤1 ├┤1 ├
│ ││ ││ │
b_2: ┤2 ├┤2 ├┤2 ├
│ ││ ││ │
out_0: ┤3 ├┤ ├┤ ├
│ ││ ││ │
out_1: ┤4 ├┤3 ├┤ ├
│ Adder ││ Adder ││ Adder │
out_2: ┤5 ├┤4 ├┤3 ├
│ ││ ││ │
out_3: ┤6 ├┤5 ├┤4 ├
│ ││ ││ │
out_4: ┤ ├┤6 ├┤5 ├
│ ││ ││ │
out_5: ┤ ├┤ ├┤6 ├
│ ││ ││ │
aux_0: ┤7 ├┤7 ├┤7 ├
└────────┘└────────┘└────────┘
```
Multiplication in this circuit is implemented in a classical approach by performing a series of shifted additions using one of the input registers while the qubits from the other input register act as control qubits for the adders.
<Admonition title="See also" type="note">
The [`MultiplierGate`](qiskit.circuit.library.MultiplierGate "qiskit.circuit.library.MultiplierGate") objects represents a multiplication, like this circuit class, but allows the compiler to select the optimal decomposition based on the context. Specific implementations can be set via the [`HLSConfig`](qiskit.transpiler.passes.HLSConfig "qiskit.transpiler.passes.HLSConfig"), e.g. this circuit can be chosen via `Multiplier=["cumulative_h18"]`.
</Admonition>
**References:**
\[1] Häner et al., Optimizing Quantum Circuits for Arithmetic, 2018. [arXiv:1805.12445](https://arxiv.org/pdf/1805.12445.pdf)
**Parameters**
* **num\_state\_qubits** ([*int*](https://docs.python.org/3/library/functions.html#int "(in Python v3.13)")) The number of qubits in either input register for state $|a\rangle$ or $|b\rangle$. The two input registers must have the same number of qubits.
* **num\_result\_qubits** ([*int*](https://docs.python.org/3/library/functions.html#int "(in Python v3.13)") *| None*) The number of result qubits to limit the output to. If number of result qubits is $n$, multiplication modulo $2^n$ is performed to limit the output to the specified number of qubits. Default value is `2 * num_state_qubits` to represent any possible result from the multiplication of the two inputs.
* **adder** ([*QuantumCircuit*](qiskit.circuit.QuantumCircuit "qiskit.circuit.quantumcircuit.QuantumCircuit") *| None*) Half adder circuit to be used for performing multiplication. The CDKMRippleCarryAdder is used as default if no adder is provided.
* **name** ([*str*](https://docs.python.org/3/library/stdtypes.html#str "(in Python v3.13)")) The name of the circuit object.
**Raises**
[**NotImplementedError**](https://docs.python.org/3/library/exceptions.html#NotImplementedError "(in Python v3.13)") If `num_result_qubits` is not default and a custom adder is provided.
## Attributes
### ancillas
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.ancillas">
A list of `AncillaQubit`s in the order that they were added. You should not mutate this.
</Attribute>
### clbits
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.clbits">
A list of `Clbit`s in the order that they were added. You should not mutate this.
**Example**
```python
from qiskit import QuantumRegister, ClassicalRegister, QuantumCircuit
qr1 = QuantumRegister(2)
qr2 = QuantumRegister(1)
cr1 = ClassicalRegister(2)
cr2 = ClassicalRegister(1)
qc = QuantumCircuit(qr1, qr2, cr1, cr2)
print("List the qubits in this circuit:", qc.qubits)
print("List the classical bits in this circuit:", qc.clbits)
```
```text
List the qubits in this circuit: [Qubit(QuantumRegister(2, 'q0'), 0),
Qubit(QuantumRegister(2, 'q0'), 1), Qubit(QuantumRegister(1, 'q1'), 0)]
List the classical bits in this circuit: [Clbit(ClassicalRegister(2, 'c0'), 0),
Clbit(ClassicalRegister(2, 'c0'), 1), Clbit(ClassicalRegister(1, 'c1'), 0)]
```
</Attribute>
### cregs
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.cregs">
A list of `Clbit`s in the order that they were added. You should not mutate this.
</Attribute>
### data
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.data">
The circuit data (instructions and context).
**Example**
```python
from qiskit import QuantumCircuit
qc = QuantumCircuit(2, 2)
qc.measure([0], [1])
print(qc.data)
```
```text
[CircuitInstruction(operation=Instruction(name='measure', num_qubits=1,
num_clbits=1, params=[]), qubits=(Qubit(QuantumRegister(2, 'q'), 0),),
clbits=(Clbit(ClassicalRegister(2, 'c'), 1),))]
```
**Returns**
A list-like object containing the [`CircuitInstruction`](qiskit.circuit.CircuitInstruction "qiskit.circuit.CircuitInstruction") instances in the circuit.
</Attribute>
### duration
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.duration">
The total duration of the circuit, set by a scheduling transpiler pass. Its unit is specified by [`unit`](#qiskit.circuit.library.HRSCumulativeMultiplier.unit "qiskit.circuit.library.HRSCumulativeMultiplier.unit").
<Admonition title="Deprecated since version 1.3.0" type="danger">
The property `qiskit.circuit.quantumcircuit.QuantumCircuit.duration` is deprecated as of Qiskit 1.3.0. It will be removed in Qiskit 3.0.0.
</Admonition>
</Attribute>
### global\_phase
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.global_phase">
The global phase of the current circuit scope in radians.
**Example**
```python
from qiskit import QuantumCircuit
circuit = QuantumCircuit(2)
circuit.h(0)
circuit.cx(0, 1)
print(circuit.global_phase)
```
```text
0.0
```
```python
from numpy import pi
circuit.global_phase = pi/4
print(circuit.global_phase)
```
```text
0.7853981633974483
```
</Attribute>
### instances
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.instances" attributeValue="182" />
### layout
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.layout">
Return any associated layout information about the circuit.
This attribute contains an optional [`TranspileLayout`](qiskit.transpiler.TranspileLayout "qiskit.transpiler.TranspileLayout") object. This is typically set on the output from [`transpile()`](compiler#qiskit.compiler.transpile "qiskit.compiler.transpile") or [`PassManager.run()`](qiskit.transpiler.PassManager#run "qiskit.transpiler.PassManager.run") to retain information about the permutations caused on the input circuit by transpilation.
There are two types of permutations caused by the [`transpile()`](compiler#qiskit.compiler.transpile "qiskit.compiler.transpile") function: an initial layout that permutes the qubits based on the selected physical qubits on the [`Target`](qiskit.transpiler.Target "qiskit.transpiler.Target"), and a final layout, which is an output permutation caused by [`SwapGate`](qiskit.circuit.library.SwapGate "qiskit.circuit.library.SwapGate")s inserted during routing.
**Example**
```python
from qiskit import QuantumCircuit
from qiskit.providers.fake_provider import GenericBackendV2
from qiskit.transpiler import generate_preset_pass_manager
# Create circuit to test transpiler on
qc = QuantumCircuit(3, 3)
qc.h(0)
qc.cx(0, 1)
qc.swap(1, 2)
qc.cx(0, 1)
# Add measurements to the circuit
qc.measure([0, 1, 2], [0, 1, 2])
# Specify the QPU to target
backend = GenericBackendV2(3)
# Transpile the circuit
pass_manager = generate_preset_pass_manager(
optimization_level=1, backend=backend
)
transpiled = pass_manager.run(qc)
# Print the layout after transpilation
print(transpiled.layout.routing_permutation())
```
```text
[0, 1, 2]
```
</Attribute>
### metadata
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.metadata">
Arbitrary user-defined dictionary of metadata for the circuit.
Qiskit will not examine the content of this mapping, but it will pass it through the transpiler and reattach it to the output, so you can track your own metadata.
**Example**
```python
from qiskit import QuantumCircuit
qc = QuantumCircuit(2, 2, metadata={'experiment_type': 'Bell state experiment'})
print(qc.metadata)
```
```text
{'experiment_type': 'Bell state experiment'}
```
</Attribute>
### num\_ancillas
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.num_ancillas">
Return the number of ancilla qubits.
**Example**
```python
from qiskit import QuantumCircuit, QuantumRegister, AncillaRegister
# Create a 2-qubit quantum circuit
reg = QuantumRegister(2)
qc = QuantumCircuit(reg)
# Create an ancilla register with 1 qubit
anc = AncillaRegister(1)
qc.add_register(anc) # Add the ancilla register to the circuit
print("Number of ancilla qubits:", qc.num_ancillas)
```
```text
Number of ancilla qubits: 1
```
</Attribute>
### num\_captured\_stretches
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.num_captured_stretches">
The number of stretches in the circuit marked as captured from an enclosing scope.
This is the length of the `iter_captured_stretches()` iterable. If this is non-zero, [`num_input_vars`](#qiskit.circuit.library.HRSCumulativeMultiplier.num_input_vars "qiskit.circuit.library.HRSCumulativeMultiplier.num_input_vars") must be zero.
</Attribute>
### num\_captured\_vars
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.num_captured_vars">
The number of real-time classical variables in the circuit marked as captured from an enclosing scope.
This is the length of the `iter_captured_vars()` iterable. If this is non-zero, [`num_input_vars`](#qiskit.circuit.library.HRSCumulativeMultiplier.num_input_vars "qiskit.circuit.library.HRSCumulativeMultiplier.num_input_vars") must be zero.
</Attribute>
### num\_clbits
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.num_clbits">
Return number of classical bits.
**Example**
```python
from qiskit import QuantumCircuit
# Create a new circuit with two qubits and one classical bit
qc = QuantumCircuit(2, 1)
print("Number of classical bits:", qc.num_clbits)
```
```text
Number of classical bits: 1
```
</Attribute>
### num\_declared\_stretches
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.num_declared_stretches">
The number of stretches in the circuit that are declared by this circuit scope, excluding captures.
This is the length of the `iter_declared_stretches()` iterable.
</Attribute>
### num\_declared\_vars
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.num_declared_vars">
The number of real-time classical variables in the circuit that are declared by this circuit scope, excluding inputs or captures.
This is the length of the `iter_declared_vars()` iterable.
</Attribute>
### num\_identifiers
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.num_identifiers">
The number of real-time classical variables and stretches in the circuit.
This is equal to [`num_vars()`](#qiskit.circuit.library.HRSCumulativeMultiplier.num_vars "qiskit.circuit.library.HRSCumulativeMultiplier.num_vars") + [`num_stretches()`](#qiskit.circuit.library.HRSCumulativeMultiplier.num_stretches "qiskit.circuit.library.HRSCumulativeMultiplier.num_stretches").
</Attribute>
### num\_input\_vars
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.num_input_vars">
The number of real-time classical variables in the circuit marked as circuit inputs.
This is the length of the `iter_input_vars()` iterable. If this is non-zero, [`num_captured_vars`](#qiskit.circuit.library.HRSCumulativeMultiplier.num_captured_vars "qiskit.circuit.library.HRSCumulativeMultiplier.num_captured_vars") must be zero.
</Attribute>
### num\_parameters
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.num_parameters">
The number of parameter objects in the circuit.
</Attribute>
### num\_qubits
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.num_qubits">
Return number of qubits.
</Attribute>
### num\_result\_qubits
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.num_result_qubits">
The number of result qubits to limit the output to.
**Returns**
The number of result qubits.
</Attribute>
### num\_state\_qubits
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.num_state_qubits">
The number of state qubits, i.e. the number of bits in each input register.
**Returns**
The number of state qubits.
</Attribute>
### num\_stretches
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.num_stretches">
The number of stretches in the circuit.
This is the length of the `iter_stretches()` iterable.
</Attribute>
### num\_vars
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.num_vars">
The number of real-time classical variables in the circuit.
This is the length of the `iter_vars()` iterable.
</Attribute>
### op\_start\_times
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.op_start_times">
Return a list of operation start times.
<Admonition title="Note" type="note">
This attribute computes the estimate starting time of the operations in the scheduled circuit and only works for simple circuits that have no control flow or other classical feed-forward operations.
</Admonition>
This attribute is enabled once one of scheduling analysis passes runs on the quantum circuit.
**Example**
```python
from qiskit import QuantumCircuit
from qiskit.providers.fake_provider import GenericBackendV2
from qiskit.transpiler import generate_preset_pass_manager
qc = QuantumCircuit(2)
qc.h(0)
qc.cx(0, 1)
qc.measure_all()
# Print the original circuit
print("Original circuit:")
print(qc)
# Transpile the circuit with a specific basis gates list and print the resulting circuit
backend = GenericBackendV2(2, basis_gates=['u1', 'u2', 'u3', 'cx'])
pm = generate_preset_pass_manager(
optimization_level=1, backend=backend, scheduling_method="alap"
)
transpiled_qc = pm.run(qc)
print("Transpiled circuit with basis gates ['u1', 'u2', 'u3', 'cx']:")
print(transpiled_qc)
# Print the start times of each instruction in the transpiled circuit
print("Start times of instructions in the transpiled circuit:")
for instruction, start_time in zip(transpiled_qc.data, transpiled_qc.op_start_times):
print(f"{instruction.operation.name}: {start_time}")
```
```text
Original circuit:
┌───┐ ░ ┌─┐
q_0: ┤ H ├──■───░─┤M├───
└───┘┌─┴─┐ ░ └╥┘┌─┐
q_1: ─────┤ X ├─░──╫─┤M├
└───┘ ░ ║ └╥┘
meas: 2/══════════════╩══╩═
0 1
Transpiled circuit with basis gates ['u1', 'u2', 'u3', 'cx']:
┌─────────┐ ░ ┌─────────────────┐┌─┐
q_0 -> 0 ───┤ U2(0,π) ├──────■───░─┤ Delay(1255[dt]) ├┤M├
┌──┴─────────┴───┐┌─┴─┐ ░ └───────┬─┬───────┘└╥┘
q_1 -> 1 ┤ Delay(196[dt]) ├┤ X ├─░─────────┤M├─────────╫─
└────────────────┘└───┘ ░ └╥┘ ║
meas: 2/═══════════════════════════════════╩══════════╩═
1 0
Start times of instructions in the transpiled circuit:
u2: 0
delay: 0
cx: 196
barrier: 2098
delay: 2098
measure: 3353
measure: 2098
```
**Returns**
List of integers representing instruction estimated start times. The index corresponds to the index of instruction in `QuantumCircuit.data`.
**Raises**
[**AttributeError**](https://docs.python.org/3/library/exceptions.html#AttributeError "(in Python v3.13)") When circuit is not scheduled.
</Attribute>
### parameters
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.parameters">
The parameters defined in the circuit.
This attribute returns the [`Parameter`](qiskit.circuit.Parameter "qiskit.circuit.Parameter") objects in the circuit sorted alphabetically. Note that parameters instantiated with a [`ParameterVector`](qiskit.circuit.ParameterVector "qiskit.circuit.ParameterVector") are still sorted numerically.
**Examples**
The snippet below shows that insertion order of parameters does not matter.
```python
>>> from qiskit.circuit import QuantumCircuit, Parameter
>>> a, b, elephant = Parameter("a"), Parameter("b"), Parameter("elephant")
>>> circuit = QuantumCircuit(1)
>>> circuit.rx(b, 0)
>>> circuit.rz(elephant, 0)
>>> circuit.ry(a, 0)
>>> circuit.parameters # sorted alphabetically!
ParameterView([Parameter(a), Parameter(b), Parameter(elephant)])
```
Bear in mind that alphabetical sorting might be unintuitive when it comes to numbers. The literal “10” comes before “2” in strict alphabetical sorting.
```python
>>> from qiskit.circuit import QuantumCircuit, Parameter
>>> angles = [Parameter("angle_1"), Parameter("angle_2"), Parameter("angle_10")]
>>> circuit = QuantumCircuit(1)
>>> circuit.u(*angles, 0)
>>> circuit.draw()
┌─────────────────────────────┐
q: ┤ U(angle_1,angle_2,angle_10) ├
└─────────────────────────────┘
>>> circuit.parameters
ParameterView([Parameter(angle_1), Parameter(angle_10), Parameter(angle_2)])
```
To respect numerical sorting, a [`ParameterVector`](qiskit.circuit.ParameterVector "qiskit.circuit.ParameterVector") can be used.
```python
>>> from qiskit.circuit import QuantumCircuit, Parameter, ParameterVector
>>> x = ParameterVector("x", 12)
>>> circuit = QuantumCircuit(1)
>>> for x_i in x:
... circuit.rx(x_i, 0)
>>> circuit.parameters
ParameterView([
ParameterVectorElement(x[0]), ParameterVectorElement(x[1]),
ParameterVectorElement(x[2]), ParameterVectorElement(x[3]),
..., ParameterVectorElement(x[11])
])
```
**Returns**
The sorted [`Parameter`](qiskit.circuit.Parameter "qiskit.circuit.Parameter") objects in the circuit.
</Attribute>
### prefix
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.prefix" attributeValue="'circuit'" />
### qregs
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.qregs">
A list of `Qubit`s in the order that they were added. You should not mutate this.
</Attribute>
### qubits
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.qubits">
A list of `Qubit`s in the order that they were added. You should not mutate this.
</Attribute>
### unit
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.unit">
The unit that [`duration`](#qiskit.circuit.library.HRSCumulativeMultiplier.duration "qiskit.circuit.library.HRSCumulativeMultiplier.duration") is specified in.
<Admonition title="Deprecated since version 1.3.0" type="danger">
The property `qiskit.circuit.quantumcircuit.QuantumCircuit.unit` is deprecated as of Qiskit 1.3.0. It will be removed in Qiskit 3.0.0.
</Admonition>
</Attribute>
### name
<Attribute id="qiskit.circuit.library.HRSCumulativeMultiplier.name" attributeTypeHint="str">
A human-readable name for the circuit.
**Example**
```python
from qiskit import QuantumCircuit
qc = QuantumCircuit(2, 2, name="my_circuit")
print(qc.name)
```
```text
my_circuit
```
</Attribute>
</Class>