Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
…eriments into issue-qiskit-community#1238-draft2

update local2/issue-#1238-draft2 with upstream/main
  • Loading branch information
Naohnakazawa committed Nov 14, 2024
2 parents b685974 + 3906340 commit 15f6055
Show file tree
Hide file tree
Showing 7 changed files with 63 additions and 30 deletions.
21 changes: 15 additions & 6 deletions qiskit_experiments/framework/composite/parallel_experiment.py
Original file line number Diff line number Diff line change
Expand Up @@ -89,14 +89,23 @@ def _combined_circuits(self, device_layout: bool) -> List[QuantumCircuit]:
# Num qubits will be computed from sub experiments
num_qubits = len(self.physical_qubits)
else:
# Work around for backend coupling map circuit inflation
# Expand the number of qubits similar to how qiskit.transpile does
# Here we progress from most to least specific way of specifying
# the number of qubits: coupling_map->target->backend
#
# TODO: Behave more like a layout transpiler pass and set the
# _layout property on the circuits. Doing this requires accessing
# private attributes of Qiskit or possibly running a layout pass of
# the transpiler if that can be done without too much overhead.
num_qubits = 1 + max(self.physical_qubits)
coupling_map = getattr(self.transpile_options, "coupling_map", None)
if coupling_map is None and self.backend:
coupling_map = self._backend_data.coupling_map
target = getattr(self.transpile_options, "target", None)
if coupling_map is not None:
num_qubits = 1 + max(*self.physical_qubits, np.max(coupling_map))
else:
num_qubits = 1 + max(self.physical_qubits)
num_qubits = max(num_qubits, 1 + np.max(coupling_map))
elif target is not None:
num_qubits = max(num_qubits, target.num_qubits)
elif self.backend:
num_qubits = max(num_qubits, self._backend_data.num_qubits)

