Esempio n. 1
0
def test_eval_trace():
    up = JzKet(S(1)/2,S(1)/2)
    down = JzKet(S(1)/2,-S(1)/2)
    d = Density((up,0.5),(down,0.5))

    t = Tr(d)
    assert t.doit() == 1
Esempio n. 2
0
    def _eval_trace(self, **kwargs):
        indices = kwargs.get('indices', None)
        exp = tensor_product_simp(self)

        if indices is None or len(indices) == 0:
            return Mul(*[Tr(arg).doit() for arg in exp.args])
        else:
            return Mul(*[Tr(value).doit() if idx in indices else value
                         for idx, value in enumerate(exp.args)])
Esempio n. 3
0
def fidelity(state1, state2):
    """ Computes the fidelity [1]_ between two quantum states

    The arguments provided to this function should be a square matrix or a
    Density object. If it is a square matrix, it is assumed to be diagonalizable.

    Parameters
    ==========

    state1, state2 : a density matrix or Matrix


    Examples
    ========

    >>> from sympy import S, sqrt
    >>> from sympy.physics.quantum.dagger import Dagger
    >>> from sympy.physics.quantum.spin import JzKet
    >>> from sympy.physics.quantum.density import Density, fidelity
    >>> from sympy.physics.quantum.represent import represent
    >>>
    >>> up = JzKet(S(1)/2,S(1)/2)
    >>> down = JzKet(S(1)/2,-S(1)/2)
    >>> amp = 1/sqrt(2)
    >>> updown = (amp * up) + (amp * down)
    >>>
    >>> # represent turns Kets into matrices
    >>> up_dm = represent(up * Dagger(up))
    >>> down_dm = represent(down * Dagger(down))
    >>> updown_dm = represent(updown * Dagger(updown))
    >>>
    >>> fidelity(up_dm, up_dm)
    1
    >>> fidelity(up_dm, down_dm) #orthogonal states
    0
    >>> fidelity(up_dm, updown_dm).evalf().round(3)
    0.707

    References
    ==========

    .. [1] https://en.wikipedia.org/wiki/Fidelity_of_quantum_states

    """
    state1 = represent(state1) if isinstance(state1, Density) else state1
    state2 = represent(state2) if isinstance(state2, Density) else state2

    if (not isinstance(state1, Matrix) or
            not isinstance(state2, Matrix)):
        raise ValueError("state1 and state2 must be of type Density or Matrix "
                         "received type=%s for state1 and type=%s for state2" %
                         (type(state1), type(state2)))

    if ( state1.shape != state2.shape and state1.is_square):
        raise ValueError("The dimensions of both args should be equal and the "
                         "matrix obtained should be a square matrix")

    sqrt_state1 = state1**S.Half
    return Tr((sqrt_state1 * state2 * sqrt_state1)**S.Half).doit()
Esempio n. 4
0
def test_outer_product():
    k = Ket('k')
    b = Bra('b')
    op = OuterProduct(k, b)

    assert isinstance(op, OuterProduct)
    assert isinstance(op, Operator)

    assert op.ket == k
    assert op.bra == b
    assert op.label == (k, b)
    assert op.is_commutative is False

    op = k*b

    assert isinstance(op, OuterProduct)
    assert isinstance(op, Operator)

    assert op.ket == k
    assert op.bra == b
    assert op.label == (k, b)
    assert op.is_commutative is False

    op = 2*k*b

    assert op == Mul(Integer(2), k, b)

    op = 2*(k*b)

    assert op == Mul(Integer(2), OuterProduct(k, b))

    assert Dagger(k*b) == OuterProduct(Dagger(b), Dagger(k))
    assert Dagger(k*b).is_commutative is False

    #test the _eval_trace
    assert Tr(OuterProduct(JzKet(1, 1), JzBra(1, 1))).doit() == 1

    # test scaled kets and bras
    assert OuterProduct(2 * k, b) == 2 * OuterProduct(k, b)
    assert OuterProduct(k, 2 * b) == 2 * OuterProduct(k, b)

    # test sums of kets and bras
    k1, k2 = Ket('k1'), Ket('k2')
    b1, b2 = Bra('b1'), Bra('b2')
    assert (OuterProduct(k1 + k2, b1) ==
            OuterProduct(k1, b1) + OuterProduct(k2, b1))
    assert (OuterProduct(k1, b1 + b2) ==
            OuterProduct(k1, b1) + OuterProduct(k1, b2))
    assert (OuterProduct(1 * k1 + 2 * k2, 3 * b1 + 4 * b2) ==
            3 * OuterProduct(k1, b1) +
            4 * OuterProduct(k1, b2) +
            6 * OuterProduct(k2, b1) +
            8 * OuterProduct(k2, b2))
