def test_make_disjunct_indices():
    i = IdxSym('i')
    j = IdxSym('j')
    k = IdxSym('k')

    def Psi(*args):
        return KetSymbol(StrLabel(Indexed(IndexedBase('Psi'), *args)), hs=0)

    def sum(term, *index_symbols):
        return KetIndexedSum(
            term, ranges=[IndexOverRange(i, 0, 2) for i in index_symbols])

    with pytest.raises(ValueError):
        sum(Psi(i, j, j), i, j, j)

    expr = sum(Psi(i, j, k), i, j, k)
    others = [expr]
    expected = expr.substitute({i: i.prime, j: j.prime, k: k.prime})
    expr_primed = expr.make_disjunct_indices(*others)
    assert expr_primed == expected

    others = [sum(Psi(i), i), sum(Psi(j), j)]
    assert expr.make_disjunct_indices(*others) == expr.substitute({
        i: i.prime,
        j: j.prime
    })

    others = [sum(Psi(i), i), sum(Psi(i.prime), i.prime)]
    assert expr.make_disjunct_indices(*others) == expr.substitute(
        {i: i.prime.prime})
Beispiel #2
0
def test_ascii_symbolic_labels():
    """Test ascii representation of symbols with symbolic labels"""
    i = IdxSym('i')
    j = IdxSym('j')
    hs0 = LocalSpace(0)
    hs1 = LocalSpace(1)
    Psi = IndexedBase('Psi')
    assert ascii(BasisKet(FockIndex(2 * i), hs=hs0)) == '|2*i>^(0)'
    assert ascii(KetSymbol(StrLabel(2 * i), hs=hs0)) == '|2*i>^(0)'
    assert (ascii(KetSymbol(StrLabel(Psi[i, j]),
                            hs=hs0 * hs1)) == '|Psi_ij>^(0*1)')
    expr = BasisKet(FockIndex(i), hs=hs0) * BasisKet(FockIndex(j), hs=hs1)
    assert ascii(expr) == '|i,j>^(0*1)'
    assert ascii(Bra(BasisKet(FockIndex(2 * i), hs=hs0))) == '<2*i|^(0)'
    assert (ascii(LocalSigma(FockIndex(i), FockIndex(j),
                             hs=hs0)) == '|i><j|^(0)')
    expr = CoherentStateKet(symbols('alpha'), hs=1).to_fock_representation()
    assert (ascii(expr) == 'exp(-alpha*conjugate(alpha)/2) * '
            '(Sum_{n in H_1} alpha**n/sqrt(n!) * |n>^(1))')

    tls = SpinSpace(label='s', spin='1/2', basis=('down', 'up'))
    Sig = IndexedBase('sigma')
    n = IdxSym('n')
    Sig_n = OperatorSymbol(StrLabel(Sig[n]), hs=tls)
    assert ascii(Sig_n, show_hs_label=False) == 'sigma_n'
Beispiel #3
0
def test_tex_symbolic_labels():
    """Test tex representation of symbols with symbolic labels"""
    i = IdxSym('i')
    j = IdxSym('j')
    hs0 = LocalSpace(0)
    hs1 = LocalSpace(1)
    Psi = IndexedBase('Psi')
    with configure_printing(tex_use_braket=True):
        assert latex(BasisKet(FockIndex(2 * i), hs=hs0)) == r'\Ket{2 i}^{(0)}'
        assert latex(KetSymbol(StrLabel(2 * i), hs=hs0)) == r'\Ket{2 i}^{(0)}'
        assert (latex(KetSymbol(StrLabel(Psi[i, j]), hs=hs0 *
                                hs1)) == r'\Ket{\Psi_{i j}}^{(0 \otimes 1)}')
        expr = BasisKet(FockIndex(i), hs=hs0) * BasisKet(FockIndex(j), hs=hs1)
        assert latex(expr) == r'\Ket{i,j}^{(0 \otimes 1)}'
        assert (latex(Bra(BasisKet(FockIndex(2 * i),
                                   hs=hs0))) == r'\Bra{2 i}^{(0)}')
        assert (latex(LocalSigma(FockIndex(i), FockIndex(j),
                                 hs=hs0)) == r'\Ket{i}\!\Bra{j}^{(0)}')
        alpha = symbols('alpha')
        expr = CoherentStateKet(alpha, hs=1).to_fock_representation()
        assert (latex(expr) == r'e^{- \frac{\alpha \overline{\alpha}}{2}} '
                r'\left(\sum_{n \in \mathcal{H}_{1}} '
                r'\frac{\alpha^{n}}{\sqrt{n!}} \Ket{n}^{(1)}\right)')
        assert (latex(
            expr, conjg_style='star') == r'e^{- \frac{\alpha {\alpha}^*}{2}} '
                r'\left(\sum_{n \in \mathcal{H}_{1}} '
                r'\frac{\alpha^{n}}{\sqrt{n!}} \Ket{n}^{(1)}\right)')

    tls = SpinSpace(label='s', spin='1/2', basis=('down', 'up'))
    Sig = IndexedBase('sigma')
    n = IdxSym('n')
    Sig_n = OperatorSymbol(StrLabel(Sig[n]), hs=tls)
    assert latex(Sig_n, show_hs_label=False) == r'\hat{\sigma}_{n}'