joint_circuits = []
sub_qubits = 0
Expand Down
4 changes: 2 additions & 2 deletions qiskit_experiments/library/tomography/fitters/cvxpy_lstsq.py
Original file line number Diff line number Diff line change
Expand Up @@ -300,8 +300,8 @@ def cvxpy_linear_lstsq(
idx = 0
for i in range(num_circ_components):
for j in range(num_tomo_components):
model = bms_r[idx] @ cvxpy.vec(rhos_r[idx]) - bms_i[idx] @ cvxpy.vec(
rhos_i[idx]
model = bms_r[idx] @ cvxpy.vec(rhos_r[idx], order="F") - bms_i[idx] @ cvxpy.vec(
rhos_i[idx], order="F"
)
data = probability_data[i, j]
args.append(model - data)
Expand Down
8 changes: 4 additions & 4 deletions qiskit_experiments/library/tomography/fitters/cvxpy_utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -234,8 +234,8 @@ def partial_trace_constaint(
ptr = partial_trace_super(input_dim, output_dim)
vec_cons = np.ravel(constraint, order="F")
return [
ptr @ cvxpy.vec(mat_r) == vec_cons.real.round(12),
ptr @ cvxpy.vec(mat_i) == vec_cons.imag.round(12),
ptr @ cvxpy.vec(mat_r, order="F") == vec_cons.real.round(12),
ptr @ cvxpy.vec(mat_i, order="F") == vec_cons.imag.round(12),
]


Expand Down Expand Up @@ -274,7 +274,7 @@ def trace_preserving_constaint(
output_dim = sdim // input_dim

ptr = partial_trace_super(input_dim, output_dim)
cons = [ptr @ cvxpy.vec(arg_r) == np.identity(input_dim).ravel()]
cons = [ptr @ cvxpy.vec(arg_r, order="F") == np.identity(input_dim).ravel()]

if hermitian:
return cons
Expand All @@ -286,7 +286,7 @@ def trace_preserving_constaint(
arg_i = mat_i
else:
raise TypeError("Input must be a cvxpy variable or list of variables")
cons.append(ptr @ cvxpy.vec(arg_i) == np.zeros(input_dim**2))
cons.append(ptr @ cvxpy.vec(arg_i, order="F") == np.zeros(input_dim**2))
return cons


Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@
from typing import Union, Optional, Iterable, List, Tuple, Sequence
from itertools import product
from qiskit.circuit import QuantumCircuit, Instruction, ClassicalRegister, Clbit
from qiskit.circuit.library import Permutation
from qiskit.circuit.library import PermutationGate
from qiskit.providers.backend import Backend
from qiskit.quantum_info.operators.base_operator import BaseOperator

Expand Down Expand Up @@ -314,7 +314,7 @@ def _permute_circuit(self) -> QuantumCircuit:
prep_qargs = list(self._prep_indices)
if len(self._prep_indices) != total_qubits:
prep_qargs += [i for i in range(total_qubits) if i not in self._prep_indices]
perm_circ.append(Permutation(total_qubits, prep_qargs).inverse(), range(total_qubits))
perm_circ.append(PermutationGate(prep_qargs).inverse(), range(total_qubits))

# Apply original circuit
if total_clbits:
Expand All @@ -327,6 +327,6 @@ def _permute_circuit(self) -> QuantumCircuit:
meas_qargs = list(self._meas_indices)
if len(self._meas_indices) != total_qubits:
meas_qargs += [i for i in range(total_qubits) if i not in self._meas_indices]
perm_circ.append(Permutation(total_qubits, meas_qargs), range(total_qubits))
perm_circ.append(PermutationGate(meas_qargs), range(total_qubits))

return perm_circ
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
---
upgrade:
- |
Minor adjustments were made to Qiskit Experiments internals to avoid
deprecation warnings when using Qiskit 1.3. See `#1482
<https://github.com/qiskit-community/qiskit-experiments/pull/1482>_`.
36 changes: 25 additions & 11 deletions test/library/characterization/test_t1.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,10 @@

from test.base import QiskitExperimentsTestCase
import numpy as np
from qiskit.circuit import Delay, Parameter
from qiskit.circuit.library import CXGate, Measure, RXGate
from qiskit.qobj.utils import MeasLevel
from qiskit.transpiler import InstructionProperties, Target
from qiskit_ibm_runtime.fake_provider import FakeAthensV2
from qiskit_experiments.test.noisy_delay_aer_simulator import NoisyDelayAerBackend
from qiskit_experiments.framework import ExperimentData, ParallelExperiment
Expand Down Expand Up @@ -249,22 +252,33 @@ def test_t1_low_quality(self):
def test_t1_parallel_exp_transpile(self):
"""Test parallel transpile options for T1 experiment"""
num_qubits = 5
instruction_durations = []
for i in range(num_qubits):
instruction_durations += [
("rx", [i], (i + 1) * 10, "ns"),
("measure", [i], (i + 1) * 1000, "ns"),
]
coupling_map = [[i - 1, i] for i in range(1, num_qubits)]
basis_gates = ["rx", "delay"]
target = Target(num_qubits=num_qubits)
target.add_instruction(
RXGate(Parameter("t")),
properties={
(i,): InstructionProperties(duration=(i + 1) * 10e-9) for i in range(num_qubits)
},
)
target.add_instruction(
Measure(),
properties={
(i,): InstructionProperties(duration=(i + 1) * 1e-6) for i in range(num_qubits)
},
)
target.add_instruction(
Delay(Parameter("t")),
properties={(i,): None for i in range(num_qubits)},
)
target.add_instruction(
CXGate(),
properties={(i - 1, i): None for i in range(1, num_qubits)},
)

exp1 = T1([1], delays=[50e-9, 100e-9, 160e-9])
exp2 = T1([3], delays=[40e-9, 80e-9, 190e-9])
parexp = ParallelExperiment([exp1, exp2], flatten_results=False)
parexp.set_transpile_options(
basis_gates=basis_gates,
instruction_durations=instruction_durations,
coupling_map=coupling_map,
target=target,
scheduling_method="alap",
)

Expand Down
12 changes: 8 additions & 4 deletions test/library/tomography/tomo_utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -52,8 +52,10 @@ def teleport_circuit(flatten_creg=True):
teleport.measure(0, creg[0])
teleport.measure(1, creg[1])
# Conditionals
teleport.z(2).c_if(creg[0], 1)
teleport.x(2).c_if(creg[1], 1)
with teleport.if_test((creg[0], True)):
teleport.z(2)
with teleport.if_test((creg[1], True)):
teleport.x(2)
return teleport


Expand All @@ -76,8 +78,10 @@ def teleport_bell_circuit(flatten_creg=True):
teleport.h(0)
teleport.measure(0, creg[0])
teleport.measure(1, creg[1])
teleport.z(2).c_if(creg[0], 1)
teleport.x(2).c_if(creg[1], 1)
with teleport.if_test((creg[0], True)):
teleport.z(2)
with teleport.if_test((creg[1], True)):
teleport.x(2)
return teleport


Expand Down

0 comments on commit 15f6055

Please sign in to comment.