Esempio n. 5
0
def test_eval_trace():
    up = JzKet(S(1)/2, S(1)/2)
    down = JzKet(S(1)/2, -S(1)/2)
    d = Density((up, 0.5), (down, 0.5))

    t = Tr(d)
    assert t.doit() == 1

    #test dummy time dependent states
    class TestTimeDepKet(TimeDepKet):
        def _eval_trace(self, bra, **options):
            return 1

    x, t = symbols('x t')
    k1 = TestTimeDepKet(0, 0.5)
    k2 = TestTimeDepKet(0, 1)
    d = Density([k1, 0.5], [k2, 0.5])
    assert d.doit() == (0.5 * OuterProduct(k1, k1.dual) +
                        0.5 * OuterProduct(k2, k2.dual))

    t = Tr(d)
    assert t.doit() == 1
def test_eval_trace():
    # This test includes tests with dependencies between TensorProducts
    #and density operators. Since, the test is more to test the behavior of
    #TensorProducts it remains here

    A, B, C, D, E, F = symbols('A B C D E F', commutative=False)

    # Density with simple tensor products as args
    t = TensorProduct(A, B)
    d = Density([t, 1.0])
    tr = Tr(d)
    assert tr.doit() == 1.0*Tr(A*Dagger(A))*Tr(B*Dagger(B))

    ## partial trace with simple tensor products as args
    t = TensorProduct(A, B, C)
    d = Density([t, 1.0])
    tr = Tr(d, [1])
    assert tr.doit() == 1.0*A*Dagger(A)*Tr(B*Dagger(B))*C*Dagger(C)

    tr = Tr(d, [0, 2])
    assert tr.doit() == 1.0*Tr(A*Dagger(A))*B*Dagger(B)*Tr(C*Dagger(C))

    # Density with multiple Tensorproducts as states
    t2 = TensorProduct(A, B)
    t3 = TensorProduct(C, D)

    d = Density([t2, 0.5], [t3, 0.5])
    t = Tr(d)
    assert t.doit() == (0.5*Tr(A*Dagger(A))*Tr(B*Dagger(B)) +
                        0.5*Tr(C*Dagger(C))*Tr(D*Dagger(D)))

    t = Tr(d, [0])
    assert t.doit() == (0.5*Tr(A*Dagger(A))*B*Dagger(B) +
                        0.5*Tr(C*Dagger(C))*D*Dagger(D))

    #Density with mixed states
    d = Density([t2 + t3, 1.0])
    t = Tr(d)
    assert t.doit() == ( 1.0*Tr(A*Dagger(A))*Tr(B*Dagger(B)) +
                        1.0*Tr(A*Dagger(C))*Tr(B*Dagger(D)) +
                        1.0*Tr(C*Dagger(A))*Tr(D*Dagger(B)) +
                        1.0*Tr(C*Dagger(C))*Tr(D*Dagger(D)))

    t = Tr(d, [1] )
    assert t.doit() == ( 1.0*A*Dagger(A)*Tr(B*Dagger(B)) +
                        1.0*A*Dagger(C)*Tr(B*Dagger(D)) +
                        1.0*C*Dagger(A)*Tr(D*Dagger(B)) +
                        1.0*C*Dagger(C)*Tr(D*Dagger(D)))