Beispiel #4
0
def test_sum_instantiator():
    """Test use of Sum instantiator."""
    i = IdxSym('i')
    j = IdxSym('j')
    ket_i = BasisKet(FockIndex(i), hs=0)
    ket_j = BasisKet(FockIndex(j), hs=0)
    A_i = OperatorSymbol(StrLabel(IndexedBase('A')[i]), hs=0)
    hs0 = LocalSpace('0')

    sum = Sum(i)(ket_i)
    ful = KetIndexedSum(ket_i, ranges=IndexOverFockSpace(i, hs=hs0))
    assert sum == ful
    assert sum == Sum(i, hs0)(ket_i)
    assert sum == Sum(i, hs=hs0)(ket_i)

    sum = Sum(i, 1, 10)(ket_i)
    ful = KetIndexedSum(ket_i, ranges=IndexOverRange(i, 1, 10))
    assert sum == ful
    assert sum == Sum(i, 1, 10, 1)(ket_i)
    assert sum == Sum(i, 1, to=10, step=1)(ket_i)
    assert sum == Sum(i, 1, 10, step=1)(ket_i)

    sum = Sum(i, (1, 2, 3))(ket_i)
    ful = KetIndexedSum(ket_i, ranges=IndexOverList(i, (1, 2, 3)))
    assert sum == KetIndexedSum(ket_i, ranges=IndexOverList(i, (1, 2, 3)))
    assert sum == Sum(i, [1, 2, 3])(ket_i)

    sum = Sum(i)(Sum(j)(ket_i * ket_j.dag()))
    ful = OperatorIndexedSum(
        ket_i * ket_j.dag(),
        ranges=(IndexOverFockSpace(i, hs0), IndexOverFockSpace(j, hs0)),
    )
    assert sum == ful
Beispiel #5
0
def test_quantum_derivative_nonatomic_free_symbols(MyScalarFunc):
    """Test the free_symbols of an evaluated derivative for non-atomic
    symbols"""
    s = IndexedBase('s')
    t = IndexedBase('t')
    i = IdxSym('i')
    j = IdxSym('j')
    t0 = symbols('t_0', real=True)
    f = MyScalarFunc("f", s[i], t[j])
    fdot = f.diff(s[i], n=2).diff(t[j]).evaluate_at({t[j]: t0})
    assert fdot == fdot.__class__(f,
                                  derivs={
                                      s[i]: 2,
                                      t[j]: 1
                                  },
                                  vals={t[j]: t0})
    assert fdot.kwargs == OrderedDict([('derivs', ((s[i], 2), (t[j], 1))),
                                       ('vals', ((t[j], t0), ))])
    assert fdot.derivs == {s[i]: 2, t[j]: 1}
    assert fdot.syms == {s[i], t[j]}
    assert fdot.vals == {t[j]: t0}
    assert fdot.free_symbols == set([s.args[0], s[i], i, t0])
    assert fdot.bound_symbols == set([t.args[0], j, t[j]])
    assert fdot.all_symbols == set(
        [s.args[0], t.args[0], t0, i, j, s[i], t[j]])
    assert fdot.diff(s[i]).n == 4
    assert fdot.diff(t[j]) == Zero

    f = MyScalarFunc("f", s[i], t[j], j)  # additional argument j
    fdot = f.diff(s[i], n=2).diff(t[j]).evaluate_at({t[j]: t0})
    assert fdot.free_symbols == set([s.args[0], i, j, s[i], t0])
    assert fdot.bound_symbols == set([t.args[0], j, t[j]])
def test_kronecker_delta():
    """Test of KroneckerDelta, in addition to the doctest"""
    i, j = IdxSym('i'), IdxSym('j')

    delta_ij = KroneckerDelta(i, j)
    assert isinstance(delta_ij, Scalar)
    assert delta_ij != Zero
    assert delta_ij != One
    assert isinstance(delta_ij.val, SympyKroneckerDelta)
    assert delta_ij.substitute({i: 1, j: 1}) == One
    assert delta_ij.substitute({i: 0, j: 1}) == Zero

    delta_i1 = KroneckerDelta(i, 1)
    assert isinstance(delta_i1, Scalar)
    assert delta_i1 != Zero
    assert delta_i1 != One
    assert isinstance(delta_i1.val, SympyKroneckerDelta)
    assert delta_i1.substitute({i: 1}) == One
    assert delta_i1.substitute({i: 0}) == Zero

    delta_1i = KroneckerDelta(1, i)
    assert isinstance(delta_1i, Scalar)
    assert delta_1i != Zero
    assert delta_1i != One
    assert isinstance(delta_1i.val, SympyKroneckerDelta)
    assert delta_i1.substitute({i: 1}) == One
    assert delta_i1.substitute({i: 0}) == Zero
