Source code for qiskit.aqua.operators.evolutions.trotterizations.qdrift

# -*- coding: utf-8 -*-

# This code is part of Qiskit.
#
# (C) Copyright IBM 2020.
#
# This code is licensed under the Apache License, Version 2.0. You may
# obtain a copy of this license in the LICENSE.txt file in the root directory
# of this source tree or at http://www.apache.org/licenses/LICENSE-2.0.
#
# Any modifications or derivative works of this code must retain this
# copyright notice, and modified files need to carry a notice indicating
# that they have been altered from the originals.

"""
QDrift Class

"""

import numpy as np

from .trotterization_base import TrotterizationBase
from ...operator_base import OperatorBase
from ...list_ops.summed_op import SummedOp
from ...list_ops.composed_op import ComposedOp


# pylint: disable=invalid-name

[docs]class QDrift(TrotterizationBase): """ The QDrift Trotterization method, which selects each each term in the Trotterization randomly, with a probability proportional to its weight. Based on the work of Earl Campbell in https://arxiv.org/abs/1811.08017. """ def __init__(self, reps: int = 1) -> None: r""" Args: reps: The number of times to repeat the Trotterization circuit. """ super().__init__(reps=reps)
[docs] def convert(self, operator: OperatorBase) -> OperatorBase: if not isinstance(operator, SummedOp): raise TypeError('Trotterization converters can only convert SummedOps.') # We artificially make the weights positive, TODO check approximation performance weights = np.abs([op.coeff for op in operator.oplist]) lambd = sum(weights) N = 2 * (lambd ** 2) * (operator.coeff ** 2) factor = lambd * operator.coeff / (N * self.reps) # The protocol calls for the removal of the individual coefficients, # and multiplication by a constant factor. scaled_ops = [(op * (factor / op.coeff)).exp_i() for op in operator.oplist] sampled_ops = np.random.choice(scaled_ops, size=(int(N * self.reps),), p=weights / lambd) return ComposedOp(sampled_ops).reduce()