Пример #1
0
    def test_zero_coeff(self):
        """
            test addition
        """
        pauli_a = 'IXYZ'
        pauli_b = 'IXYZ'
        coeff_a = 0.5
        coeff_b = -0.5
        pauli_term_a = [coeff_a, label_to_pauli(pauli_a)]
        pauli_term_b = [coeff_b, label_to_pauli(pauli_b)]
        opA = Operator(paulis=[pauli_term_a])
        opB = Operator(paulis=[pauli_term_b])
        newOP = opA + opB

        self.assertEqual(0, len(newOP.paulis),
                         "{}".format(newOP.print_operators()))

        paulis = ['IXYZ', 'XXZY', 'IIZZ', 'XXYY', 'ZZXX', 'YYYY']
        coeffs = [0.2, 0.6, 0.8, -0.2, -0.6, -0.8]
        op = Operator(paulis=[])
        for coeff, pauli in zip(coeffs, paulis):
            pauli_term = [coeff, label_to_pauli(pauli)]
            op += Operator(paulis=[pauli_term])

        for i in range(6):
            opA = Operator(paulis=[[-coeffs[i], label_to_pauli(paulis[i])]])
            op += opA
            self.assertEqual(6 - (i + 1), len(op.paulis))
Пример #2
0
    def setUp(self):
        np.random.seed(0)

        self.num_qubits = 4
        m_size = np.power(2, self.num_qubits)
        matrix = np.random.rand(m_size, m_size)
        self.qubitOp = Operator(matrix=matrix)
Пример #3
0
    def test_addition_noninplace(self):
        """
            test addition
        """
        pauli_a = 'IXYZ'
        pauli_b = 'ZYIX'
        coeff_a = 0.5
        coeff_b = 0.5
        pauli_term_a = [coeff_a, label_to_pauli(pauli_a)]
        pauli_term_b = [coeff_b, label_to_pauli(pauli_b)]
        opA = Operator(paulis=[pauli_term_a])
        opB = Operator(paulis=[pauli_term_b])
        copy_opA = copy.deepcopy(opA)
        newOP = opA + opB

        self.assertEqual(copy_opA, opA)
        self.assertEqual(2, len(newOP.paulis))

        pauli_c = 'IXYZ'
        coeff_c = 0.25
        pauli_term_c = [coeff_c, label_to_pauli(pauli_c)]
        newOP = newOP + Operator(paulis=[pauli_term_c])

        self.assertEqual(2, len(newOP.paulis))
        self.assertEqual(0.75, newOP.paulis[0][0])
Пример #4
0
    def _setup_qpe(self):
        self._operator._check_representation('paulis')
        self._ret['translation'] = sum(
            [abs(p[0]) for p in self._operator.paulis])
        self._ret['stretch'] = 0.5 / self._ret['translation']

        # translate the operator
        self._operator._simplify_paulis()
        translation_op = Operator([[
            self._ret['translation'],
            Pauli(np.zeros(self._operator.num_qubits),
                  np.zeros(self._operator.num_qubits))
        ]])
        translation_op._simplify_paulis()
        self._operator += translation_op

        # stretch the operator
        for p in self._operator._paulis:
            p[0] = p[0] * self._ret['stretch']

        # check for identify paulis to get its coef for applying global phase shift on ancillae later
        num_identities = 0
        for p in self._operator.paulis:
            if np.all(p[1].v == 0) and np.all(p[1].w == 0):
                num_identities += 1
                if num_identities > 1:
                    raise RuntimeError(
                        'Multiple identity pauli terms are present.')
                self._ancilla_phase_coef = p[0].real if isinstance(
                    p[0], complex) else p[0]

        self._construct_qpe_evolution()
        logger.info('QPE circuit qasm length is roughly {}.'.format(
            len(self._circuit.qasm().split('\n'))))
Пример #5
0
    def test_chop_complex_only_2(self):

        paulis = ['IXYZ', 'XXZY', 'IIZZ', 'XXYY', 'ZZXX', 'YYYY']
        coeffs = [
            0.2 + -1j * 0.8, 0.6 + -1j * 0.6, 0.8 + -1j * 0.2,
            -0.2 + -1j * 0.8, -0.6 - -1j * 0.6, -0.8 - -1j * 0.2
        ]
        op = Operator(paulis=[])
        for coeff, pauli in zip(coeffs, paulis):
            pauli_term = [coeff, label_to_pauli(pauli)]
            op += Operator(paulis=[pauli_term])

        op1 = copy.deepcopy(op)
        op1.chop(threshold=0.4)
        self.assertEqual(len(op1.paulis), 6,
                         "\n{}".format(op1.print_operators()))

        op2 = copy.deepcopy(op)
        op2.chop(threshold=0.7)
        self.assertEqual(len(op2.paulis), 4,
                         "\n{}".format(op2.print_operators()))

        op3 = copy.deepcopy(op)
        op3.chop(threshold=0.9)
        self.assertEqual(len(op3.paulis), 0,
                         "\n{}".format(op3.print_operators()))
Пример #6
0
 def from_params(self, params):
     if EnergyInput.PROP_KEY_QUBITOP not in params:
         raise AlgorithmError("Qubit operator is required.")
     qparams = params[EnergyInput.PROP_KEY_QUBITOP]
     self._qubit_op = Operator.load_from_dict(qparams)
     if EnergyInput.PROP_KEY_AUXOPS in params:
         auxparams = params[EnergyInput.PROP_KEY_AUXOPS]
         self._aux_ops = [Operator.load_from_dict(auxparams[i]) for i in range(len(auxparams))]
