예제 #1
0
    def test_basic_pulse(self):
        """
        Test for basic pulse generation and attributes.
        """
        coeff = np.array([0.1, 0.2, 0.3, 0.4])
        tlist = np.array([0., 1., 2., 3.])
        ham = sigmaz()

        # Basic tests
        pulse1 = Pulse(ham, 1, tlist, coeff)
        assert_allclose(
            pulse1.get_ideal_qobjevo(2)(0).full(),
            tensor(identity(2), sigmaz()).full() * coeff[0])
        pulse1.tlist = 2 * tlist
        assert_allclose(pulse1.tlist, 2 * tlist)
        pulse1.tlist = tlist
        pulse1.coeff = 2 * coeff
        assert_allclose(pulse1.coeff, 2 * coeff)
        pulse1.coeff = coeff
        pulse1.qobj = 2 * sigmay()
        assert_allclose(pulse1.qobj.full(), 2 * sigmay().full())
        pulse1.qobj = ham
        pulse1.targets = 3
        assert_allclose(pulse1.targets, 3)
        pulse1.targets = 1
        qobjevo = pulse1.get_ideal_qobjevo(2)
        if parse_version(qutip.__version__) >= parse_version('5.dev'):
            expected = QobjEvo([tensor(identity(2), sigmaz()), coeff],
                               tlist=tlist,
                               order=0)
        else:
            expected = QobjEvo([tensor(identity(2), sigmaz()), coeff],
                               tlist=tlist,
                               args={"_step_func_coeff": True})
        _compare_qobjevo(qobjevo, expected, 0, 3)
예제 #2
0
 def __init__(self):
     N = 3
     self.t1 = QobjEvo([qeye(N)*(1.+0.1j),[create(N)*(1.-0.1j),f]])
     self.t2 = QobjEvo([destroy(N)*(1.-0.2j)])
     self.t3 = QobjEvo([[destroy(N)*create(N)*(1.+0.2j),f]])
     self.q1 = qeye(N)*(1.+0.3j)
     self.q2 = destroy(N)*(1.-0.3j)
     self.q3 = destroy(N)*create(N)*(1.+0.4j)
예제 #3
0
def test_general_stochastic():
    "Stochastic: general_stochastic"
    "Reproduce smesolve homodyne"
    tol = 0.025
    N = 4
    gamma = 0.25
    ntraj = 20
    nsubsteps = 50
    a = destroy(N)

    H = [[a.dag() * a, f]]
    psi0 = coherent(N, 0.5)
    sc_ops = [np.sqrt(gamma) * a, np.sqrt(gamma) * a * 0.5]
    e_ops = [a.dag() * a, a + a.dag(), (-1j) * (a - a.dag())]

    L = liouvillian(QobjEvo([[a.dag() * a, f]], args={"a": 2}), c_ops=sc_ops)
    L.compile()
    sc_opsM = [QobjEvo(spre(op) + spost(op.dag())) for op in sc_ops]
    [op.compile() for op in sc_opsM]
    e_opsM = [spre(op) for op in e_ops]

    def d1(t, vec):
        return L.mul_vec(t, vec)

    def d2(t, vec):
        out = []
        for op in sc_opsM:
            out.append(op.mul_vec(t, vec) - op.expect(t, vec) * vec)
        return np.stack(out)

    times = np.linspace(0, 0.5, 13)
    res_ref = mesolve(H, psi0, times, sc_ops, e_ops, args={"a": 2})
    list_methods_tol = ['euler-maruyama', 'platen', 'explicit15']
    for solver in list_methods_tol:
        res = general_stochastic(ket2dm(psi0),
                                 times,
                                 d1,
                                 d2,
                                 len_d2=2,
                                 e_ops=e_opsM,
                                 normalize=False,
                                 ntraj=ntraj,
                                 nsubsteps=nsubsteps,
                                 solver=solver)
    assert_(
        all([
            np.mean(abs(res.expect[idx] - res_ref.expect[idx])) < tol
            for idx in range(len(e_ops))
        ]))
    assert_(len(res.measurement) == ntraj)