Esempio n. 7
0
def test_outer_product():
    k = Ket('k')
    b = Bra('b')
    op = OuterProduct(k, b)

    assert isinstance(op, OuterProduct)
    assert isinstance(op, Operator)

    assert op.ket == k
    assert op.bra == b
    assert op.label == (k, b)
    assert op.is_commutative is False

    op = k * b

    assert isinstance(op, OuterProduct)
    assert isinstance(op, Operator)

    assert op.ket == k
    assert op.bra == b
    assert op.label == (k, b)
    assert op.is_commutative is False

    op = 2 * k * b

    assert op == Mul(Integer(2), k, b)

    op = 2 * (k * b)

    assert op == Mul(Integer(2), OuterProduct(k, b))

    assert Dagger(k * b) == OuterProduct(Dagger(b), Dagger(k))
    assert Dagger(k * b).is_commutative is False

    #test the _eval_trace
    assert Tr(OuterProduct(JzKet(1, 1), JzBra(1, 1))).doit() == 1
Esempio n. 8
0
def test_eval_trace():
    up = JzKet(S(1) / 2, S(1) / 2)
    down = JzKet(S(1) / 2, -S(1) / 2)
    d = Density((up, 0.5), (down, 0.5))

    t = Tr(d)
    assert t.doit() == 1

    #test dummy time dependent states
    class TestTimeDepKet(TimeDepKet):
        def _eval_trace(self, bra, **options):
            return 1

    x, t = symbols('x t')
    k1 = TestTimeDepKet(0, 0.5)
    k2 = TestTimeDepKet(0, 1)
    d = Density([k1, 0.5], [k2, 0.5])
    assert d.doit() == (0.5 * OuterProduct(k1, k1.dual) +
                        0.5 * OuterProduct(k2, k2.dual))

    t = Tr(d)
    assert t.doit() == 1
Esempio n. 9
0
def test_permute():
    A, B, C, D, E, F, G = symbols('A B C D E F G', commutative=False)
    t = Tr(A * B * C * D * E * F * G)

    assert t.permute(0).args[0].args == (A, B, C, D, E, F, G)
    assert t.permute(2).args[0].args == (F, G, A, B, C, D, E)
    assert t.permute(4).args[0].args == (D, E, F, G, A, B, C)
    assert t.permute(6).args[0].args == (B, C, D, E, F, G, A)
    assert t.permute(8).args[0].args == t.permute(1).args[0].args

    assert t.permute(-1).args[0].args == (B, C, D, E, F, G, A)
    assert t.permute(-3).args[0].args == (D, E, F, G, A, B, C)
    assert t.permute(-5).args[0].args == (F, G, A, B, C, D, E)
    assert t.permute(-8).args[0].args == t.permute(-1).args[0].args

    t = Tr((A + B) * (B * B) * C * D)
    assert t.permute(2).args[0].args == (C, D, (A + B), (B**2))

    t1 = Tr(A * B)
    t2 = t1.permute(1)
    assert id(t1) != id(t2) and t1 == t2