Пример #7
0
    def test_equal_operator(self):

        paulis = ['IXYZ', 'XXZY', 'IIZZ', 'XXYY', 'ZZXX', 'YYYY']
        coeffs = [0.2, 0.6, 0.8, -0.2, -0.6, -0.8]
        op1 = Operator(paulis=[])
        for coeff, pauli in zip(coeffs, paulis):
            pauli_term = [coeff, label_to_pauli(pauli)]
            op1 += Operator(paulis=[pauli_term])

        paulis = ['IXYZ', 'XXZY', 'IIZZ', 'XXYY', 'ZZXX', 'YYYY']
        coeffs = [0.2, 0.6, 0.8, -0.2, -0.6, -0.8]
        op2 = Operator(paulis=[])
        for coeff, pauli in zip(coeffs, paulis):
            pauli_term = [coeff, label_to_pauli(pauli)]
            op2 += Operator(paulis=[pauli_term])

        paulis = ['IXYY', 'XXZY', 'IIZZ', 'XXYY', 'ZZXX', 'YYYY']
        coeffs = [0.2, 0.6, 0.8, -0.2, -0.6, -0.8]
        op3 = Operator(paulis=[])
        for coeff, pauli in zip(coeffs, paulis):
            pauli_term = [coeff, label_to_pauli(pauli)]
            op3 += Operator(paulis=[pauli_term])

        paulis = ['IXYZ', 'XXZY', 'IIZZ', 'XXYY', 'ZZXX', 'YYYY']
        coeffs = [-0.2, 0.6, 0.8, -0.2, -0.6, -0.8]
        op4 = Operator(paulis=[])
        for coeff, pauli in zip(coeffs, paulis):
            pauli_term = [coeff, label_to_pauli(pauli)]
            op4 += Operator(paulis=[pauli_term])

        self.assertEqual(op1, op2)
        self.assertNotEqual(op1, op3)
        self.assertNotEqual(op1, op4)
        self.assertNotEqual(op3, op4)
Пример #8
0
    def test_create_from_paulis_0(self):
        """
            test with single paulis
        """
        num_qubits = 4
        for pauli_label in itertools.product('IXYZ', repeat=num_qubits):
            coeff = np.random.random(1)[0]
            pauli_term = [coeff, label_to_pauli(pauli_label)]
            op = Operator(paulis=[pauli_term])

            op.convert('paulis', 'matrix')
            op.convert('paulis', 'grouped_paulis')

            depth = 1
            var_form = get_variational_form_instance('RYRZ')
            var_form.init_args(op.num_qubits, depth)
            circuit = var_form.construct_circuit(
                np.array(np.random.randn(var_form.num_parameters)))
            execute_config = {'shots': 1, 'skip_transpiler': False}
            matrix_mode = op.eval('matrix', circuit,
                                  'local_statevector_simulator',
                                  execute_config)[0]
            non_matrix_mode = op.eval('paulis', circuit,
                                      'local_statevector_simulator',
                                      execute_config)[0]
Пример #9
0
def get_partition_qubitops(values):
    """Construct the Hamiltonian for a given Partition instance.

    Given a list of numbers for the Number Partitioning problem, we
    construct the Hamiltonian described as a list of Pauli gates.

    Args:
        values (numpy.ndarray): array of values.

    Returns:
        operator.Operator, float: operator for the Hamiltonian and a
        constant shift for the obj function.

    """
    n = len(values)
    # The Hamiltonian is:
    # \sum_{i,j=1,\dots,n} ij z_iz_j + \sum_{i=1,\dots,n} i^2
    pauli_list = []
    for i in range(n):
        for j in range(i):
            wp = np.zeros(n)
            vp = np.zeros(n)
            vp[i] = 1
            vp[j] = 1
            pauli_list.append((2 * values[i] * values[j], Pauli(vp, wp)))
    return Operator(paulis=pauli_list), sum(values * values)
Пример #10
0
    def _two_body_mapping(h2_ijkm, a_i, a_j, a_k, a_m, threshold):
        """
        Subroutine for two body mapping.

        Args:
            h1_ijkm (complex): value of h2 at index (i,j,k,m)
            a_i (Pauli): pauli at index i
            a_j (Pauli): pauli at index j
            a_k (Pauli): pauli at index k
            a_m (Pauli): pauli at index m
            threshold: (float): threshold to remove a pauli

        Returns:
            Operator: Operator for those paulis
        """
        pauli_list = []
        for alpha in range(2):
            for beta in range(2):
                for gamma in range(2):
                    for delta in range(2):
                        pauli_prod_1 = sgn_prod(a_i[alpha], a_k[beta])
                        pauli_prod_2 = sgn_prod(pauli_prod_1[0], a_m[gamma])
                        pauli_prod_3 = sgn_prod(pauli_prod_2[0], a_j[delta])

                        phase1 = pauli_prod_1[1] * pauli_prod_2[
                            1] * pauli_prod_3[1]
                        phase2 = np.power(-1j, alpha + beta) * np.power(
                            1j, gamma + delta)
                        pauli_term = [
                            h2_ijkm / 16 * phase1 * phase2, pauli_prod_3[0]
                        ]
                        if np.absolute(pauli_term[0]) > threshold:
                            pauli_list.append(pauli_term)
        return Operator(paulis=pauli_list)
Пример #11
0
def get_stableset_qubitops(w):
    """Generate Hamiltonian for the maximum stableset in a graph.

    Args:
        w (numpy.ndarray) : adjacency matrix.

    Returns:
        operator.Operator, float: operator for the Hamiltonian and a
        constant shift for the obj function.

    """
    num_nodes = len(w)
    pauli_list = []
    shift = 0
    for i in range(num_nodes):
        for j in range(i + 1, num_nodes):
            if (w[i, j] != 0):
                wp = np.zeros(num_nodes)
                vp = np.zeros(num_nodes)
                vp[i] = 1
                vp[j] = 1
                pauli_list.append((1.0, Pauli(vp, wp)))
                shift += 1
    for i in range(num_nodes):
        degree = sum(w[i, :])
        wp = np.zeros(num_nodes)
        vp = np.zeros(num_nodes)
        vp[i] = 1
        pauli_list.append((degree - 1 / 2, Pauli(vp, wp)))
    return Operator(paulis=pauli_list), shift - num_nodes / 2
Пример #12
0
    def test_multiplication(self):
        """
            test multiplication
        """
        pauli_a = 'IXYZ'
        pauli_b = 'ZYIX'
        coeff_a = 0.5
        coeff_b = 0.5
        pauli_term_a = [coeff_a, label_to_pauli(pauli_a)]
        pauli_term_b = [coeff_b, label_to_pauli(pauli_b)]
        opA = Operator(paulis=[pauli_term_a])
        opB = Operator(paulis=[pauli_term_b])
        newOP = opA * opB
        # print(newOP.print_operators())

        self.assertEqual(1, len(newOP.paulis))
        self.assertEqual(-0.25, newOP.paulis[0][0])
        self.assertEqual('ZZYY', newOP.paulis[0][1].to_label())