예제 #4
0
    def test_pulse_constructor(self):
        """
        Test for creating empty Pulse, Pulse with constant coefficients etc.
        """
        coeff = np.array([0.1, 0.2, 0.3, 0.4])
        tlist = np.array([0., 1., 2., 3.])
        ham = sigmaz()
        # Special ways of initializing pulse
        pulse2 = Pulse(sigmax(), 0, tlist, True)
        assert_allclose(
            pulse2.get_ideal_qobjevo(2)(0).full(),
            tensor(sigmax(), identity(2)).full())

        pulse3 = Pulse(sigmay(), 0)
        assert_allclose(pulse3.get_ideal_qobjevo(2)(0).norm(), 0.)

        pulse4 = Pulse(None, None)  # Dummy empty ham
        assert_allclose(pulse4.get_ideal_qobjevo(2)(0).norm(), 0.)

        tlist_noise = np.array([1., 2.5, 3.])
        coeff_noise = np.array([0.5, 0.1, 0.5])
        tlist_noise2 = np.array([0.5, 2, 3.])
        coeff_noise2 = np.array([0.1, 0.2, 0.3])
        # Pulse with different dims
        random_qobj = Qobj(np.random.random((3, 3)))
        pulse5 = Pulse(sigmaz(), 1, tlist, True)
        pulse5.add_coherent_noise(sigmay(), 1, tlist_noise, coeff_noise)
        pulse5.add_lindblad_noise(random_qobj,
                                  0,
                                  tlist=tlist_noise2,
                                  coeff=coeff_noise2)
        qu, c_ops = pulse5.get_noisy_qobjevo(dims=[3, 2])
        if parse_version(qutip.__version__) >= parse_version('5.dev'):
            expected = QobjEvo([
                tensor([identity(3), sigmaz()]),
                [tensor([identity(3), sigmay()]), coeff_noise]
            ],
                               tlist=tlist_noise,
                               order=0)
        else:
            expected = QobjEvo([
                tensor([identity(3), sigmaz()]),
                [tensor([identity(3), sigmay()]), coeff_noise]
            ],
                               tlist=tlist_noise,
                               args={"_step_func_coeff": True})
        _compare_qobjevo(qu, expected, 0, 3)
예제 #5
0
def _merge_qobjevo(qobjevo_list, full_tlist=None):
    """
    Combine a list of `:class:qutip.QobjEvo` into one,
    different tlist will be merged.
    """
    # no qobjevo
    if not qobjevo_list:
        raise ValueError("qobjevo_list is empty.")

    # In qutip5 this can be done automatically.
    if parse_version(qutip.__version__) >= parse_version("5.dev"):
        return sum(
            [op for op in qobjevo_list if isinstance(op, (Qobj, QobjEvo))])

    if full_tlist is None:
        full_tlist = _find_common_tlist(qobjevo_list)
    spline_types_num = set()
    args = {}
    for qu in qobjevo_list:
        if isinstance(qu, QobjEvo):
            try:
                spline_types_num.add(qu.args["_step_func_coeff"])
            except Exception:
                pass
            args.update(qu.args)
    if len(spline_types_num) > 1:
        raise ValueError("Cannot merge Qobjevo with different spline kinds.")

    for i, qobjevo in enumerate(qobjevo_list):
        if isinstance(qobjevo, Qobj):
            qobjevo_list[i] = QobjEvo(qobjevo)
            qobjevo = qobjevo_list[i]
        for j, ele in enumerate(qobjevo.ops):
            if isinstance(ele.coeff, np.ndarray):
                new_coeff = _fill_coeff(ele.coeff, qobjevo.tlist, full_tlist,
                                        args)
                qobjevo_list[i].ops[j].coeff = new_coeff
        qobjevo_list[i].tlist = full_tlist

    qobjevo = sum(qobjevo_list)
    return qobjevo