def test_operator_kronecker_sum():
    """Test that Kronecker delta are eliminiated from indexed sums over
    operators"""
    i = IdxSym('i')
    j = IdxSym('j')
    alpha = symbols('alpha')
    delta_ij = KroneckerDelta(i, j)
    delta_0i = KroneckerDelta(0, i)
    delta_1j = KroneckerDelta(1, j)
    delta_0j = KroneckerDelta(0, j)
    delta_1i = KroneckerDelta(1, i)

    def A(i, j):
        return OperatorSymbol(StrLabel(IndexedBase('A')[i, j]), hs=0)

    term = delta_ij * A(i, j)
    sum = OperatorIndexedSum.create(term,
                                    ranges=(IndexOverList(i, (1, 2)),
                                            IndexOverList(j, (1, 2))))
    assert sum == OperatorIndexedSum.create(A(i, i),
                                            ranges=(IndexOverList(i,
                                                                  (1, 2)), ))
    assert sum.doit() == (OperatorSymbol("A_11", hs=0) +
                          OperatorSymbol("A_22", hs=0))

    term = alpha * delta_ij * A(i, j)
    range_i = IndexOverList(i, (1, 2))
    range_j = IndexOverList(j, (1, 2))
    sum = OperatorIndexedSum.create(term, ranges=(range_i, range_j))
    assert isinstance(sum, ScalarTimesOperator)
    expected = alpha * OperatorIndexedSum.create(
        A(i, i), ranges=(IndexOverList(i, (1, 2)), ))
    assert sum == expected

    hs = LocalSpace('0', basis=('g', 'e'))
    i_range = IndexOverFockSpace(i, hs)
    j_range = IndexOverFockSpace(j, hs)
    sig_ij = LocalSigma(FockIndex(i), FockIndex(j), hs=hs)
    sig_0j = LocalSigma('g', FockIndex(j), hs=hs)
    sig_i1 = LocalSigma(FockIndex(i), 'e', hs=hs)

    term = delta_0i * delta_1j * sig_ij

    sum = OperatorIndexedSum.create(term, ranges=(i_range, ))
    expected = delta_1j * sig_0j
    assert sum == expected

    sum = OperatorIndexedSum.create(term, ranges=(j_range, ))
    expected = delta_0i * sig_i1
    assert sum == expected

    term = (delta_0i * delta_1j + delta_0j * delta_1i) * sig_ij
    sum = OperatorIndexedSum.create(term, ranges=(i_range, j_range))
    expected = LocalSigma('g', 'e', hs=hs) + LocalSigma('e', 'g', hs=hs)
    assert sum == expected
def test_two_hs_symbol_sum():
    """Test sum_{ij} a_{ij} Psi_{ij}"""
    i = IdxSym('i')
    j = IdxSym('j')
    a = IndexedBase('a')
    hs1 = LocalSpace('1', dimension=3)
    hs2 = LocalSpace('2', dimension=3)
    hs = hs1 * hs2
    Psi = IndexedBase('Psi')
    a_ij = a[i, j]
    Psi_ij = Psi[i, j]
    KetPsi_ij = KetSymbol(StrLabel(Psi_ij), hs=hs)
    term = a_ij * KetPsi_ij

    expr1 = KetIndexedSum(
        term,
        ranges=(IndexOverFockSpace(i, hs=hs1), IndexOverFockSpace(j, hs=hs2)),
    )

    expr2 = KetIndexedSum(term,
                          ranges=(IndexOverRange(i, 0,
                                                 2), IndexOverRange(j, 0, 2)))

    assert expr1.term.free_symbols == set(
        [i, j, symbols('a'), symbols('Psi'), a_ij, Psi_ij])
    assert expr1.free_symbols == set(
        [symbols('a'), symbols('Psi'), a_ij, Psi_ij])
    assert expr1.variables == [i, j]

    assert (
        ascii(expr1) == 'Sum_{i in H_1} Sum_{j in H_2} a_ij * |Psi_ij>^(1*2)')
    assert unicode(expr1) == '∑_{i ∈ ℌ₁} ∑_{j ∈ ℌ₂} a_ij |Ψ_ij⟩^(1⊗2)'
    assert (latex(expr1) ==
            r'\sum_{i \in \mathcal{H}_{1}} \sum_{j \in \mathcal{H}_{2}} '
            r'a_{i j} \left\lvert \Psi_{i j} \right\rangle^{(1 \otimes 2)}')

    assert ascii(expr2) == 'Sum_{i,j=0}^{2} a_ij * |Psi_ij>^(1*2)'
    assert unicode(expr2) == '∑_{i,j=0}^{2} a_ij |Ψ_ij⟩^(1⊗2)'
    assert (latex(expr2) == r'\sum_{i,j=0}^{2} a_{i j} '
            r'\left\lvert \Psi_{i j} \right\rangle^{(1 \otimes 2)}')

    assert expr1.doit() == expr2.doit()
    assert expr1.doit() == KetPlus(
        a[0, 0] * KetSymbol('Psi_00', hs=hs),
        a[0, 1] * KetSymbol('Psi_01', hs=hs),
        a[0, 2] * KetSymbol('Psi_02', hs=hs),
        a[1, 0] * KetSymbol('Psi_10', hs=hs),
        a[1, 1] * KetSymbol('Psi_11', hs=hs),
        a[1, 2] * KetSymbol('Psi_12', hs=hs),
        a[2, 0] * KetSymbol('Psi_20', hs=hs),
        a[2, 1] * KetSymbol('Psi_21', hs=hs),
        a[2, 2] * KetSymbol('Psi_22', hs=hs),
    )
def test_qubit_state_bra():
    """Test  sum_i alpha_i <i| for TLS"""
    i = IdxSym('i')
    alpha = IndexedBase('alpha')
    alpha_i = alpha[i]
    hs_tls = LocalSpace('tls', basis=('g', 'e'))

    term = alpha_i * BasisKet(FockIndex(i), hs=hs_tls).dag()

    expr = KetIndexedSum.create(term, ranges=IndexOverFockSpace(i, hs=hs_tls))

    assert IndexOverFockSpace(i, hs=hs_tls) in expr.ket.kwargs['ranges']

    assert ascii(expr) == "Sum_{i in H_tls} alpha_i * <i|^(tls)"

    assert expr.ket.term.free_symbols == set([i, symbols('alpha'), alpha_i])
    assert expr.free_symbols == set([symbols('alpha'), alpha_i])
    assert expr.ket.variables == [i]
    assert expr.space == hs_tls
    assert len(expr.ket.args) == 1
    assert len(expr.ket.operands) == 1
    assert len(expr.ket.kwargs) == 1
    assert expr.ket.args[0] == term.ket
    assert expr.ket.term == term.ket
    assert len(expr.kwargs) == 0
    expr_expand = Bra.create(expr.ket.doit().substitute({
        alpha[0]: alpha['g'],
        alpha[1]: alpha['e']
    }))
    assert expr_expand == (alpha['g'] * BasisKet('g', hs=hs_tls).dag() +
                           alpha['e'] * BasisKet('e', hs=hs_tls).dag())
    assert ascii(expr_expand) == 'alpha_e * <e|^(tls) + alpha_g * <g|^(tls)'
