Beispiel #1
0
 def _define(self):
     """
     gate cu3(theta,phi,lambda) c, t
     { u1(pi/2) t;
       cx c,t;
       u3(-theta/2,0,0) t;
       cx c,t;
       u3(theta/2,-pi/2,0) t;
     }
     """
     from qiskit.extensions.standard.u1 import U1Gate
     from qiskit.extensions.standard.u3 import U3Gate
     from qiskit.extensions.standard.x import CnotGate
     definition = []
     q = QuantumRegister(2, 'q')
     rule = [
         (U1Gate(pi / 2), [q[1]], []),
         (CnotGate(), [q[0], q[1]], []),
         (U3Gate(-self.params[0] / 2, 0, 0), [q[1]], []),
         (CnotGate(), [q[0], q[1]], []),
         (U3Gate(self.params[0] / 2, -pi / 2, 0), [q[1]], [])
     ]
     for inst in rule:
         definition.append(inst)
     self.definition = definition
Beispiel #2
0
 def _define_decompositions(self):
     """
     gate cu3(theta,phi,lambda) c, t
     { u1((lambda-phi)/2) t; cx c,t;
       u3(-theta/2,0,-(phi+lambda)/2) t; cx c,t;
       u3(theta/2,phi,0) t;
     }
     """
     decomposition = DAGCircuit()
     q = QuantumRegister(2, "q")
     decomposition.add_qreg(q)
     decomposition.add_basis_element("u1", 1, 0, 1)
     decomposition.add_basis_element("u3", 1, 0, 3)
     decomposition.add_basis_element("cx", 2, 0, 0)
     rule = [
         U1Gate((self.param[2] - self.param[1]) / 2, q[1]),
         CnotGate(q[0], q[1]),
         U3Gate(-self.param[0] / 2, 0, -(self.param[1] + self.param[2]) / 2,
                q[1]),
         CnotGate(q[0], q[1]),
         U3Gate(self.param[0] / 2, self.param[1], 0, q[1])
     ]
     for inst in rule:
         decomposition.apply_operation_back(inst)
     self._decompositions = [decomposition]
Beispiel #3
0
 def _define(self):
     definition = []
     q = QuantumRegister(1, "q")
     rule = [(U3Gate(0, 0, 0), [q[0]], [])]
     for inst in rule:
         definition.append(inst)
     self.definition = definition
Beispiel #4
0
def simplify_U(theta, phi, lam):
    """Return the gate u1, u2, or u3 implementing U with the fewest pulses.

    The returned gate implements U exactly, not up to a global phase.

    Args:
        theta, phi, lam: input Euler rotation angles for a general U gate

    Returns:
        Gate: one of IdGate, U1Gate, U2Gate, U3Gate.
    """
    gate = U3Gate(theta, phi, lam)
    # Y rotation is 0 mod 2*pi, so the gate is a u1
    if abs(gate.params[0] % (2.0 * math.pi)) < _CUTOFF_PRECISION:
        gate = U1Gate(gate.params[0] + gate.params[1] + gate.params[2])
    # Y rotation is pi/2 or -pi/2 mod 2*pi, so the gate is a u2
    if isinstance(gate, U3Gate):
        # theta = pi/2 + 2*k*pi
        if abs((gate.params[0] - math.pi / 2) %
               (2.0 * math.pi)) < _CUTOFF_PRECISION:
            gate = U2Gate(gate.params[1],
                          gate.params[2] + (gate.params[0] - math.pi / 2))
        # theta = -pi/2 + 2*k*pi
        if abs((gate.params[0] + math.pi / 2) %
               (2.0 * math.pi)) < _CUTOFF_PRECISION:
            gate = U2Gate(
                gate.params[1] + math.pi,
                gate.params[2] - math.pi + (gate.params[0] + math.pi / 2))
    # u1 and lambda is 0 mod 4*pi so gate is nop
    if isinstance(gate, U1Gate) and abs(gate.params[0] %
                                        (4.0 * math.pi)) < _CUTOFF_PRECISION:
        gate = IdGate()
    return gate