Пример #13
0
    def _compute_energy(self):
        self._operator._check_representation('paulis')
        self._ret['translation'] = sum(
            [abs(p[0]) for p in self._operator.paulis])
        self._ret['stretch'] = 0.5 / self._ret['translation']

        # translate the operator
        self._operator._simplify_paulis()
        translation_op = Operator([[
            self._ret['translation'],
            Pauli(np.zeros(self._operator.num_qubits),
                  np.zeros(self._operator.num_qubits))
        ]])
        translation_op._simplify_paulis()
        self._operator += translation_op

        # stretch the operator
        for p in self._operator._paulis:
            p[0] = p[0] * self._ret['stretch']

        # check for identify paulis to get its coef for applying global phase shift on ancilla later
        num_identities = 0
        for p in self._operator.paulis:
            if np.all(p[1].v == 0) and np.all(p[1].w == 0):
                num_identities += 1
                if num_identities > 1:
                    raise RuntimeError(
                        'Multiple identity pauli terms are present.')
                self._ancilla_phase_coef = p[0].real if isinstance(
                    p[0], complex) else p[0]

        self._ret['phase'] = self._estimate_phase_iteratively()
        self._ret['top_measurement_decimal'] = sum([
            t[0] * t[1] for t in
            zip([1 / 2**p for p in range(1, self._num_iterations + 1)],
                [int(n) for n in self._ret['top_measurement_label']])
        ])
        self._ret['energy'] = self._ret['phase'] / self._ret[
            'stretch'] - self._ret['translation']
Пример #14
0
    def test_addition_inplace(self):
        """
            test addition
        """
        pauli_a = 'IXYZ'
        pauli_b = 'ZYIX'
        coeff_a = 0.5
        coeff_b = 0.5
        pauli_term_a = [coeff_a, label_to_pauli(pauli_a)]
        pauli_term_b = [coeff_b, label_to_pauli(pauli_b)]
        opA = Operator(paulis=[pauli_term_a])
        opB = Operator(paulis=[pauli_term_b])
        opA += opB

        self.assertEqual(2, len(opA.paulis))

        pauli_c = 'IXYZ'
        coeff_c = 0.25
        pauli_term_c = [coeff_c, label_to_pauli(pauli_c)]
        opA += Operator(paulis=[pauli_term_c])

        self.assertEqual(2, len(opA.paulis))
        self.assertEqual(0.75, opA.paulis[0][0])
Пример #15
0
        def __init__(self, cost_operator, p):
            self.cost_operator = cost_operator
            self.p = p
            self.num_parameters = 2 * p
            self.parameter_bounds = [(0, np.pi)] * p + [(0, 2 * np.pi)] * p
            self.preferred_init_points = [0] * p * 2

            # prepare the mixer operator
            v = np.zeros(self.cost_operator.num_qubits)
            ws = np.eye(self.cost_operator.num_qubits)
            self.mixer_operator = reduce(lambda x, y: x + y, [
                Operator([[1, Pauli(v, ws[i, :])]])
                for i in range(self.cost_operator.num_qubits)
            ])
Пример #16
0
    def test_zero_elimination(self):
        pauli_a = 'IXYZ'
        coeff_a = 0.0
        pauli_term_a = [coeff_a, label_to_pauli(pauli_a)]
        opA = Operator(paulis=[pauli_term_a])
        self.assertEqual(1, len(opA.paulis), "{}".format(opA.print_operators()))
        opA.zeros_coeff_elimination()

        self.assertEqual(0, len(opA.paulis), "{}".format(opA.print_operators()))
Пример #17
0
    def _construct_qpe_evolution(self):
        """Implement the Quantum Phase Estimation algorithm"""

        a = QuantumRegister(self._num_ancillae, name='a')
        c = ClassicalRegister(self._num_ancillae, name='c')
        q = QuantumRegister(self._operator.num_qubits, name='q')
        qc = QuantumCircuit(a, q, c)

        # initialize state_in
        qc.data += self._state_in.construct_circuit('circuit', q).data

        # Put all ancillae in uniform superposition
        qc.u2(0, np.pi, a) if self._use_basis_gates else qc.h(a)

        # phase kickbacks via dynamics
        pauli_list = self._operator.reorder_paulis(
            grouping=self._paulis_grouping)
        if len(pauli_list) == 1:
            slice_pauli_list = pauli_list
        else:
            if self._expansion_mode == 'trotter':
                slice_pauli_list = pauli_list
            elif self._expansion_mode == 'suzuki':
                slice_pauli_list = Operator._suzuki_expansion_slice_pauli_list(
                    pauli_list, 1, self._expansion_order)
            else:
                raise ValueError('Unrecognized expansion mode {}.'.format(
                    self._expansion_mode))
        for i in range(self._num_ancillae):
            qc.data += self._operator.construct_evolution_circuit(
                slice_pauli_list,
                -2 * np.pi,
                self._num_time_slices,
                q,
                a,
                ctl_idx=i,
                use_basis_gates=self._use_basis_gates).data
            # global phase shift for the ancilla due to the identity pauli term
            qc.u1(2 * np.pi * self._ancilla_phase_coef * (2**i), a[i])

        # inverse qft on ancillae
        self._iqft.construct_circuit('circuit', a, qc)

        # measuring ancillae
        qc.measure(a, c)

        self._circuit = qc
Пример #18
0
    def test_create_from_matrix(self):
        """
            test with matrix initialization
        """
        for num_qubits in range(1, 6):
            m_size = np.power(2, num_qubits)
            matrix = np.random.rand(m_size, m_size)

            op = Operator(matrix=matrix)
            op.convert('matrix', 'paulis')
            op.convert('matrix', 'grouped_paulis')
            depth = 1
            var_form = get_variational_form_instance('RYRZ')
            var_form.init_args(op.num_qubits, depth)
            circuit = var_form.construct_circuit(np.array(np.random.randn(var_form.num_parameters)))

            execute_config = {'shots': 1, 'skip_transpiler': False}
            matrix_mode = op.eval('matrix', circuit, 'local_statevector_simulator', execute_config)[0]
            non_matrix_mode = op.eval('paulis', circuit, 'local_statevector_simulator', execute_config)[0]