def test_coherent_state():
    """Test fock representation of coherent state"""
    alpha = symbols('alpha')
    hs0 = LocalSpace(0)
    hs1 = LocalSpace(1, dimension=3)
    i = IdxSym('i')
    n = IdxSym('n')

    psi = CoherentStateKet(alpha, hs=hs0)
    psi_focksum_3 = psi.to_fock_representation(max_terms=3)
    assert len(psi_focksum_3.term) == 3
    for n_val in (0, 1, 2):
        assert n_val in psi_focksum_3.term.ranges[0]
    psi_focksum_inf = psi.to_fock_representation()
    with pytest.raises(InfiniteSumError):
        len(psi_focksum_inf.term)
    for n_val in (0, 1, 2, 3):
        assert n_val in psi_focksum_inf.term.ranges[0]

    assert psi_focksum_inf.term.term.free_symbols == set([n, symbols('alpha')])
    assert psi_focksum_inf.free_symbols == set([symbols('alpha')])
    assert psi_focksum_inf.term.variables == [n]

    assert psi_focksum_inf.substitute({n: i}).term.variables == [i]
    assert (psi_focksum_inf.substitute({hs0: hs1}) == CoherentStateKet(
        alpha, hs=hs1).to_fock_representation())

    assert (psi.to_fock_representation(index_symbol='i').substitute(
        {i: n}) == psi_focksum_inf)
    assert (psi.to_fock_representation(index_symbol=i).substitute(
        {i: n}) == psi_focksum_inf)

    assert psi_focksum_3.doit([IndexedSum
                               ]) == psi_focksum_inf.doit([IndexedSum],
                                                          max_terms=3)
    psi_expanded_3 = psi_focksum_3.doit([IndexedSum])
    assert psi_expanded_3 == (
        sympy.exp(-alpha * alpha.conjugate() / 2) * KetPlus(
            BasisKet(0, hs=LocalSpace(0)),
            ScalarTimesKet(alpha, BasisKet(1, hs=LocalSpace(0))),
            ScalarTimesKet(alpha**2 / sympy.sqrt(2),
                           BasisKet(2, hs=LocalSpace(0))),
        ))

    psi = CoherentStateKet(alpha, hs=hs1)
    assert psi.to_fock_representation().doit(
        [IndexedSum]) == psi_expanded_3.substitute({hs0: hs1})
Beispiel #11
0
def test_index_over_range_with_step():
    i = IdxSym('i')
    r = IndexOverRange(i, 1, 10, step=2)
    assert len(r) == 5
    assert list(r.range) == [1, 3, 5, 7, 9]
    for val in r.range:
        assert val in r
    assert 2 not in r
    assert 10 not in r
Beispiel #12
0
def test_index_over_range_bw():
    i = IdxSym('i')
    r = IndexOverRange(i, 10, 1, step=-2)
    assert len(r) == 5
    assert list(r.range) == [10, 8, 6, 4, 2]
    for val in r.range:
        assert val in r
    assert 5 not in r
    assert 1 not in r