Beispiel #5
0
 def _define(self):
     definition = []
     q = QuantumRegister(1, "q")
     rule = [(U3Gate(pi / 2, self.params[0], self.params[1]), [q[0]], [])]
     for inst in rule:
         definition.append(inst)
     self.definition = definition
Beispiel #6
0
 def _define(self):
     """
     self.u3(theta / 2, 0, 0, q_target)
     self.cx(q_control, q_target)
     self.u3(-theta / 2, 0, 0, q_target)
     self.cx(q_control, q_target)
     """
     definition = []
     q = QuantumRegister(2, "q")
     rule = [(U3Gate(self.params[0] / 2, 0, 0), [q[1]], []),
             (CnotGate(), [q[0], q[1]], []),
             (U3Gate(-self.params[0] / 2, 0, 0), [q[1]], []),
             (CnotGate(), [q[0], q[1]], [])]
     for inst in rule:
         definition.append(inst)
     self.definition = definition
Beispiel #7
0
    def __call__(self, target, basis_fidelity=None):
        """Decompose a two-qubit unitary over fixed basis + SU(2) using the best approximation given
        that each basis application has a finite fidelity.
        """
        basis_fidelity = basis_fidelity or self.basis_fidelity
        if hasattr(target, 'to_operator'):
            # If input is a BaseOperator subclass this attempts to convert
            # the object to an Operator so that we can extract the underlying
            # numpy matrix from `Operator.data`.
            target = target.to_operator().data
        if hasattr(target, 'to_matrix'):
            # If input is Gate subclass or some other class object that has
            # a to_matrix method this will call that method.
            target = target.to_matrix()
        # Convert to numpy array incase not already an array
        target = np.asarray(target, dtype=complex)
        # Check input is a 2-qubit unitary
        if target.shape != (4, 4):
            raise QiskitError(
                "TwoQubitBasisDecomposer: expected 4x4 matrix for target")
        if not is_unitary_matrix(target):
            raise QiskitError(
                "TwoQubitBasisDecomposer: target matrix is not unitary.")

        target_decomposed = TwoQubitWeylDecomposition(target)
        traces = self.traces(target_decomposed)
        expected_fidelities = [
            trace_to_fid(traces[i]) * basis_fidelity**i for i in range(4)
        ]

        best_nbasis = np.argmax(expected_fidelities)
        decomposition = self.decomposition_fns[best_nbasis](target_decomposed)
        decomposition_angles = [_DECOMPOSER1Q.angles(x) for x in decomposition]

        q = QuantumRegister(2)
        return_circuit = QuantumCircuit(q)
        for i in range(best_nbasis):
            return_circuit.append(U3Gate(*decomposition_angles[2 * i]), [q[0]])
            return_circuit.append(U3Gate(*decomposition_angles[2 * i + 1]),
                                  [q[1]])
            return_circuit.append(self.gate, [q[0], q[1]])
        return_circuit.append(U3Gate(*decomposition_angles[2 * best_nbasis]),
                              [q[0]])
        return_circuit.append(
            U3Gate(*decomposition_angles[2 * best_nbasis + 1]), [q[1]])

        return return_circuit
Beispiel #8
0
 def _define_decompositions(self):
     decomposition = DAGCircuit()
     q = QuantumRegister(1, "q")
     decomposition.add_qreg(q)
     rule = [U3Gate(pi, pi / 2, pi / 2, q[0])]
     for inst in rule:
         decomposition.apply_operation_back(inst)
     self._decompositions = [decomposition]
Beispiel #9
0
 def _define(self):
     from qiskit.extensions.standard.u3 import U3Gate
     definition = []
     q = QuantumRegister(1, "q")
     rule = [(U3Gate(pi, pi / 2, pi / 2), [q[0]], [])]
     for inst in rule:
         definition.append(inst)
     self.definition = definition