Пример #19
0
def get_graphpartition_qubitops(weight_matrix):
    """Generate Hamiltonian for the graph partitioning

    Args:
        weight_matrix (numpy.ndarray) : adjacency matrix.

    Returns:
        operator.Operator, float: operator for the Hamiltonian and a
        constant shift for the obj function.

    Goals:
        1 separate the vertices into two set of the same size
        2 make sure the number of edges between the two set is minimized.
    Hamiltonian:
    H = H_A + H_B
    H_A = sum\_{(i,j)\in E}{(1-ZiZj)/2}
    H_B = (sum_{i}{Zi})^2 = sum_{i}{Zi^2}+sum_{i!=j}{ZiZj}
    H_A is for achieving goal 2 and H_B is for achieving goal 1.
    """
    num_nodes = len(weight_matrix)
    pauli_list = []
    shift = 0

    for i in range(num_nodes):
        for j in range(i):
            if (weight_matrix[i, j] != 0):
                wp = np.zeros(num_nodes)
                vp = np.zeros(num_nodes)
                vp[i] = 1
                vp[j] = 1
                pauli_list.append([-0.5, Pauli(vp, wp)])
                shift += 0.5

    for i in range(num_nodes):
        for j in range(num_nodes):
            if i != j:
                wp = np.zeros(num_nodes)
                vp = np.zeros(num_nodes)
                vp[i] = 1
                vp[j] = 1
                pauli_list.append([1, Pauli(vp, wp)])
            else:
                shift += 1
    return Operator(paulis=pauli_list), shift
Пример #20
0
    def _estimate_phase_iteratively(self):
        """Iteratively construct the different order of controlled evolution circuit to carry out phase estimation"""
        pauli_list = self._operator.reorder_paulis(
            grouping=self._paulis_grouping)
        if len(pauli_list) == 1:
            slice_pauli_list = pauli_list
        else:
            if self._expansion_mode == 'trotter':
                slice_pauli_list = pauli_list
            else:
                slice_pauli_list = Operator._suzuki_expansion_slice_pauli_list(
                    pauli_list, 1, self._expansion_order)

        self._ret['top_measurement_label'] = ''

        omega_coef = 0
        # k runs from the number of iterations back to 1
        for k in range(self._num_iterations, 0, -1):
            omega_coef /= 2
            qc = self._construct_kth_evolution(slice_pauli_list, k,
                                               -2 * np.pi * omega_coef)
            measurements = self.execute(qc).get_counts(qc)

            if '0' not in measurements:
                if '1' in measurements:
                    x = 1
                else:
                    raise RuntimeError(
                        'Unexpected measurement {}.'.format(measurements))
            else:
                if '1' not in measurements:
                    x = 0
                else:
                    x = 1 if measurements['1'] > measurements['0'] else 0
            self._ret['top_measurement_label'] = '{}{}'.format(
                x, self._ret['top_measurement_label'])
            omega_coef = omega_coef + x / 2
            logger.info(
                'Reverse iteration {} of {} with measured bit {}'.format(
                    k, self._num_iterations, x))
        return omega_coef
Пример #21
0
 def setUp(self):
     np.random.seed(50)
     pauli_dict = {
         'paulis': [{
             "coeff": {
                 "imag": 0.0,
                 "real": -1.052373245772859
             },
             "label": "II"
         }, {
             "coeff": {
                 "imag": 0.0,
                 "real": 0.39793742484318045
             },
             "label": "ZI"
         }, {
             "coeff": {
                 "imag": 0.0,
                 "real": -0.39793742484318045
             },
             "label": "IZ"
         }, {
             "coeff": {
                 "imag": 0.0,
                 "real": -0.01128010425623538
             },
             "label": "ZZ"
         }, {
             "coeff": {
                 "imag": 0.0,
                 "real": 0.18093119978423156
             },
             "label": "XX"
         }]
     }
     qubitOp = Operator.load_from_dict(pauli_dict)
     self.algo_input = get_input_instance('EnergyInput')
     self.algo_input.qubit_op = qubitOp
Пример #22
0
    def _one_body_mapping(h1_ij, a_i, a_j, threshold):
        """
        Subroutine for one body mapping.

        Args:
            h1_ij (complex): value of h1 at index (i,j)
            a_i (Pauli): pauli at index i
            a_j (Pauli): pauli at index j
            threshold: (float): threshold to remove a pauli

        Returns:
            Operator: Operator for those paulis
        """
        pauli_list = []
        for alpha in range(2):
            for beta in range(2):
                pauli_prod = sgn_prod(a_i[alpha], a_j[beta])
                coeff = h1_ij / 4 * pauli_prod[1] * np.power(
                    -1j, alpha) * np.power(1j, beta)
                pauli_term = [coeff, pauli_prod[0]]
                if np.absolute(pauli_term[0]) > threshold:
                    pauli_list.append(pauli_term)
        return Operator(paulis=pauli_list)
Пример #23
0
def get_maxcut_qubitops(weight_matrix):
    """Generate Hamiltonian for the maximum stableset in a graph.

    Args:
        weight_matrix (numpy.ndarray) : adjacency matrix.

    Returns:
        operator.Operator, float: operator for the Hamiltonian and a
        constant shift for the obj function.

    """
    num_nodes = weight_matrix.shape[0]
    pauli_list = []
    shift = 0
    for i in range(num_nodes):
        for j in range(i):
            if (weight_matrix[i,j] != 0):
                wp = np.zeros(num_nodes)
                vp = np.zeros(num_nodes)
                vp[i] = 1
                vp[j] = 1
                pauli_list.append([0.5 * weight_matrix[i, j], Pauli(vp, wp)])
                shift -= 0.5 * weight_matrix[i, j]
    return Operator(paulis=pauli_list), shift
Пример #24
0
# =============================================================================

import unittest
from parameterized import parameterized
from qiskit_acqua import get_algorithm_instance, get_initial_state_instance, get_iqft_instance, Operator
from qiskit_acqua.utils import decimal_to_binary
import numpy as np
from test.common import QISKitAcquaTestCase
from scipy.linalg import expm

X = np.array([[0, 1], [1, 0]])
Y = np.array([[0, -1j], [1j, 0]])
Z = np.array([[1, 0], [0, -1]])
I = np.array([[1, 0], [0, 1]])
h1 = X + Y + Z + I
qubitOp_simple = Operator(matrix=h1)