Beispiel #13
0
def test_unicode_ket_operations():
    """Test the unicode representation of ket operations"""
    hs1 = LocalSpace('q_1', basis=('g', 'e'))
    hs2 = LocalSpace('q_2', basis=('g', 'e'))
    ket_g1 = BasisKet('g', hs=hs1)
    ket_e1 = BasisKet('e', hs=hs1)
    ket_g2 = BasisKet('g', hs=hs2)
    ket_e2 = BasisKet('e', hs=hs2)
    psi1 = KetSymbol("Psi_1", hs=hs1)
    psi2 = KetSymbol("Psi_2", hs=hs1)
    phi = KetSymbol("Phi", hs=hs2)
    A = OperatorSymbol("A_0", hs=hs1)
    gamma = symbols('gamma', positive=True)
    alpha = symbols('alpha')
    beta = symbols('beta')
    phase = exp(-I * gamma)
    i = IdxSym('i')
    assert unicode(psi1 + psi2) == '|Ψ₁⟩^(q₁) + |Ψ₂⟩^(q₁)'
    assert unicode(psi1 * phi) == '|Ψ₁⟩^(q₁) ⊗ |Φ⟩^(q₂)'
    assert unicode(phase * psi1) == 'exp(-ⅈ γ) |Ψ₁⟩^(q₁)'
    assert unicode((alpha + 1) * KetSymbol('Psi', hs=0)) == '(α + 1) |Ψ⟩⁽⁰⁾'
    assert (unicode(
        A * psi1) == 'A\u0302_0^(q\u2081) |\u03a8\u2081\u27e9^(q\u2081)')
    #        Â_0^(q₁) |Ψ₁⟩^(q₁)
    assert unicode(BraKet(psi1, psi2)) == '⟨Ψ₁|Ψ₂⟩^(q₁)'
    expr = BraKet(KetSymbol('Psi_1', alpha, hs=hs1),
                  KetSymbol('Psi_2', beta, hs=hs1))
    assert unicode(expr) == '⟨Ψ₁(α)|Ψ₂(β)⟩^(q₁)'
    assert unicode(ket_e1.dag() * ket_e1) == '1'
    assert unicode(ket_g1.dag() * ket_e1) == '0'
    assert unicode(KetBra(psi1, psi2)) == '|Ψ₁⟩⟨Ψ₂|^(q₁)'
    expr = KetBra(KetSymbol('Psi_1', alpha, hs=hs1),
                  KetSymbol('Psi_2', beta, hs=hs1))
    assert unicode(expr) == '|Ψ₁(α)⟩⟨Ψ₂(β)|^(q₁)'
    bell1 = (ket_e1 * ket_g2 - I * ket_g1 * ket_e2) / sqrt(2)
    bell2 = (ket_e1 * ket_e2 - ket_g1 * ket_g2) / sqrt(2)
    assert unicode(bell1) == '1/√2 (|eg⟩^(q₁⊗q₂) - ⅈ |ge⟩^(q₁⊗q₂))'
    assert (unicode(BraKet.create(
        bell1,
        bell2)) == r'1/2 (⟨eg|^(q₁⊗q₂) + ⅈ ⟨ge|^(q₁⊗q₂)) (|ee⟩^(q₁⊗q₂) - '
            r'|gg⟩^(q₁⊗q₂))')
    assert (unicode(KetBra.create(
        bell1,
        bell2)) == r'1/2 (|eg⟩^(q₁⊗q₂) - ⅈ |ge⟩^(q₁⊗q₂))(⟨ee|^(q₁⊗q₂) - '
            r'⟨gg|^(q₁⊗q₂))')
    assert (unicode(
        KetBra.create(bell1, bell2),
        show_hs_label=False) == r'1/2 (|eg⟩ - ⅈ |ge⟩)(⟨ee| - ⟨gg|)')
    expr = KetBra(KetSymbol('Psi', hs=0), BasisKet(FockIndex(i), hs=0))
    assert unicode(expr) == "|Ψ⟩⟨i|⁽⁰⁾"
    expr = KetBra(BasisKet(FockIndex(i), hs=0), KetSymbol('Psi', hs=0))
    assert unicode(expr) == "|i⟩⟨Ψ|⁽⁰⁾"
    expr = BraKet(KetSymbol('Psi', hs=0), BasisKet(FockIndex(i), hs=0))
    assert unicode(expr) == "⟨Ψ|i⟩⁽⁰⁾"
    expr = BraKet(BasisKet(FockIndex(i), hs=0), KetSymbol('Psi', hs=0))
    assert unicode(expr) == "⟨i|Ψ⟩⁽⁰⁾"
Beispiel #14
0
def test_tex_hilbert_elements():
    """Test the tex representation of "atomic" Hilbert space algebra
    elements"""
    assert latex(LocalSpace(1)) == r'\mathcal{H}_{1}'
    assert latex(LocalSpace(1, dimension=2)) == r'\mathcal{H}_{1}'
    assert latex(LocalSpace(1, basis=(r'g', 'e'))) == r'\mathcal{H}_{1}'
    assert latex(LocalSpace('local')) == r'\mathcal{H}_{\text{local}}'
    assert latex(LocalSpace('kappa')) == r'\mathcal{H}_{\kappa}'
    assert latex(TrivialSpace) == r'\mathcal{H}_{\text{null}}'
    assert latex(FullSpace) == r'\mathcal{H}_{\text{total}}'
    assert latex(LocalSpace(StrLabel(IdxSym('i')))) == r'\mathcal{H}_{i}'
Beispiel #15
0
def test_unicode_hilbert_elements():
    """Test the unicode representation of "atomic" Hilbert space algebra
    elements"""
    assert unicode(LocalSpace(1)) == 'ℌ₁'
    assert unicode(LocalSpace(1, dimension=2)) == 'ℌ₁'
    assert unicode(LocalSpace(1, basis=('g', 'e'))) == 'ℌ₁'
    assert unicode(LocalSpace('local')) == 'ℌ_local'
    assert unicode(LocalSpace('kappa')) == 'ℌ_κ'
    assert unicode(TrivialSpace) == 'ℌ_null'
    assert unicode(FullSpace) == 'ℌ_total'
    assert unicode(LocalSpace(StrLabel(IdxSym('i')))) == 'ℌ_i'
def test_srepr_idx_sym():
    """Test the representation of IdxSym instances"""
    i = IdxSym('i')
    assert srepr(i) == "IdxSym('i', integer=True)"
    assert srepr(i.prime) == "IdxSym('i', integer=True, primed=1)"
    assert eval(srepr(i)) == i
    assert eval(srepr(i.prime)) == i.prime

    i_pos = IdxSym('i', positive=True)
    assert i != i_pos
    assert srepr(i_pos) == "IdxSym('i', integer=True, positive=True)"
    assert eval(srepr(i_pos)) == i_pos
    assert (srepr(i_pos.prime.prime) ==
            "IdxSym('i', integer=True, positive=True, primed=2)")
    assert eval(srepr(i_pos.prime.prime)) == i_pos.prime.prime

    i_nonint = IdxSym('i', integer=False)
    assert i != i_nonint
    assert srepr(i_nonint) == "IdxSym('i', integer=False)"
    assert eval(srepr(i_nonint)) == i_nonint
    assert eval(srepr(i_nonint.prime.prime)) == i_nonint.prime.prime