Beispiel #10
0
 def _define(self):
     from qiskit.extensions.standard.u3 import U3Gate
     definition = []
     q = QuantumRegister(1, 'q')
     rule = [(U3Gate(0, 0, self.params[0]), [q[0]], [])]
     for inst in rule:
         definition.append(inst)
     self.definition = definition
Beispiel #11
0
 def _define(self):
     """
     gate cu3(theta,phi,lambda) c, t
     { u1((lambda-phi)/2) t; cx c,t;
       u3(-theta/2,0,-(phi+lambda)/2) t; cx c,t;
       u3(theta/2,phi,0) t;
     }
     """
     definition = []
     q = QuantumRegister(2, "q")
     rule = [(U1Gate((self.params[2] - self.params[1]) / 2), [q[1]], []),
             (CnotGate(), [q[0], q[1]], []),
             (U3Gate(-self.params[0] / 2, 0,
                     -(self.params[1] + self.params[2]) / 2), [q[1]], []),
             (CnotGate(), [q[0], q[1]], []),
             (U3Gate(self.params[0] / 2, self.params[1], 0), [q[1]], [])]
     for inst in rule:
         definition.append(inst)
     self.definition = definition
Beispiel #12
0
 def _define(self):
     """
     gate ry(theta) a { u3(theta, 0, 0) a; }
     """
     definition = []
     q = QuantumRegister(1, "q")
     rule = [(U3Gate(self.params[0], 0, 0), [q[0]], [])]
     for inst in rule:
         definition.append(inst)
     self.definition = definition
Beispiel #13
0
    def _define(self):
        """
        gate cry(lambda) a,b
        { u3(lambda/2,0,0) b; cx a,b;
          u3(-lambda/2,0,0) b; cx a,b;
        }

        """
        from qiskit.extensions.standard.x import CnotGate
        from qiskit.extensions.standard.u3 import U3Gate
        definition = []
        q = QuantumRegister(2, "q")
        rule = [(U3Gate(self.params[0] / 2, 0, 0), [q[1]], []),
                (CnotGate(), [q[0], q[1]], []),
                (U3Gate(-self.params[0] / 2, 0, 0), [q[1]], []),
                (CnotGate(), [q[0], q[1]], [])]
        for inst in rule:
            definition.append(inst)
        self.definition = definition
Beispiel #14
0
 def _define_decompositions(self):
     """
     gate ry(theta) a { u3(theta, 0, 0) a; }
     """
     decomposition = DAGCircuit()
     q = QuantumRegister(1, "q")
     decomposition.add_qreg(q)
     rule = [U3Gate(self.params[0], 0, 0, q[0])]
     for inst in rule:
         decomposition.apply_operation_back(inst)
     self._decompositions = [decomposition]
Beispiel #15
0
 def _define(self):
     """
     gate x a { u3(pi,0,pi) a; }
     """
     from qiskit.extensions.standard.u3 import U3Gate
     definition = []
     q = QuantumRegister(1, 'q')
     rule = [(U3Gate(pi, 0, pi), [q[0]], [])]
     for inst in rule:
         definition.append(inst)
     self.definition = definition
 def _define(self):
     self.definition = []
     q = QuantumRegister(self.num_qubits)
     theta = qRAM_encoding_angles(self.distribution, self.num_qubits)
     self.definition.append((U3Gate(2 * theta[0][0], 0, 0), q[self.num_qubits - 1], []))
     for step in range(self.num_qubits - 1):
         step = step + 1
         ctrl_q = list(map(lambda x: q[self.num_qubits - x - 1], range(step)))
         for region in range(2 ** step):
             self.definition.append((XRegionGate(self.num_qubits, to_bin(region, step)), q, []))
             self.definition.append((RYGate(- 2 * theta[step][region]).control(len(ctrl_q)), ctrl_q + [q[self.num_qubits - step - 1]], []))
             self.definition.append((XRegionGate(self.num_qubits, to_bin(region, step)), q, []))