pauli_dict = {
    'paulis': [{
        "coeff": {
            "imag": 0.0,
            "real": -1.052373245772859
        },
        "label": "II"
    }, {
        "coeff": {
            "imag": 0.0,
            "real": 0.39793742484318045
        },
        "label": "ZI"
    }, {
Пример #25
0
        "label": "IZ"
    }, {
        "coeff": {
            "imag": 0.0,
            "real": -0.01128010425623538
        },
        "label": "ZZ"
    }, {
        "coeff": {
            "imag": 0.0,
            "real": 0.18093119978423156
        },
        "label": "XX"
    }]
}
qubitOp_h2_with_2_qubit_reduction = Operator.load_from_dict(pauli_dict)


class TestIQPE(QISKitAcquaTestCase):
    """QPE tests."""
    @parameterized.expand([
        [qubitOp_h2_with_2_qubit_reduction],
    ])
    def test_qpe(self, qubitOp):
        self.algorithm = 'QPE'
        self.log.debug('Testing QPE')

        self.qubitOp = qubitOp

        exact_eigensolver = get_algorithm_instance('ExactEigensolver')
        exact_eigensolver.init_args(self.qubitOp, k=1)
Пример #26
0
class TestOperator(QISKitAcquaTestCase):
    """Operator tests."""
    def setUp(self):
        np.random.seed(0)

        self.num_qubits = 4
        m_size = np.power(2, self.num_qubits)
        matrix = np.random.rand(m_size, m_size)
        self.qubitOp = Operator(matrix=matrix)

    def test_real_eval(self):
        depth = 1
        var_form = get_variational_form_instance('RYRZ')
        var_form.init_args(self.qubitOp.num_qubits, depth)
        circuit = var_form.construct_circuit(
            np.array(np.random.randn(var_form.num_parameters)))
        # self.qubitOp.coloring = None
        execute_config_ref = {'shots': 1, 'skip_transpiler': False}
        execute_config = {'shots': 10000, 'skip_transpiler': False}
        reference = self.qubitOp.eval('matrix', circuit,
                                      'local_statevector_simulator',
                                      execute_config_ref)[0]
        reference = reference.real

        paulis_mode = self.qubitOp.eval('paulis', circuit,
                                        'local_qasm_simulator', execute_config)
        grouped_paulis_mode = self.qubitOp.eval('grouped_paulis', circuit,
                                                'local_qasm_simulator',
                                                execute_config)

        paulis_mode_p_3sigma = paulis_mode[0] + 3 * paulis_mode[1]
        paulis_mode_m_3sigma = paulis_mode[0] - 3 * paulis_mode[1]

        grouped_paulis_mode_p_3sigma = grouped_paulis_mode[
            0] + 3 * grouped_paulis_mode[1]
        grouped_paulis_mode_m_3sigma = grouped_paulis_mode[
            0] - 3 * grouped_paulis_mode[1]
        self.assertLessEqual(reference, paulis_mode_p_3sigma.real)
        self.assertGreaterEqual(reference, paulis_mode_m_3sigma.real)
        self.assertLessEqual(reference, grouped_paulis_mode_p_3sigma.real)
        self.assertGreaterEqual(reference, grouped_paulis_mode_m_3sigma.real)

        execute_config = {'shots': 10000, 'skip_transpiler': True}
        paulis_mode = self.qubitOp.eval('paulis', circuit,
                                        'local_qasm_simulator', execute_config)
        grouped_paulis_mode = self.qubitOp.eval('grouped_paulis', circuit,
                                                'local_qasm_simulator',
                                                execute_config)

        paulis_mode_p_3sigma = paulis_mode[0] + 3 * paulis_mode[1]
        paulis_mode_m_3sigma = paulis_mode[0] - 3 * paulis_mode[1]

        grouped_paulis_mode_p_3sigma = grouped_paulis_mode[
            0] + 3 * grouped_paulis_mode[1]
        grouped_paulis_mode_m_3sigma = grouped_paulis_mode[
            0] - 3 * grouped_paulis_mode[1]
        self.assertLessEqual(reference, paulis_mode_p_3sigma.real,
                             "With skip_transpiler on")
        self.assertGreaterEqual(reference, paulis_mode_m_3sigma.real,
                                "With skip_transpiler on")
        self.assertLessEqual(reference, grouped_paulis_mode_p_3sigma.real,
                             "With skip_transpiler on")
        self.assertGreaterEqual(reference, grouped_paulis_mode_m_3sigma.real,
                                "With skip_transpiler on")

    def test_exact_eval(self):
        depth = 1
        var_form = get_variational_form_instance('RYRZ')
        var_form.init_args(self.qubitOp.num_qubits, depth)
        circuit = var_form.construct_circuit(
            np.array(np.random.randn(var_form.num_parameters)))

        execute_config = {'shots': 1, 'skip_transpiler': False}
        matrix_mode = self.qubitOp.eval('matrix', circuit,
                                        'local_statevector_simulator',
                                        execute_config)[0]
        non_matrix_mode = self.qubitOp.eval('paulis', circuit,
                                            'local_statevector_simulator',
                                            execute_config)[0]
        diff = abs(matrix_mode - non_matrix_mode)
        self.assertLess(
            diff, 0.01, "Values: ({} vs {})".format(matrix_mode,
                                                    non_matrix_mode))

        execute_config = {'shots': 1, 'skip_transpiler': True}
        non_matrix_mode = self.qubitOp.eval('paulis', circuit,
                                            'local_statevector_simulator',
                                            execute_config)[0]
        diff = abs(matrix_mode - non_matrix_mode)
        self.assertLess(
            diff, 0.01, "With skip_transpiler on, Values: ({} vs {})".format(
                matrix_mode, non_matrix_mode))

    def test_create_from_paulis_0(self):
        """
            test with single paulis
        """
        num_qubits = 4
        for pauli_label in itertools.product('IXYZ', repeat=num_qubits):
            coeff = np.random.random(1)[0]
            pauli_term = [coeff, label_to_pauli(pauli_label)]
            op = Operator(paulis=[pauli_term])

            op.convert('paulis', 'matrix')
            op.convert('paulis', 'grouped_paulis')

            depth = 1
            var_form = get_variational_form_instance('RYRZ')
            var_form.init_args(op.num_qubits, depth)
            circuit = var_form.construct_circuit(
                np.array(np.random.randn(var_form.num_parameters)))
            execute_config = {'shots': 1, 'skip_transpiler': False}
            matrix_mode = op.eval('matrix', circuit,
                                  'local_statevector_simulator',
                                  execute_config)[0]
            non_matrix_mode = op.eval('paulis', circuit,
                                      'local_statevector_simulator',
                                      execute_config)[0]

    def test_create_from_matrix(self):
        """
            test with matrix initialization
        """
        for num_qubits in range(1, 6):
            m_size = np.power(2, num_qubits)
            matrix = np.random.rand(m_size, m_size)

            op = Operator(matrix=matrix)
            op.convert('matrix', 'paulis')
            op.convert('matrix', 'grouped_paulis')
            depth = 1
            var_form = get_variational_form_instance('RYRZ')
            var_form.init_args(op.num_qubits, depth)
            circuit = var_form.construct_circuit(
                np.array(np.random.randn(var_form.num_parameters)))

            execute_config = {'shots': 1, 'skip_transpiler': False}
            matrix_mode = op.eval('matrix', circuit,
                                  'local_statevector_simulator',
                                  execute_config)[0]
            non_matrix_mode = op.eval('paulis', circuit,
                                      'local_statevector_simulator',
                                      execute_config)[0]

    def test_multiplication(self):
        """
            test multiplication
        """
        pauli_a = 'IXYZ'
        pauli_b = 'ZYIX'
        coeff_a = 0.5
        coeff_b = 0.5
        pauli_term_a = [coeff_a, label_to_pauli(pauli_a)]
        pauli_term_b = [coeff_b, label_to_pauli(pauli_b)]
        opA = Operator(paulis=[pauli_term_a])
        opB = Operator(paulis=[pauli_term_b])
        newOP = opA * opB
        # print(newOP.print_operators())

        self.assertEqual(1, len(newOP.paulis))
        self.assertEqual(-0.25, newOP.paulis[0][0])
        self.assertEqual('ZZYY', newOP.paulis[0][1].to_label())

    def test_addition(self):
        """
            test addition
        """
        pauli_a = 'IXYZ'
        pauli_b = 'ZYIX'
        coeff_a = 0.5
        coeff_b = 0.5
        pauli_term_a = [coeff_a, label_to_pauli(pauli_a)]
        pauli_term_b = [coeff_b, label_to_pauli(pauli_b)]
        opA = Operator(paulis=[pauli_term_a])
        opB = Operator(paulis=[pauli_term_b])
        newOP = opA + opB

        self.assertEqual(2, len(newOP.paulis))

        pauli_c = 'IXYZ'
        coeff_c = 0.25
        pauli_term_c = [coeff_c, label_to_pauli(pauli_c)]
        newOP += Operator(paulis=[pauli_term_c])

        self.assertEqual(2, len(newOP.paulis))
        self.assertEqual(0.75, newOP.paulis[0][0])

    def test_zero_coeff(self):
        """
            test addition
        """
        pauli_a = 'IXYZ'
        pauli_b = 'IXYZ'
        coeff_a = 0.5
        coeff_b = -0.5
        pauli_term_a = [coeff_a, label_to_pauli(pauli_a)]
        pauli_term_b = [coeff_b, label_to_pauli(pauli_b)]
        opA = Operator(paulis=[pauli_term_a])
        opB = Operator(paulis=[pauli_term_b])
        newOP = opA + opB

        self.assertEqual(0, len(newOP.paulis),
                         "{}".format(newOP.print_operators()))

        paulis = ['IXYZ', 'XXZY', 'IIZZ', 'XXYY', 'ZZXX', 'YYYY']
        coeffs = [0.2, 0.6, 0.8, -0.2, -0.6, -0.8]
        op = Operator(paulis=[])
        for coeff, pauli in zip(coeffs, paulis):
            pauli_term = [coeff, label_to_pauli(pauli)]
            op += Operator(paulis=[pauli_term])

        for i in range(6):
            opA = Operator(paulis=[[-coeffs[i], label_to_pauli(paulis[i])]])
            op += opA
            self.assertEqual(6 - (i + 1), len(op.paulis))

    def test_dia_matrix(self):
        """
            test conversion to dia_matrix
        """
        num_qubits = 4
        pauli_term = []
        for pauli_label in itertools.product('IZ', repeat=num_qubits):
            coeff = np.random.random(1)[0]
            pauli_term.append([coeff, label_to_pauli(pauli_label)])
        op = Operator(paulis=pauli_term)

        op.convert('paulis', 'matrix')
        op.convert('paulis', 'grouped_paulis')
        op._to_dia_matrix('paulis')

        self.assertEqual(op.matrix.ndim, 1)

        num_qubits = 4
        pauli_term = []
        for pauli_label in itertools.product('YZ', repeat=num_qubits):
            coeff = np.random.random(1)[0]
            pauli_term.append([coeff, label_to_pauli(pauli_label)])
        op = Operator(paulis=pauli_term)

        op.convert('paulis', 'matrix')
        op.convert('paulis', 'grouped_paulis')
        op._to_dia_matrix('paulis')

        self.assertEqual(op.matrix.ndim, 2)

    def test_equal_operator(self):

        paulis = ['IXYZ', 'XXZY', 'IIZZ', 'XXYY', 'ZZXX', 'YYYY']
        coeffs = [0.2, 0.6, 0.8, -0.2, -0.6, -0.8]
        op1 = Operator(paulis=[])
        for coeff, pauli in zip(coeffs, paulis):
            pauli_term = [coeff, label_to_pauli(pauli)]
            op1 += Operator(paulis=[pauli_term])

        paulis = ['IXYZ', 'XXZY', 'IIZZ', 'XXYY', 'ZZXX', 'YYYY']
        coeffs = [0.2, 0.6, 0.8, -0.2, -0.6, -0.8]
        op2 = Operator(paulis=[])
        for coeff, pauli in zip(coeffs, paulis):
            pauli_term = [coeff, label_to_pauli(pauli)]
            op2 += Operator(paulis=[pauli_term])

        paulis = ['IXYY', 'XXZY', 'IIZZ', 'XXYY', 'ZZXX', 'YYYY']
        coeffs = [0.2, 0.6, 0.8, -0.2, -0.6, -0.8]
        op3 = Operator(paulis=[])
        for coeff, pauli in zip(coeffs, paulis):
            pauli_term = [coeff, label_to_pauli(pauli)]
            op3 += Operator(paulis=[pauli_term])

        paulis = ['IXYZ', 'XXZY', 'IIZZ', 'XXYY', 'ZZXX', 'YYYY']
        coeffs = [-0.2, 0.6, 0.8, -0.2, -0.6, -0.8]
        op4 = Operator(paulis=[])
        for coeff, pauli in zip(coeffs, paulis):
            pauli_term = [coeff, label_to_pauli(pauli)]
            op4 += Operator(paulis=[pauli_term])

        self.assertEqual(op1, op2)
        self.assertNotEqual(op1, op3)
        self.assertNotEqual(op1, op4)
        self.assertNotEqual(op3, op4)

    def test_chop_real_only(self):

        paulis = ['IXYZ', 'XXZY', 'IIZZ', 'XXYY', 'ZZXX', 'YYYY']
        coeffs = [0.2, 0.6, 0.8, -0.2, -0.6, -0.8]
        op = Operator(paulis=[])
        for coeff, pauli in zip(coeffs, paulis):
            pauli_term = [coeff, label_to_pauli(pauli)]
            op += Operator(paulis=[pauli_term])

        op1 = copy.deepcopy(op)
        op1.chop(threshold=0.4)
        self.assertEqual(len(op1.paulis), 4,
                         "\n{}".format(op1.print_operators()))
        gt_op1 = Operator(paulis=[])
        for i in range(1, 3):
            pauli_term = [coeffs[i], label_to_pauli(paulis[i])]
            gt_op1 += Operator(paulis=[pauli_term])
            pauli_term = [coeffs[i + 3], label_to_pauli(paulis[i + 3])]
            gt_op1 += Operator(paulis=[pauli_term])
        self.assertEqual(op1, gt_op1)

        op2 = copy.deepcopy(op)
        op2.chop(threshold=0.7)
        self.assertEqual(len(op2.paulis), 2,
                         "\n{}".format(op2.print_operators()))
        gt_op2 = Operator(paulis=[])
        for i in range(2, 3):
            pauli_term = [coeffs[i], label_to_pauli(paulis[i])]
            gt_op2 += Operator(paulis=[pauli_term])
            pauli_term = [coeffs[i + 3], label_to_pauli(paulis[i + 3])]
            gt_op2 += Operator(paulis=[pauli_term])
        self.assertEqual(op2, gt_op2)

        op3 = copy.deepcopy(op)
        op3.chop(threshold=0.9)
        self.assertEqual(len(op3.paulis), 0,
                         "\n{}".format(op3.print_operators()))
        gt_op3 = Operator(paulis=[])
        for i in range(3, 3):
            pauli_term = [coeffs[i], label_to_pauli(paulis[i])]
            gt_op3 += Operator(paulis=[pauli_term])
            pauli_term = [coeffs[i + 3], label_to_pauli(paulis[i + 3])]
            gt_op3 += Operator(paulis=[pauli_term])
        self.assertEqual(op3, gt_op3)

    def test_chop_complex_only_1(self):

        paulis = ['IXYZ', 'XXZY', 'IIZZ', 'XXYY', 'ZZXX', 'YYYY']
        coeffs = [
            0.2 + -1j * 0.2, 0.6 + -1j * 0.6, 0.8 + -1j * 0.8,
            -0.2 + -1j * 0.2, -0.6 - -1j * 0.6, -0.8 - -1j * 0.8
        ]
        op = Operator(paulis=[])
        for coeff, pauli in zip(coeffs, paulis):
            pauli_term = [coeff, label_to_pauli(pauli)]
            op += Operator(paulis=[pauli_term])

        op1 = copy.deepcopy(op)
        op1.chop(threshold=0.4)
        self.assertEqual(len(op1.paulis), 4,
                         "\n{}".format(op1.print_operators()))
        gt_op1 = Operator(paulis=[])
        for i in range(1, 3):
            pauli_term = [coeffs[i], label_to_pauli(paulis[i])]
            gt_op1 += Operator(paulis=[pauli_term])
            pauli_term = [coeffs[i + 3], label_to_pauli(paulis[i + 3])]
            gt_op1 += Operator(paulis=[pauli_term])
        self.assertEqual(op1, gt_op1)

        op2 = copy.deepcopy(op)
        op2.chop(threshold=0.7)
        self.assertEqual(len(op2.paulis), 2,
                         "\n{}".format(op2.print_operators()))
        gt_op2 = Operator(paulis=[])
        for i in range(2, 3):
            pauli_term = [coeffs[i], label_to_pauli(paulis[i])]
            gt_op2 += Operator(paulis=[pauli_term])
            pauli_term = [coeffs[i + 3], label_to_pauli(paulis[i + 3])]
            gt_op2 += Operator(paulis=[pauli_term])
        self.assertEqual(op2, gt_op2)

        op3 = copy.deepcopy(op)
        op3.chop(threshold=0.9)
        self.assertEqual(len(op3.paulis), 0,
                         "\n{}".format(op3.print_operators()))
        gt_op3 = Operator(paulis=[])
        for i in range(3, 3):
            pauli_term = [coeffs[i], label_to_pauli(paulis[i])]
            gt_op3 += Operator(paulis=[pauli_term])
            pauli_term = [coeffs[i + 3], label_to_pauli(paulis[i + 3])]
            gt_op3 += Operator(paulis=[pauli_term])
        self.assertEqual(op3, gt_op3)

    def test_chop_complex_only_2(self):

        paulis = ['IXYZ', 'XXZY', 'IIZZ', 'XXYY', 'ZZXX', 'YYYY']
        coeffs = [
            0.2 + -1j * 0.8, 0.6 + -1j * 0.6, 0.8 + -1j * 0.2,
            -0.2 + -1j * 0.8, -0.6 - -1j * 0.6, -0.8 - -1j * 0.2
        ]
        op = Operator(paulis=[])
        for coeff, pauli in zip(coeffs, paulis):
            pauli_term = [coeff, label_to_pauli(pauli)]
            op += Operator(paulis=[pauli_term])

        op1 = copy.deepcopy(op)
        op1.chop(threshold=0.4)
        self.assertEqual(len(op1.paulis), 6,
                         "\n{}".format(op1.print_operators()))

        op2 = copy.deepcopy(op)
        op2.chop(threshold=0.7)
        self.assertEqual(len(op2.paulis), 4,
                         "\n{}".format(op2.print_operators()))

        op3 = copy.deepcopy(op)
        op3.chop(threshold=0.9)
        self.assertEqual(len(op3.paulis), 0,
                         "\n{}".format(op3.print_operators()))

    def test_representations(self):

        self.assertEqual(len(self.qubitOp.representations), 1)
        self.assertEqual(self.qubitOp.representations, ['matrix'])
        self.qubitOp.convert("matrix", "paulis")
        self.assertEqual(len(self.qubitOp.representations), 2)
        self.assertEqual(self.qubitOp.representations, ['paulis', 'matrix'])
        self.qubitOp.convert("matrix", "grouped_paulis")
        self.assertEqual(len(self.qubitOp.representations), 3)
        self.assertEqual(self.qubitOp.representations,
                         ['paulis', 'grouped_paulis', 'matrix'])

    def test_num_qubits(self):

        op = Operator(paulis=[])
        self.assertEqual(op.num_qubits, 0)
        self.assertEqual(self.qubitOp.num_qubits, self.num_qubits)

    def test_is_empty(self):
        op = Operator(paulis=[])
        self.assertTrue(op.is_empty())
        self.assertFalse(self.qubitOp.is_empty())