Beispiel #17
0
def test_quantum_symbols_with_symargs():
    """Test properties and behavior of symbols with scalar arguments,
    through the example of an OperatorSymbol"""
    t = IndexedBase('t')
    i = IdxSym('i')
    j = IdxSym('j')
    alpha, beta = symbols('alpha, beta')
    A = OperatorSymbol("A", t[i], (alpha + 1)**2, hs=0)
    assert A.label == 'A'
    assert len(A.args) == 3
    assert A.kwargs == {'hs': LocalSpace('0')}
    assert A._get_instance_key(A.args, A.kwargs) == (
        OperatorSymbol,
        'A',
        t[i],
        (alpha + 1)**2,
        ('hs', A.space),
    )
    A_beta = OperatorSymbol("A", beta, (alpha + 1)**2, hs=0)
    assert A != A_beta
    assert A.substitute({t[i]: beta}) == A_beta
    half = sympy.sympify(1) / 2
    assert A.sym_args == (t[i], (alpha + 1)**2)
    assert A.free_symbols == {symbols('t'), i, t[i], alpha}
    assert len(A.bound_symbols) == 0
    assert A.simplify_scalar(sympy.expand) == OperatorSymbol("A",
                                                             t[i],
                                                             alpha**2 +
                                                             2 * alpha + 1,
                                                             hs=0)
    assert A.diff(beta) == ZeroOperator
    assert A.diff(t[j]) == ZeroOperator
    assert OperatorSymbol("A", t[i], i, j, hs=0).diff(t[j]) == ZeroOperator
    assert A.diff(alpha) == OperatorDerivative(A, derivs=((alpha, 1), ))
    assert A.expand() == A
    series = A.series_expand(t[i], about=beta, order=2)
    assert len(series) == 3
    assert series[0] == OperatorSymbol("A", beta, (alpha + 1)**2, hs=0)
    assert series[2] == half * OperatorDerivative(
        A, derivs=((t[i], 2), ), vals=((t[i], beta), ))
def test_partial_expansion():
    """Test partially executing the sum (only for a subset of summation
    indices)"""
    i = IdxSym('i')
    j = IdxSym('j')
    k = IdxSym('k')
    hs = LocalSpace('0', dimension=2)
    Psi = IndexedBase('Psi')

    def r(index_symbol):
        return IndexOverFockSpace(index_symbol, hs=hs)

    psi_ijk = KetSymbol(StrLabel(Psi[i, j, k]), hs=hs)

    def psi(i_val, j_val, k_val):
        return psi_ijk.substitute({i: i_val, j: j_val, k: k_val})

    expr = KetIndexedSum(psi_ijk, ranges=(r(i), r(j), r(k)))

    expr_expanded = expr.doit(indices=[i])
    assert expr_expanded == KetIndexedSum(psi(0, j, k) + psi(1, j, k),
                                          ranges=(r(j), r(k)))

    expr_expanded = expr.doit(indices=[j])
    assert expr_expanded == KetIndexedSum(psi(i, 0, k) + psi(i, 1, k),
                                          ranges=(r(i), r(k)))

    assert expr.doit(indices=[j]) == expr.doit(indices=['j'])

    expr_expanded = expr.doit(indices=[i, j])
    assert expr_expanded == KetIndexedSum(psi(0, 0, k) + psi(1, 0, k) +
                                          psi(0, 1, k) + psi(1, 1, k),
                                          ranges=r(k))

    assert expr.doit(indices=[i, j]) == expr.doit(indices=[j, i])

    assert expr.doit(indices=[i, j, k]) == expr.doit()

    with pytest.raises(ValueError):
        expr.doit(indices=[i], max_terms=10)
Beispiel #19
0
def test_ascii_hilbert_elements():
    """Test the ascii representation of "atomic" Hilbert space algebra
    elements"""
    assert ascii(LocalSpace(1)) == 'H_1'
    assert ascii(LocalSpace(1, dimension=2)) == 'H_1'
    assert ascii(LocalSpace(1, basis=('g', 'e'))) == 'H_1'
    assert ascii(LocalSpace('local')) == 'H_local'
    assert ascii(LocalSpace('kappa')) == 'H_kappa'
    with pytest.raises(ValueError):
        LocalSpace(r'\kappa')
    assert ascii(TrivialSpace) == 'H_null'
    assert ascii(FullSpace) == 'H_total'
    assert ascii(LocalSpace(StrLabel(IdxSym('i')))) == 'H_i'
def test_tls_norm():
    """Test that calculating the norm of a TLS state results in 1"""
    hs = LocalSpace('tls', dimension=2)
    i = IdxSym('i')

    ket_i = BasisKet(FockIndex(i), hs=hs)
    nrm = BraKet.create(ket_i, ket_i)
    assert nrm == 1

    psi = KetIndexedSum((1 / sympy.sqrt(2)) * ket_i,
                        ranges=IndexOverFockSpace(i, hs))
    nrm = BraKet.create(psi, psi)
    assert nrm == 1
def test_pull_constfactor_from_operator_sum():
    """Test that a constant in pulled from a sum of operators."""
    i = IdxSym('i')
    alpha = symbols('alpha')

    def A(i, j):
        return OperatorSymbol(StrLabel(IndexedBase('A')[i, j]), hs=0)

    term = alpha * A(i, i)
    range_i = IndexOverList(i, (1, 2))
    expr = OperatorIndexedSum.create(term, ranges=(range_i, ))
    assert isinstance(expr, ScalarTimesOperator)
    assert expr.coeff == alpha
    assert isinstance(expr.term, OperatorIndexedSum)