Beispiel #17
0
 def _define_decompositions(self):
     """
     gate rx(theta) a {u3(theta, -pi/2, pi/2) a;}
     """
     decomposition = DAGCircuit()
     q = QuantumRegister(1, "q")
     decomposition.add_qreg(q)
     decomposition.add_basis_element("u3", 1, 0, 3)
     rule = [U3Gate(self.param[0], -pi / 2, pi / 2, q[0])]
     for inst in rule:
         decomposition.apply_operation_back(inst)
     self._decompositions = [decomposition]
Beispiel #18
0
 def _define(self):
     """
     gate x a {
     u3(pi,0,pi) a;
     }
     """
     definition = []
     q = QuantumRegister(1, "q")
     rule = [(U3Gate(pi, 0, pi), [q[0]], [])]
     for inst in rule:
         definition.append(inst)
     self.definition = definition
Beispiel #19
0
 def _define(self):
     """
     gate cu3(theta,phi,lambda) c, t
     { u1(pi/2) t;
       cx c,t;
       u3(-theta/2,0,0) t;
       cx c,t;
       u3(theta/2,-pi/2,0) t;
     }
     """
     definition = []
     q = QuantumRegister(2, 'q')
     rule = [
         (U1Gate(pi / 2), [q[1]], []),
         (CnotGate(), [q[0], q[1]], []),
         (U3Gate(-self.params[0] / 2, 0, 0), [q[1]], []),
         (CnotGate(), [q[0], q[1]], []),
         (U3Gate(self.params[0] / 2, -pi / 2, 0), [q[1]], [])
     ]
     for inst in rule:
         definition.append(inst)
     self.definition = definition
Beispiel #20
0
 def _define(self):
     """
     gate r(θ, φ) a {u3(θ, φ - π/2, -φ + π/2) a;}
     """
     from qiskit.extensions.standard.u3 import U3Gate
     definition = []
     q = QuantumRegister(1, "q")
     theta = self.params[0]
     phi = self.params[1]
     rule = [(U3Gate(theta, phi - pi / 2, -phi + pi / 2), [q[0]], [])]
     for inst in rule:
         definition.append(inst)
     self.definition = definition
Beispiel #21
0
 def _define(self):
     """
     gate r(θ, φ) a {u3(θ, φ - π/2, -φ + π/2) a;}
     """
     definition = []
     q = QuantumRegister(1, "q")
     theta = self.params[0]
     phi = self.params[1]
     rule = [
         (U3Gate(theta, phi - pi / 2, -phi + pi / 2), [q[0]], [])
     ]
     for inst in rule:
         definition.append(inst)
     self.definition = definition
Beispiel #22
0
    def _define(self):
        """convert to direct rx (180 degrees)."""
        definition = []
        q = QuantumRegister(1, "q")
        if PulseBackedOptimizationContext.get():
            rule = [
                (DirectRXGate(pi), [q[0]], []),
            ]
        else:
            rule = [(U3Gate(pi, 0, pi), [q[0]], [])]

        for inst in rule:
            definition.append(inst)
        self.definition = definition
Beispiel #23
0
 def _define(self):
     """
     gate rx(theta) a {r(theta, 0) a;}
     """
     definition = []
     q = QuantumRegister(1, "q")
     if PulseBackedOptimizationContext.get():
         rule = [(DirectRXGate(self.params[0]), [q[0]], [])]
     else:
         rule = [(U3Gate(self.params[0], -np.pi / 2,
                         np.pi / 2), [q[0]], [])]
     for inst in rule:
         definition.append(inst)
     self.definition = definition