Esempio n. 10
0
def test_doit():

    x, y = symbols('x y')
    A, B, C, D, E, F = symbols('A B C D E F', commutative=False)
    d = Density([XKet(), 0.5], [PxKet(), 0.5])
    assert (0.5 * (PxKet() * Dagger(PxKet())) + 0.5 *
            (XKet() * Dagger(XKet()))) == d.doit()

    # check for kets with expr in them
    d_with_sym = Density([XKet(x * y), 0.5], [PxKet(x * y), 0.5])
    assert (0.5 * (PxKet(x * y) * Dagger(PxKet(x * y))) + 0.5 *
            (XKet(x * y) * Dagger(XKet(x * y)))) == d_with_sym.doit()

    d = Density([(A + B) * C, 1.0])
    assert d.doit() == (1.0 * A * C * Dagger(C) * Dagger(A) +
                        1.0 * A * C * Dagger(C) * Dagger(B) +
                        1.0 * B * C * Dagger(C) * Dagger(A) +
                        1.0 * B * C * Dagger(C) * Dagger(B))

    #  With TensorProducts as args
    # Density with simple tensor products as args
    t = TensorProduct(A, B, C)
    d = Density([t, 1.0])
    assert d.doit() == \
        1.0 * TensorProduct(A*Dagger(A), B*Dagger(B), C*Dagger(C))

    # Density with multiple Tensorproducts as states
    t2 = TensorProduct(A, B)
    t3 = TensorProduct(C, D)

    d = Density([t2, 0.5], [t3, 0.5])
    assert d.doit() == (0.5 * TensorProduct(A * Dagger(A), B * Dagger(B)) +
                        0.5 * TensorProduct(C * Dagger(C), D * Dagger(D)))

    #Density with mixed states
    d = Density([t2 + t3, 1.0])
    assert d.doit() == (1.0 * TensorProduct(A * Dagger(A), B * Dagger(B)) +
                        1.0 * TensorProduct(A * Dagger(C), B * Dagger(D)) +
                        1.0 * TensorProduct(C * Dagger(A), D * Dagger(B)) +
                        1.0 * TensorProduct(C * Dagger(C), D * Dagger(D)))

    #Density operators with spin states
    tp1 = TensorProduct(JzKet(1, 1), JzKet(1, -1))
    d = Density([tp1, 1])

    # full trace
    t = Tr(d)
    assert t.doit() == 1

    #Partial trace on density operators with spin states
    t = Tr(d, [0])
    assert t.doit() == JzKet(1, -1) * Dagger(JzKet(1, -1))
    t = Tr(d, [1])
    assert t.doit() == JzKet(1, 1) * Dagger(JzKet(1, 1))

    # with another spin state
    tp2 = TensorProduct(JzKet(S(1) / 2, S(1) / 2), JzKet(S(1) / 2, -S(1) / 2))
    d = Density([tp2, 1])

    #full trace
    t = Tr(d)
    assert t.doit() == 1

    #Partial trace on density operators with spin states
    t = Tr(d, [0])
    assert t.doit() == JzKet(S(1) / 2, -S(1) / 2) * Dagger(
        JzKet(S(1) / 2, -S(1) / 2))
    t = Tr(d, [1])
    assert t.doit() == JzKet(S(1) / 2,
                             S(1) / 2) * Dagger(JzKet(S(1) / 2,
                                                      S(1) / 2))
Esempio n. 11
0
def test_Tr():
    A, B = symbols('A B', commutative=False)
    t = Tr(A*B)
    assert str(t) == 'Tr(A*B)'
Esempio n. 12
0
def test_trace_new():
    a, b, c, d, Y = symbols('a b c d Y')
    A, B, C, D = symbols('A B C D', commutative=False)

    assert Tr(a + b) == a + b
    assert Tr(A + B) == Tr(A) + Tr(B)

    #check trace args not implicitly permuted
    assert Tr(C * D * A * B).args[0].args == (C, D, A, B)

    # check for mul and adds
    assert Tr((a * b) + (c * d)) == (a * b) + (c * d)
    # Tr(scalar*A) = scalar*Tr(A)
    assert Tr(a * A) == a * Tr(A)
    assert Tr(a * A * B * b) == a * b * Tr(A * B)

    # since A is symbol and not commutative
    assert isinstance(Tr(A), Tr)

    #POW
    assert Tr(pow(a, b)) == a**b
    assert isinstance(Tr(pow(A, a)), Tr)

    #Matrix
    M = Matrix([[1, 1], [2, 2]])
    assert Tr(M) == 3

    ##test indices in different forms
    #no index
    t = Tr(A)
    assert t.args[1] == Tuple()

    #single index
    t = Tr(A, 0)
    assert t.args[1] == Tuple(0)

    #index in a list
    t = Tr(A, [0])
    assert t.args[1] == Tuple(0)

    t = Tr(A, [0, 1, 2])
    assert t.args[1] == Tuple(0, 1, 2)

    #index is tuple
    t = Tr(A, (0))
    assert t.args[1] == Tuple(0)

    t = Tr(A, (1, 2))
    assert t.args[1] == Tuple(1, 2)

    #trace indices test
    t = Tr((A + B), [2])
    assert t.args[0].args[1] == Tuple(2) and t.args[1].args[1] == Tuple(2)

    t = Tr(a * A, [2, 3])
    assert t.args[1].args[1] == Tuple(2, 3)

    #class with trace method defined
    #to simulate numpy objects
    class Foo:
        def trace(self):
            return 1

    assert Tr(Foo()) == 1

    #argument test
    # check for value error, when either/both arguments are not provided
    raises(ValueError, lambda: Tr())
    raises(ValueError, lambda: Tr(A, 1, 2))