Beispiel #22
0
def test_ascii_scalar():
    """Test rendering of scalar values"""
    assert ascii(2) == ascii(ScalarValue(2)) == '2'
    ascii.printer.cache = {}
    # we always want 2.0 to be printed as '2'. Without this normalization, the
    # state of the cache might introduce non-reproducible behavior, as 2==2.0
    assert ascii(2.0) == ascii(ScalarValue(2.0)) == '2'
    assert ascii(1j) == ascii(ScalarValue(1j)) == '1j'
    assert ascii('foo') == 'foo'

    i = IdxSym('i')
    alpha = IndexedBase('alpha')
    assert ascii(i) == ascii(ScalarValue(i)) == 'i'
    assert ascii(alpha[i]) == ascii(ScalarValue(alpha[i])) == 'alpha_i'
Beispiel #23
0
def test_abstract_taylor_series(MyScalarFunc):
    """Test a series expansion that is the abstract Taylor series only"""
    s = IndexedBase('s')
    t = IndexedBase('t')
    i = IdxSym('i')
    j = IdxSym('j')
    t0 = symbols('t_0', real=True)
    f = MyScalarFunc("f", s[i], t[j])

    series = f.series_expand(t[j], about=0, order=3)
    assert isinstance(series[0], MyScalarFunc)
    assert isinstance(series[1], QuantumDerivative)
    assert isinstance(series[2], ScalarTimes)
    D = series[1].__class__
    assert series[0] == MyScalarFunc("f", s[i], 0)
    assert series[1] == D(f, derivs={t[j]: 1}, vals={t[j]: 0})
    assert series[2] == D(f, derivs={t[j]: 2}, vals={t[j]: 0}) / 2
    assert series[3] == D(f, derivs={t[j]: 3}, vals={t[j]: 0}) / 6

    series = f.series_expand(t[j], about=t0, order=3)
    assert series[0] == MyScalarFunc("f", s[i], t0)
    assert series[1] == D(f, derivs={t[j]: 1}, vals={t[j]: t0})
    assert series[2] == D(f, derivs={t[j]: 2}, vals={t[j]: t0}) / 2
    assert series[3] == D(f, derivs={t[j]: 3}, vals={t[j]: t0}) / 6
Beispiel #24
0
def test_unicode_symbolic_labels():
    """Test unicode representation of symbols with symbolic labels"""
    i = IdxSym('i')
    j = IdxSym('j')
    hs0 = LocalSpace(0)
    hs1 = LocalSpace(1)
    Psi = IndexedBase('Psi')
    assert unicode(BasisKet(FockIndex(2 * i), hs=hs0)) == '|2 i⟩⁽⁰⁾'
    assert unicode(KetSymbol(StrLabel(2 * i), hs=hs0)) == '|2 i⟩⁽⁰⁾'
    assert (unicode(KetSymbol(StrLabel(Psi[i, j]),
                              hs=hs0 * hs1)) == '|Ψ_ij⟩^(0⊗1)')
    expr = BasisKet(FockIndex(i), hs=hs0) * BasisKet(FockIndex(j), hs=hs1)
    assert unicode(expr) == '|i,j⟩^(0⊗1)'
    assert unicode(Bra(BasisKet(FockIndex(2 * i), hs=hs0))) == '⟨2 i|⁽⁰⁾'
    assert (unicode(LocalSigma(FockIndex(i), FockIndex(j),
                               hs=hs0)) == '|i⟩⟨j|⁽⁰⁾')
    expr = CoherentStateKet(symbols('alpha'), hs=1).to_fock_representation()
    assert unicode(expr) == 'exp(-α α ⃰/2) (∑_{n ∈ ℌ₁} αⁿ/√n! |n⟩⁽¹⁾)'

    tls = SpinSpace(label='s', spin='1/2', basis=('down', 'up'))
    Sig = IndexedBase('sigma')
    n = IdxSym('n')
    Sig_n = OperatorSymbol(StrLabel(Sig[n]), hs=tls)
    assert unicode(Sig_n, show_hs_label=False) == 'σ̂ₙ'
def test_ketbra_indexed_sum():
    """Test ketbra product of sums"""
    i = IdxSym('i')
    hs = LocalSpace(1, dimension=5)
    alpha = IndexedBase('alpha')

    psi = KetSymbol('Psi', hs=hs)

    psi1 = KetIndexedSum(
        alpha[1, i] * BasisKet(FockIndex(i), hs=hs),
        ranges=IndexOverFockSpace(i, hs),
    )

    psi2 = KetIndexedSum(
        alpha[2, i] * BasisKet(FockIndex(i), hs=hs),
        ranges=IndexOverFockSpace(i, hs),
    )

    expr = psi1 * psi2.dag()
    assert expr.space == hs
    expected = OperatorIndexedSum(
        alpha[2, i.prime].conjugate() * alpha[1, i] *
        KetBra.create(BasisKet(FockIndex(i), hs=hs),
                      BasisKet(FockIndex(i.prime), hs=hs)),
        ranges=(IndexOverFockSpace(i, hs), IndexOverFockSpace(i.prime, hs)),
    )
    assert expr == expected
    assert KetBra.create(psi1, psi2) == expr

    expr = psi * psi2.dag()
    assert expr.space == hs
    expected = OperatorIndexedSum(
        alpha[2, i].conjugate() *
        KetBra.create(psi, BasisKet(FockIndex(i), hs=hs)),
        ranges=IndexOverFockSpace(i, hs),
    )
    assert expr == expected
    assert KetBra.create(psi, psi2) == expr

    expr = psi1 * psi.dag()
    assert expr.space == hs
    expected = OperatorIndexedSum(
        alpha[1, i] * KetBra.create(BasisKet(FockIndex(i), hs=hs), psi),
        ranges=IndexOverFockSpace(i, hs),
    )
    assert expr == expected
    assert KetBra.create(psi1, psi) == expr