Beispiel #24
0
 def _convert_to_basis_gates(gates):
     if isinstance(gates, list):
         return [Custom._convert_to_basis_gates(gate) for gate in gates]
     elif isinstance(gates, CompositeGate):
         gates.data = [Custom._convert_to_basis_gates(gate) for gate in gates.data]
         return gates
     else:
         if isinstance(gates, RYGate):
             return U3Gate(gates.param[0], 0, 0, gates.arg[0])
         elif isinstance(gates, RZGate):
             return U1Gate(gates.param[0], gates.arg[0])
         elif isinstance(gates, CnotGate):
             return gates
         else:
             raise RuntimeError('Unexpected component {} from the initialization circuit.'.format(gates.qasm()))
Beispiel #25
0
 def _define(self):
     """Calculate a subcircuit that implements this unitary."""
     definition = []
     q = QuantumRegister(2, "q")
     theta = self.params[0]
     rule = [
         (U3Gate(np.pi / 2, theta, 0), [q[0]], []),
         (HGate(), [q[1]], []),
         (CnotGate(), [q[0], q[1]], []),
         (U1Gate(-theta), [q[1]], []),
         (CnotGate(), [q[0], q[1]], []),
         (HGate(), [q[1]], []),
         (U2Gate(-np.pi, np.pi - theta), [q[0]], []),
     ]
     for inst in rule:
         definition.append(inst)
     self.definition = definition