Esempio n. 13
0
def test_eval_trace():

    q1 = Qubit('10110')
    q2 = Qubit('01010')
    d = Density([q1, 0.6], [q2, 0.4])

    t = Tr(d)
    assert t.doit() == 1

    # extreme bits
    t = Tr(d, 0)
    assert t.doit() == (0.4 * Density([Qubit('0101'), 1]) +
                        0.6 * Density([Qubit('1011'), 1]))
    t = Tr(d, 4)
    assert t.doit() == (0.4 * Density([Qubit('1010'), 1]) +
                        0.6 * Density([Qubit('0110'), 1]))
    # index somewhere in between
    t = Tr(d, 2)
    assert t.doit() == (0.4 * Density([Qubit('0110'), 1]) +
                        0.6 * Density([Qubit('1010'), 1]))
    #trace all indices
    t = Tr(d, [0, 1, 2, 3, 4])
    assert t.doit() == 1

    # trace some indices, initialized in
    # non-canonical order
    t = Tr(d, [2, 1, 3])
    assert t.doit() == (0.4 * Density([Qubit('00'), 1]) +
                        0.6 * Density([Qubit('10'), 1]))

    # mixed states
    q = (1 / sqrt(2)) * (Qubit('00') + Qubit('11'))
    d = Density([q, 1.0])
    t = Tr(d, 0)
    assert t.doit() == (0.5 * Density([Qubit('0'), 1]) +
                        0.5 * Density([Qubit('1'), 1]))
Esempio n. 14
0
 def _eval_trace(self, **kwargs):
     indices = kwargs.get('indices', [])
     return Tr(self.doit(), indices).doit()
Esempio n. 15
0
def test_Tr():
    #TODO: Handle indices
    A, B = symbols('A B', commutative=False)
    t = Tr(A * B)
    assert latex(t) == r'\mbox{Tr}\left(A B\right)'
Esempio n. 16
0
def test_eval_trace():
    q1 = Qubit('10110')
    q2 = Qubit('01010')
    d = Density([q1, 0.6], [q2, 0.4])

    t = Tr(d)
    assert t.doit() == 1

    # extreme bits
    t = Tr(d, 0)
    assert t.doit() == (0.4*Density([Qubit('0101'), 1]) +
                        0.6*Density([Qubit('1011'), 1]))
    t = Tr(d, 4)
    assert t.doit() == (0.4*Density([Qubit('1010'), 1]) +
                        0.6*Density([Qubit('0110'), 1]))
    # index somewhere in between
    t = Tr(d, 2)
    assert t.doit() == (0.4*Density([Qubit('0110'), 1]) +
                        0.6*Density([Qubit('1010'), 1]))
    #trace all indices
    t = Tr(d, [0, 1, 2, 3, 4])
    assert t.doit() == 1

    # trace some indices, initialized in
    # non-canonical order
    t = Tr(d, [2, 1, 3])
    assert t.doit() == (0.4*Density([Qubit('00'), 1]) +
                        0.6*Density([Qubit('10'), 1]))

    # mixed states
    q = (1/sqrt(2)) * (Qubit('00') + Qubit('11'))
    d = Density( [q, 1.0] )
    t = Tr(d, 0)
    assert t.doit() == (0.5*Density([Qubit('0'), 1]) +
                        0.5*Density([Qubit('1'), 1]))