def test_indexed_sum_over_kronecker_scalarvalue():
    """Test indexed_sum_over_kronecker for a ScalarValue.

    This is an auxiliary test to resolve a bug in test_tls_norm
    """
    i = IdxSym('i')
    ip = i.prime
    term = KroneckerDelta(i, ip) / 2
    assert isinstance(term, ScalarValue)
    hs = LocalSpace('tls', dimension=2)
    i_range = IndexOverFockSpace(i, hs)
    ip_range = IndexOverFockSpace(ip, hs)
    sum = indexed_sum_over_kronecker(
        ScalarIndexedSum,
        ops=(term,),
        kwargs=dict(ranges=(i_range, ip_range)),
    )
    assert sum == 1
def test_create_on_fock_expansion():
    """Test ``Create * sum_i alpha_i |i> = sqrt(i+1) * alpha_i * |i+1>``"""
    i = IdxSym('i')
    alpha = IndexedBase('alpha')
    hs = LocalSpace('0', dimension=3)

    expr = Create(hs=hs) * KetIndexedSum(
        alpha[i] * BasisKet(FockIndex(i), hs=hs),
        ranges=IndexOverFockSpace(i, hs),
    )

    assert expr == KetIndexedSum(
        sympy.sqrt(i + 1) * alpha[i] * BasisKet(FockIndex(i + 1), hs=hs),
        ranges=IndexOverFockSpace(i, hs),
    )

    assert expr.doit() == (alpha[0] * BasisKet(1, hs=hs) +
                           sympy.sqrt(2) * alpha[1] * BasisKet(2, hs=hs))
Beispiel #28
0
def test_unicode_scalar():
    """Test rendering of scalar values"""
    assert unicode(2) == '2'
    # we always want 2.0 to be printed as '2'. Without this normalization, the
    # state of the cache might introduce non-reproducible behavior, as 2==2.0
    unicode.printer.cache = {}
    assert 2 == 2.0
    assert unicode(2.0) == '2'  # would be '2.0' without normalization
    assert unicode(1j) == '1j'
    assert ((I / 2) - 0.5j) == 0
    assert unicode(I / 2) == 'ⅈ/2'
    assert unicode(0.5j) == '0.5j'
    assert unicode(sympy.pi) == 'π'
    assert unicode(sympy.pi / 4) == 'π/4'

    i = IdxSym('i')
    alpha = IndexedBase('alpha')
    assert unicode(alpha[i]) == 'α_i'
    assert unicode(alpha[1]) == 'α₁'
def test_invalid_spin_space():
    """Test that a ValueError is raised when trying to instantiate a SpinSpace
    with and invalid `spin` value"""
    with pytest.raises(ValueError) as exc_info:
        SpinSpace(0, spin=0)
    assert "must be greater than zero" in str(exc_info.value)
    with pytest.raises(ValueError) as exc_info:
        SpinSpace(0, spin=-1)
    assert "must be greater than zero" in str(exc_info.value)
    with pytest.raises(ValueError) as exc_info:
        SpinSpace(0, spin=sympy.Rational(2, 3))
    assert "must be an integer or half-integer" in str(exc_info.value)
    with pytest.raises(ValueError) as exc_info:
        SpinSpace(0, spin="one")
    assert "must be an integer or half-integer" in str(exc_info.value)
    with pytest.raises(ValueError) as exc_info:
        SpinSpace(0, spin=IdxSym('i'))
    assert "must be an integer or half-integer" in str(exc_info.value)
    with pytest.raises(TypeError) as exc_info:
        SpinSpace(0)
    assert "required keyword-only argument: 'spin'" in str(exc_info.value)
def test_braket_indexed_sum():
    """Test braket product of sums"""
    i = IdxSym('i')
    hs = LocalSpace(1, dimension=5)
    alpha = IndexedBase('alpha')

    psi = KetSymbol('Psi', hs=hs)

    psi1 = KetIndexedSum(
        alpha[1, i] * BasisKet(FockIndex(i), hs=hs),
        ranges=IndexOverFockSpace(i, hs),
    )

    psi2 = KetIndexedSum(
        alpha[2, i] * BasisKet(FockIndex(i), hs=hs),
        ranges=IndexOverFockSpace(i, hs),
    )

    expr = Bra.create(psi1) * psi2
    assert expr.space == TrivialSpace
    assert expr == ScalarIndexedSum.create(
        alpha[1, i].conjugate() * alpha[2, i],
        ranges=(IndexOverFockSpace(i, hs), ),
    )
    assert BraKet.create(psi1, psi2) == expr

    expr = psi.dag() * psi2
    assert expr == ScalarIndexedSum(
        alpha[2, i] * BraKet(psi, BasisKet(FockIndex(i), hs=hs)),
        ranges=IndexOverFockSpace(i, hs),
    )
    assert BraKet.create(psi, psi2) == expr

    expr = psi1.dag() * psi
    assert expr == ScalarIndexedSum(
        alpha[1, i].conjugate() * BraKet(BasisKet(FockIndex(i), hs=hs), psi),
        ranges=IndexOverFockSpace(i, hs),
    )
    assert BraKet.create(psi1, psi) == expr