Пример #27
0
    def mapping(self, map_type, threshold=0.00000001, num_workers=4):
        """
        Using multiprocess to speedup the mapping, the improvement can be
        observed when h2 is a non-sparse matrix.

        Args:
            map_type (str): case-insensitive mapping type. "jordan_wigner", "parity", "bravyi_kitaev"
            threshold (float): threshold for Pauli simplification
            num_workers (int): number of processes used to map.

        Returns:
            Operator: create an Operator object in Paulis form.

        Raises:
            ACQUAChemistryError: if the `map_type` can not be recognized.
        """
        """
        ####################################################################
        ############   DEFINING MAPPED FERMIONIC OPERATORS    ##############
        ####################################################################
        """
        n = self._h1.shape[0]  # number of fermionic modes / qubits
        map_type = map_type.lower()
        if map_type == 'jordan_wigner':
            a = self._jordan_wigner_mode(n)
        elif map_type == 'parity':
            a = self._parity_mode(n)
        elif map_type == 'bravyi_kitaev':
            a = self._bravyi_kitaev_mode(n)
        else:
            raise ACQUAChemistryError(
                'Please specify the supported modes: jordan_wigner, parity, bravyi_kitaev'
            )
        """
        ####################################################################
        ############    BUILDING THE MAPPED HAMILTONIAN     ################
        ####################################################################
        """
        max_workers = min(num_workers, multiprocessing.cpu_count())
        pauli_list = Operator(paulis=[])
        with concurrent.futures.ProcessPoolExecutor(
                max_workers=max_workers) as executor:
            #######################    One-body    #############################
            futures = [
                executor.submit(FermionicOperator._one_body_mapping,
                                self._h1[i, j], a[i], a[j], threshold)
                for i, j in itertools.product(range(n), repeat=2)
                if self._h1[i, j] != 0
            ]
            for future in concurrent.futures.as_completed(futures):
                result = future.result()
                pauli_list += result
            pauli_list.chop(threshold=threshold)

            #######################    Two-body    #############################
            futures = [
                executor.submit(FermionicOperator._two_body_mapping,
                                self._h2[i, j, k,
                                         m], a[i], a[j], a[k], a[m], threshold)
                for i, j, k, m in itertools.product(range(n), repeat=4)
                if self._h2[i, j, k, m] != 0
            ]
            for future in concurrent.futures.as_completed(futures):
                result = future.result()
                pauli_list += result
            pauli_list.chop(threshold=threshold)

        if self._ph_trans_shift is not None:
            pauli_list += Operator(paulis=[[
                self._ph_trans_shift,
                label_to_pauli('I' * self._h1.shape[0])
            ]])

        return pauli_list