예제 #6
0
    def test_random_noise(self):
        """
        Test for the white noise
        """
        tlist = np.array([1, 2, 3, 4, 5, 6])
        coeff = np.array([1, 1, 1, 1, 1, 1])
        dummy_qobjevo = QobjEvo(sigmaz(), tlist=tlist)
        mean = 0.
        std = 0.5
        pulses = [
            Pulse(sigmaz(), 0, tlist, coeff),
            Pulse(sigmax(), 0, tlist, coeff * 2),
            Pulse(sigmay(), 0, tlist, coeff * 3)
        ]

        # random noise with operators from proc_qobjevo
        gaussnoise = RandomNoise(dt=0.1,
                                 rand_gen=np.random.normal,
                                 loc=mean,
                                 scale=std)
        noisy_pulses, systematic_noise = \
            gaussnoise.get_noisy_pulses(pulses=pulses)
        assert_allclose(noisy_pulses[2].qobj.full(), sigmay().full())
        assert_allclose(noisy_pulses[1].coherent_noise[0].qobj.full(),
                        sigmax().full())
        assert_allclose(len(noisy_pulses[0].coherent_noise[0].tlist),
                        len(noisy_pulses[0].coherent_noise[0].coeff))

        # random noise with dt and other random number generator
        pulses = [
            Pulse(sigmaz(), 0, tlist, coeff),
            Pulse(sigmax(), 0, tlist, coeff * 2),
            Pulse(sigmay(), 0, tlist, coeff * 3)
        ]
        gaussnoise = RandomNoise(lam=0.1, dt=0.2, rand_gen=np.random.poisson)
        assert_(gaussnoise.rand_gen is np.random.poisson)
        noisy_pulses, systematic_noise = \
            gaussnoise.get_noisy_pulses(pulses=pulses)
        assert_allclose(noisy_pulses[0].coherent_noise[0].tlist,
                        np.linspace(1, 6,
                                    int(5 / 0.2) + 1))
        assert_allclose(noisy_pulses[1].coherent_noise[0].tlist,
                        np.linspace(1, 6,
                                    int(5 / 0.2) + 1))
        assert_allclose(noisy_pulses[2].coherent_noise[0].tlist,
                        np.linspace(1, 6,
                                    int(5 / 0.2) + 1))
예제 #7
0
    def get_ideal_qobjevo(self, dims):
        """
        Get the QobjEvo representation of the drift Hamiltonian.

        Parameters
        ----------
        dims: int or list
            Dimension of the system.
            If int, we assume it is the number of qubits in the system.
            If list, it is the dimension of the component systems.

        Returns
        -------
        ideal_evo: :class:`qutip.QobjEvo`
            A `QobjEvo` representing the drift evolution.
        """
        if not self.drift_hamiltonians:
            self.drift_hamiltonians = [_EvoElement(None, None)]
        qu_list = [
            QobjEvo(evo.get_qobj(dims)) for evo in self.drift_hamiltonians
        ]
        return _merge_qobjevo(qu_list)
예제 #8
0
 def _get_qobjevo_helper(self, spline_kind, dims):
     """
     Please refer to `_Evoelement.get_qobjevo` for documentation.
     """
     mat = self.get_qobj(dims)
     if self.tlist is None and self.coeff is None:
         qu = QobjEvo(mat) * 0.0
     elif isinstance(self.coeff, bool):
         if self.coeff:
             if self.tlist is None:
                 qu = QobjEvo(mat, tlist=self.tlist)
             else:
                 qu = QobjEvo([mat, np.ones(len(self.tlist))],
                              tlist=self.tlist)
         else:
             qu = QobjEvo(mat * 0.0, tlist=self.tlist)
     else:
         if spline_kind == "cubic":
             qu = QobjEvo(
                 [mat, self.coeff],
                 tlist=self.tlist,
             )
         elif spline_kind == "step_func":
             if len(self.coeff) == len(self.tlist) - 1:
                 self.coeff = np.concatenate([self.coeff, [0.0]])
             if parse_version(qutip.__version__) >= parse_version("5.dev"):
                 qu = QobjEvo([mat, self.coeff], tlist=self.tlist, order=0)
             else:
                 qu = QobjEvo(
                     [mat, self.coeff],
                     tlist=self.tlist,
                     args={"_step_func_coeff": True},
                 )
         else:
             # The spline will follow other pulses or
             # use the default value of QobjEvo
             raise ValueError("The pulse has an unknown spline type.")
     return qu