Esempio n. 17
0
def test_Tr():
    A, B = symbols("A B", commutative=False)
    t = Tr(A * B)
    assert str(t) == "Tr(A*B)"
Esempio n. 18
0
def test_permute():
    A, B, C, D, E, F, G = symbols('A B C D E F G', commutative=False)
    t = Tr(A*B*C*D*E*F*G)

    assert t.permute(0).args[0].args == (A, B, C, D, E, F, G)
    assert t.permute(2).args[0].args == (F, G, A, B, C, D, E)
    assert t.permute(4).args[0].args == (D, E, F, G, A, B, C)
    assert t.permute(6).args[0].args == (B, C, D, E, F, G, A)
    assert t.permute(8).args[0].args == t.permute(1).args[0].args

    assert t.permute(-1).args[0].args == (B, C, D, E, F, G, A)
    assert t.permute(-3).args[0].args == (D, E, F, G, A, B, C)
    assert t.permute(-5).args[0].args == (F, G, A, B, C, D, E)
    assert t.permute(-8).args[0].args == t.permute(-1).args[0].args

    t = Tr((A + B)*(B*B)*C*D)
    assert t.permute(2).args[0].args == (C, D, (A + B), (B**2))

    t1 = Tr(A*B)
    t2 = t1.permute(1)
    assert id(t1) != id(t2) and t1 == t2
Esempio n. 19
0
def test_eval_trace():
    # This test includes tests with dependencies between TensorProducts
    #and density operators. Since, the test is more to test the behavior of
    #TensorProducts it remains here

    A, B, C, D, E, F = symbols('A B C D E F', commutative=False)

    # Density with simple tensor products as args
    t = TensorProduct(A, B)
    d = Density([t, 1.0])
    tr = Tr(d)
    assert tr.doit() == 1.0 * Tr(A * Dagger(A)) * Tr(B * Dagger(B))

    ## partial trace with simple tensor products as args
    t = TensorProduct(A, B, C)
    d = Density([t, 1.0])
    tr = Tr(d, [1])
    assert tr.doit() == 1.0 * A * Dagger(A) * Tr(B * Dagger(B)) * C * Dagger(C)

    tr = Tr(d, [0, 2])
    assert tr.doit() == 1.0 * Tr(A * Dagger(A)) * B * Dagger(B) * Tr(
        C * Dagger(C))

    # Density with multiple Tensorproducts as states
    t2 = TensorProduct(A, B)
    t3 = TensorProduct(C, D)

    d = Density([t2, 0.5], [t3, 0.5])
    t = Tr(d)
    assert t.doit() == (0.5 * Tr(A * Dagger(A)) * Tr(B * Dagger(B)) +
                        0.5 * Tr(C * Dagger(C)) * Tr(D * Dagger(D)))

    t = Tr(d, [0])
    assert t.doit() == (0.5 * Tr(A * Dagger(A)) * B * Dagger(B) +
                        0.5 * Tr(C * Dagger(C)) * D * Dagger(D))

    #Density with mixed states
    d = Density([t2 + t3, 1.0])
    t = Tr(d)
    assert t.doit() == (1.0 * Tr(A * Dagger(A)) * Tr(B * Dagger(B)) +
                        1.0 * Tr(A * Dagger(C)) * Tr(B * Dagger(D)) +
                        1.0 * Tr(C * Dagger(A)) * Tr(D * Dagger(B)) +
                        1.0 * Tr(C * Dagger(C)) * Tr(D * Dagger(D)))

    t = Tr(d, [1])
    assert t.doit() == (1.0 * A * Dagger(A) * Tr(B * Dagger(B)) +
                        1.0 * A * Dagger(C) * Tr(B * Dagger(D)) +
                        1.0 * C * Dagger(A) * Tr(D * Dagger(B)) +
                        1.0 * C * Dagger(C) * Tr(D * Dagger(D)))