Пример #28
0
    def test_chop_complex_only_1(self):

        paulis = ['IXYZ', 'XXZY', 'IIZZ', 'XXYY', 'ZZXX', 'YYYY']
        coeffs = [
            0.2 + -1j * 0.2, 0.6 + -1j * 0.6, 0.8 + -1j * 0.8,
            -0.2 + -1j * 0.2, -0.6 - -1j * 0.6, -0.8 - -1j * 0.8
        ]
        op = Operator(paulis=[])
        for coeff, pauli in zip(coeffs, paulis):
            pauli_term = [coeff, label_to_pauli(pauli)]
            op += Operator(paulis=[pauli_term])

        op1 = copy.deepcopy(op)
        op1.chop(threshold=0.4)
        self.assertEqual(len(op1.paulis), 4,
                         "\n{}".format(op1.print_operators()))
        gt_op1 = Operator(paulis=[])
        for i in range(1, 3):
            pauli_term = [coeffs[i], label_to_pauli(paulis[i])]
            gt_op1 += Operator(paulis=[pauli_term])
            pauli_term = [coeffs[i + 3], label_to_pauli(paulis[i + 3])]
            gt_op1 += Operator(paulis=[pauli_term])
        self.assertEqual(op1, gt_op1)

        op2 = copy.deepcopy(op)
        op2.chop(threshold=0.7)
        self.assertEqual(len(op2.paulis), 2,
                         "\n{}".format(op2.print_operators()))
        gt_op2 = Operator(paulis=[])
        for i in range(2, 3):
            pauli_term = [coeffs[i], label_to_pauli(paulis[i])]
            gt_op2 += Operator(paulis=[pauli_term])
            pauli_term = [coeffs[i + 3], label_to_pauli(paulis[i + 3])]
            gt_op2 += Operator(paulis=[pauli_term])
        self.assertEqual(op2, gt_op2)

        op3 = copy.deepcopy(op)
        op3.chop(threshold=0.9)
        self.assertEqual(len(op3.paulis), 0,
                         "\n{}".format(op3.print_operators()))
        gt_op3 = Operator(paulis=[])
        for i in range(3, 3):
            pauli_term = [coeffs[i], label_to_pauli(paulis[i])]
            gt_op3 += Operator(paulis=[pauli_term])
            pauli_term = [coeffs[i + 3], label_to_pauli(paulis[i + 3])]
            gt_op3 += Operator(paulis=[pauli_term])
        self.assertEqual(op3, gt_op3)
Пример #29
0
    def test_num_qubits(self):

        op = Operator(paulis=[])
        self.assertEqual(op.num_qubits, 0)
        self.assertEqual(self.qubitOp.num_qubits, self.num_qubits)
Пример #30
0
 def test_is_empty(self):
     op = Operator(paulis=[])
     self.assertTrue(op.is_empty())
     self.assertFalse(self.qubitOp.is_empty())