Beispiel #26
0
 def _define(self):
     """Calculate a subcircuit that implements this unitary."""
     from qiskit.extensions.standard.x import CnotGate
     from qiskit.extensions.standard.u1 import U1Gate
     from qiskit.extensions.standard.u2 import U2Gate
     from qiskit.extensions.standard.u3 import U3Gate
     from qiskit.extensions.standard.h import HGate
     definition = []
     q = QuantumRegister(2, "q")
     theta = self.params[0]
     rule = [
         (U3Gate(np.pi / 2, theta, 0), [q[0]], []),
         (HGate(), [q[1]], []),
         (CnotGate(), [q[0], q[1]], []),
         (U1Gate(-theta), [q[1]], []),
         (CnotGate(), [q[0], q[1]], []),
         (HGate(), [q[1]], []),
         (U2Gate(-np.pi, np.pi - theta), [q[0]], []),
     ]
     for inst in rule:
         definition.append(inst)
     self.definition = definition
 def _define(self):
     definition = []
     q = QuantumRegister(self.num_qubits)
     if self.least_significant_bit_first:
         q = q[::-1]
     theta = qRAM_encoding_angles(self.distribution, self.num_qubits)
     definition.append((U3Gate(2 * theta[0][0], 0,
                               0), [q[self.num_qubits - 1]], []))
     for step in range(self.num_qubits - 1):
         step = step + 1
         ctrl_q = list(
             map(lambda x: q[self.num_qubits - x - 1], range(step)))
         for region in range(2**step):
             definition.append((XRegionGate(self.num_qubits,
                                            region), q, []))
             definition.append(
                 (RYGate(-2 * theta[step][region]).control(len(ctrl_q)),
                  ctrl_q + [q[self.num_qubits - step - 1]], []))
             definition.append((XRegionGate(self.num_qubits,
                                            region), q, []))
     if self.least_significant_bit_first:
         q = q[::-1]
     self.definition = definition
    def run(self, dag):
        """Return a new circuit that has been optimized."""
        runs = dag.collect_runs(["u1", "u2", "u3", "id"])
        for run in runs:
            right_name = "u1"
            right_parameters = (0, 0, 0)  # (theta, phi, lambda)

            for current_node in run:
                left_name = current_node.name
                if (current_node.condition is not None
                        or len(current_node.qargs) != 1
                        or left_name not in ["u1", "u2", "u3", "id"]):
                    raise MapperError("internal error")
                if left_name == "u1":
                    left_parameters = (0, 0, current_node.op.params[0])
                elif left_name == "u2":
                    left_parameters = (np.pi / 2, current_node.op.params[0],
                                       current_node.op.params[1])
                elif left_name == "u3":
                    left_parameters = tuple(current_node.op.params)
                else:
                    left_name = "u1"  # replace id with u1
                    left_parameters = (0, 0, 0)
                # If there are any sympy objects coming from the gate convert
                # to numpy.
                left_parameters = tuple([float(x) for x in left_parameters])
                # Compose gates
                name_tuple = (left_name, right_name)
                if name_tuple == ("u1", "u1"):
                    # u1(lambda1) * u1(lambda2) = u1(lambda1 + lambda2)
                    right_parameters = (0, 0, right_parameters[2] +
                                        left_parameters[2])
                elif name_tuple == ("u1", "u2"):
                    # u1(lambda1) * u2(phi2, lambda2) = u2(phi2 + lambda1, lambda2)
                    right_parameters = (np.pi / 2, right_parameters[1] +
                                        left_parameters[2],
                                        right_parameters[2])
                elif name_tuple == ("u2", "u1"):
                    # u2(phi1, lambda1) * u1(lambda2) = u2(phi1, lambda1 + lambda2)
                    right_name = "u2"
                    right_parameters = (np.pi / 2, left_parameters[1],
                                        right_parameters[2] +
                                        left_parameters[2])
                elif name_tuple == ("u1", "u3"):
                    # u1(lambda1) * u3(theta2, phi2, lambda2) =
                    #     u3(theta2, phi2 + lambda1, lambda2)
                    right_parameters = (right_parameters[0],
                                        right_parameters[1] +
                                        left_parameters[2],
                                        right_parameters[2])
                elif name_tuple == ("u3", "u1"):
                    # u3(theta1, phi1, lambda1) * u1(lambda2) =
                    #     u3(theta1, phi1, lambda1 + lambda2)
                    right_name = "u3"
                    right_parameters = (left_parameters[0], left_parameters[1],
                                        right_parameters[2] +
                                        left_parameters[2])
                elif name_tuple == ("u2", "u2"):
                    # Using Ry(pi/2).Rz(2*lambda).Ry(pi/2) =
                    #    Rz(pi/2).Ry(pi-2*lambda).Rz(pi/2),
                    # u2(phi1, lambda1) * u2(phi2, lambda2) =
                    #    u3(pi - lambda1 - phi2, phi1 + pi/2, lambda2 + pi/2)
                    right_name = "u3"
                    right_parameters = (np.pi - left_parameters[2] -
                                        right_parameters[1],
                                        left_parameters[1] + np.pi / 2,
                                        right_parameters[2] + np.pi / 2)
                elif name_tuple[1] == "nop":
                    right_name = left_name
                    right_parameters = left_parameters
                else:
                    # For composing u3's or u2's with u3's, use
                    # u2(phi, lambda) = u3(pi/2, phi, lambda)
                    # together with the qiskit.mapper.compose_u3 method.
                    right_name = "u3"
                    # Evaluate the symbolic expressions for efficiency
                    right_parameters = Optimize1qGates.compose_u3(
                        left_parameters[0], left_parameters[1],
                        left_parameters[2], right_parameters[0],
                        right_parameters[1], right_parameters[2])
                    # Why evalf()? This program:
                    #   OPENQASM 2.0;
                    #   include "qelib1.inc";
                    #   qreg q[2];
                    #   creg c[2];
                    #   u3(0.518016983430947*pi,1.37051598592907*pi,1.36816383603222*pi) q[0];
                    #   u3(1.69867232277986*pi,0.371448347747471*pi,0.461117217930936*pi) q[0];
                    #   u3(0.294319836336836*pi,0.450325871124225*pi,1.46804720442555*pi) q[0];
                    #   measure q -> c;
                    # took >630 seconds (did not complete) to optimize without
                    # calling evalf() at all, 19 seconds to optimize calling
                    # evalf() AFTER compose_u3, and 1 second to optimize
                    # calling evalf() BEFORE compose_u3.
                # 1. Here down, when we simplify, we add f(theta) to lambda to
                # correct the global phase when f(theta) is 2*pi. This isn't
                # necessary but the other steps preserve the global phase, so
                # we continue in that manner.
                # 2. The final step will remove Z rotations by 2*pi.
                # 3. Note that is_zero is true only if the expression is exactly
                # zero. If the input expressions have already been evaluated
                # then these final simplifications will not occur.
                # TODO After we refactor, we should have separate passes for
                # exact and approximate rewriting.

                # Y rotation is 0 mod 2*pi, so the gate is a u1
                if np.mod(right_parameters[0], (2 * np.pi)) == 0 \
                        and right_name != "u1":
                    right_name = "u1"
                    right_parameters = (0, 0, right_parameters[1] +
                                        right_parameters[2] +
                                        right_parameters[0])
                # Y rotation is pi/2 or -pi/2 mod 2*pi, so the gate is a u2
                if right_name == "u3":
                    # theta = pi/2 + 2*k*pi
                    if np.mod((right_parameters[0] - np.pi / 2),
                              (2 * np.pi)) == 0:
                        right_name = "u2"
                        right_parameters = (np.pi / 2, right_parameters[1],
                                            right_parameters[2] +
                                            (right_parameters[0] - np.pi / 2))
                    # theta = -pi/2 + 2*k*pi
                    if np.mod((right_parameters[0] + np.pi / 2),
                              (2 * np.pi)) == 0:
                        right_name = "u2"
                        right_parameters = (np.pi / 2,
                                            right_parameters[1] + np.pi,
                                            right_parameters[2] - np.pi +
                                            (right_parameters[0] + np.pi / 2))
                # u1 and lambda is 0 mod 2*pi so gate is nop (up to a global phase)
                if right_name == "u1" and np.mod(right_parameters[2],
                                                 (2 * np.pi)) == 0:
                    right_name = "nop"

            # Replace the the first node in the run with a dummy DAG which contains a dummy
            # qubit. The name is irrelevant, because substitute_node_with_dag will take care of
            # putting it in the right place.
            run_qarg = (QuantumRegister(1, 'q'), 0)
            new_op = Gate(name="", num_qubits=1, params=[])
            if right_name == "u1":
                new_op = U1Gate(right_parameters[2])
            if right_name == "u2":
                new_op = U2Gate(right_parameters[1], right_parameters[2])
            if right_name == "u3":
                new_op = U3Gate(*right_parameters)

            if right_name != 'nop':
                new_dag = DAGCircuit()
                new_dag.add_qreg(run_qarg[0])
                new_dag.apply_operation_back(new_op, [run_qarg], [])
                dag.substitute_node_with_dag(run[0], new_dag)

            # Delete the other nodes in the run
            for current_node in run[1:]:
                dag.remove_op_node(current_node)
            if right_name == "nop":
                dag.remove_op_node(run[0])

        return dag
    def create_dag_op(self, name, args, qubits):
        """Create a DAG op node.
        """
        if name == "u0":
            op = U0Gate(args[0], qubits[0])
        elif name == "u1":
            op = U1Gate(args[0], qubits[0])
        elif name == "u2":
            op = U2Gate(args[0], args[1], qubits[0])
        elif name == "u3":
            op = U3Gate(args[0], args[1], args[2], qubits[0])
        elif name == "x":
            op = XGate(qubits[0])
        elif name == "y":
            op = YGate(qubits[0])
        elif name == "z":
            op = ZGate(qubits[0])
        elif name == "t":
            op = TGate(qubits[0])
        elif name == "tdg":
            op = TdgGate(qubits[0])
        elif name == "s":
            op = SGate(qubits[0])
        elif name == "sdg":
            op = SdgGate(qubits[0])
        elif name == "swap":
            op = SwapGate(qubits[0], qubits[1])
        elif name == "rx":
            op = RXGate(args[0], qubits[0])
        elif name == "ry":
            op = RYGate(args[0], qubits[0])
        elif name == "rz":
            op = RZGate(args[0], qubits[0])
        elif name == "rzz":
            op = RZZGate(args[0], qubits[0], qubits[1])
        elif name == "id":
            op = IdGate(qubits[0])
        elif name == "h":
            op = HGate(qubits[0])
        elif name == "cx":
            op = CnotGate(qubits[0], qubits[1])
        elif name == "cy":
            op = CyGate(qubits[0], qubits[1])
        elif name == "cz":
            op = CzGate(qubits[0], qubits[1])
        elif name == "ch":
            op = CHGate(qubits[0], qubits[1])
        elif name == "crz":
            op = CrzGate(args[0], qubits[0], qubits[1])
        elif name == "cu1":
            op = Cu1Gate(args[0], qubits[0], qubits[1])
        elif name == "cu3":
            op = Cu3Gate(args[0], args[1], args[2], qubits[0], qubits[1])
        elif name == "ccx":
            op = ToffoliGate(qubits[0], qubits[1], qubits[2])
        elif name == "cswap":
            op = FredkinGate(qubits[0], qubits[1], qubits[2])
        else:
            raise BackendError("unknown operation for name ast node name %s" %
                               name)

        self.circuit.add_basis_element(op.name, len(op.qargs), len(op.cargs),
                                       len(op.param))
        self.start_gate(op)
        self.end_gate(op)