예제 #9
0
    def test_noisy_pulse(self):
        """
        Test for lindblad noise and different tlist
        """
        coeff = np.array([0.1, 0.2, 0.3, 0.4])
        tlist = np.array([0., 1., 2., 3.])
        ham = sigmaz()
        pulse1 = Pulse(ham, 1, tlist, coeff)
        # Add coherent noise and lindblad noise with different tlist
        pulse1.spline_kind = "step_func"
        tlist_noise = np.array([0., 1., 2.5, 3.])
        coeff_noise = np.array([0., 0.5, 0.1, 0.5])
        pulse1.add_coherent_noise(sigmay(), 0, tlist_noise, coeff_noise)
        tlist_noise2 = np.array([0., 0.5, 2, 3.])
        coeff_noise2 = np.array([0., 0.1, 0.2, 0.3])
        pulse1.add_lindblad_noise(sigmax(), 1, coeff=True)
        pulse1.add_lindblad_noise(sigmax(),
                                  0,
                                  tlist=tlist_noise2,
                                  coeff=coeff_noise2)

        assert_allclose(
            pulse1.get_ideal_qobjevo(2)(0).full(),
            tensor(identity(2), sigmaz()).full() * 0.1)
        noise_qu, c_ops = pulse1.get_noisy_qobjevo(2)
        assert_allclose(pulse1.get_full_tlist(),
                        np.array([0., 0.5, 1., 2., 2.5, 3.]))
        if parse_version(qutip.__version__) >= parse_version('5.dev'):
            expected = QobjEvo([[
                tensor(identity(2), sigmaz()),
                np.array([0.1, 0.1, 0.2, 0.3, 0.3, 0.4])
            ],
                                [
                                    tensor(sigmay(), identity(2)),
                                    np.array([0., 0., 0.5, 0.5, 0.1, 0.5])
                                ]],
                               tlist=np.array([0., 0.5, 1., 2., 2.5, 3.]),
                               order=0)
        else:
            expected = QobjEvo([[
                tensor(identity(2), sigmaz()),
                np.array([0.1, 0.1, 0.2, 0.3, 0.3, 0.4])
            ],
                                [
                                    tensor(sigmay(), identity(2)),
                                    np.array([0., 0., 0.5, 0.5, 0.1, 0.5])
                                ]],
                               tlist=np.array([0., 0.5, 1., 2., 2.5, 3.]),
                               args={"_step_func_coeff": True})
        _compare_qobjevo(noise_qu, expected, 0, 3)

        for c_op in c_ops:
            try:
                isconstant = c_op.isconstant
            except AttributeError:
                isconstant = (len(c_op.ops) == 0)
            if isconstant:
                assert_allclose(
                    c_op(0).full(),
                    tensor(identity(2), sigmax()).full())
            else:
                if parse_version(qutip.__version__) >= parse_version('5.dev'):
                    expected = QobjEvo([
                        tensor(sigmax(), identity(2)),
                        np.array([0., 0.1, 0.1, 0.2, 0.2, 0.3])
                    ],
                                       tlist=np.array(
                                           [0., 0.5, 1., 2., 2.5, 3.]),
                                       order=0)
                else:
                    expected = QobjEvo([
                        tensor(sigmax(), identity(2)),
                        np.array([0., 0.1, 0.1, 0.2, 0.2, 0.3])
                    ],
                                       tlist=np.array(
                                           [0., 0.5, 1., 2., 2.5, 3.]),
                                       args={"_step_func_coeff": True})
                _compare_qobjevo(c_op, expected, 0, 3)
예제 #10
0
        etamL, gammL = C(-1.0, mu_l)

        etapR, gampR = C(1.0, mu_r)
        etamR, gammR = C(-1.0, mu_r)

        ck_plus = etapR + etapL
        vk_plus = gampR + gampL
        ck_minus = etamR + etamL
        vk_minus = gammR + gammL

        return ck_plus, vk_plus, ck_minus, vk_minus


_HAMILTONIAN_EVO_KINDS = {
    "qobj": lambda H: H,
    "qobjevo": lambda H: QobjEvo([H]),
    "listevo": lambda H: [H],
}


def hamiltonian_to_sys(H, evo, liouvillianize):
    if liouvillianize:
        H = liouvillian(H)
    H = _HAMILTONIAN_EVO_KINDS[evo](H)
    return H


class TestHEOMSolver:
    def test_create_bosonic(self):
        Q = sigmaz()
        H = sigmax()