Beispiel #30
0
    def _process_node(self, node):
        """Carry out the action associated with a node."""
        if node.type == "program":
            self._process_children(node)

        elif node.type == "qreg":
            qreg = QuantumRegister(node.index, node.name)
            self.dag.add_qreg(qreg)

        elif node.type == "creg":
            creg = ClassicalRegister(node.index, node.name)
            self.dag.add_creg(creg)

        elif node.type == "id":
            raise QiskitError("internal error: _process_node on id")

        elif node.type == "int":
            raise QiskitError("internal error: _process_node on int")

        elif node.type == "real":
            raise QiskitError("internal error: _process_node on real")

        elif node.type == "indexed_id":
            raise QiskitError("internal error: _process_node on indexed_id")

        elif node.type == "id_list":
            # We process id_list nodes when they are leaves of barriers.
            return [
                self._process_bit_id(node_children)
                for node_children in node.children
            ]

        elif node.type == "primary_list":
            # We should only be called for a barrier.
            return [self._process_bit_id(m) for m in node.children]

        elif node.type == "gate":
            self._process_gate(node)

        elif node.type == "custom_unitary":
            self._process_custom_unitary(node)

        elif node.type == "universal_unitary":
            args = self._process_node(node.children[0])
            qid = self._process_bit_id(node.children[1])
            for element in qid:
                self.dag.apply_operation_back(U3Gate(*args, element),
                                              self.condition)

        elif node.type == "cnot":
            self._process_cnot(node)

        elif node.type == "expression_list":
            return node.children

        elif node.type == "binop":
            raise QiskitError("internal error: _process_node on binop")

        elif node.type == "prefix":
            raise QiskitError("internal error: _process_node on prefix")

        elif node.type == "measure":
            self._process_measure(node)

        elif node.type == "format":
            self.version = node.version()

        elif node.type == "barrier":
            ids = self._process_node(node.children[0])
            qubits = []
            for qubit in ids:
                for j, _ in enumerate(qubit):
                    qubits.append(qubit[j])
            self.dag.apply_operation_back(Barrier(len(qubits)), qubits, [])

        elif node.type == "reset":
            id0 = self._process_bit_id(node.children[0])
            for i, _ in enumerate(id0):
                self.dag.apply_operation_back(Reset(), [id0[i]], [],
                                              self.condition)

        elif node.type == "if":
            self._process_if(node)

        elif node.type == "opaque":
            self._process_gate(node, opaque=True)

        elif node.type == "external":
            raise QiskitError("internal error: _process_node on external")

        else:
            raise QiskitError("internal error: undefined node type", node.type,
                              "line=%s" % node.line, "file=%s" % node.file)
        return None