Пример #1
0
def calc_Vsh(A, r_s, sanity_checks=False):
    D = A.shape[2]
    Dm1 = A.shape[1]
    q = A.shape[0]

    R = sp.zeros((D, q, Dm1), dtype=A.dtype, order='C')

    for s in xrange(q):
        R[:, s, :] = r_s.dot(A[s].conj().T)

    R = R.reshape((q * D, Dm1))
    Vconj = ns.nullspace_qr(R.conj().T).T

    if sanity_checks:
        if not sp.allclose(mm.mmul(Vconj.conj(), R), 0):
            log.warning("Sanity Fail in calc_Vsh!: VR != 0")
        if not sp.allclose(mm.mmul(Vconj,
                                   Vconj.conj().T), sp.eye(Vconj.shape[0])):
            log.warning("Sanity Fail in calc_Vsh!: V H(V) != eye")

    Vconj = Vconj.reshape((q * D - Dm1, D, q))

    Vsh = Vconj.T
    Vsh = sp.asarray(Vsh, order='C')

    if sanity_checks:
        Vs = sp.transpose(Vsh, axes=(0, 2, 1)).conj()
        M = eps_r_noop(r_s, Vs, A)
        if not sp.allclose(M, 0):
            log.warning("Sanity Fail in calc_Vsh!: Bad Vsh")

    return Vsh
Пример #2
0
def calc_Vsh(A, r_s, sanity_checks=False):
    D = A.shape[2]
    Dm1 = A.shape[1]
    q = A.shape[0]
    
    R = sp.zeros((D, q, Dm1), dtype=A.dtype, order='C')

    for s in xrange(q):
        R[:,s,:] = r_s.dot(A[s].conj().T)

    R = R.reshape((q * D, Dm1))
    Vconj = ns.nullspace_qr(R.conj().T).T

    if sanity_checks:
        if not sp.allclose(mm.mmul(Vconj.conj(), R), 0):
            log.warning("Sanity Fail in calc_Vsh!: VR != 0")
        if not sp.allclose(mm.mmul(Vconj, Vconj.conj().T), sp.eye(Vconj.shape[0])):
            log.warning("Sanity Fail in calc_Vsh!: V H(V) != eye")
        
    Vconj = Vconj.reshape((q * D - Dm1, D, q))

    Vsh = Vconj.T
    Vsh = sp.asarray(Vsh, order='C')

    if sanity_checks:
        Vs = sp.transpose(Vsh, axes=(0, 2, 1)).conj()
        M = eps_r_noop(r_s, Vs, A)
        if not sp.allclose(M, 0):
            log.warning("Sanity Fail in calc_Vsh!: Bad Vsh")

    return Vsh
Пример #3
0
 def _calc_B_r_diss(self, op, K, C, n, set_eta=True):
     if self.q[n] * self.D[n] - self.D[n - 1] > 0:
         l_sqrt, l_sqrt_inv, r_sqrt, r_sqrt_inv = tm.calc_l_r_roots(self.l[n - 1], 
                                                                self.r[n],
                                                                sanity_checks=self.sanity_checks,
                                                                sc_data=("site", n))
         Vsh = tm.calc_Vsh(self.A[n], r_sqrt, sanity_checks=self.sanity_checks)
         x = self.calc_x(n, Vsh, l_sqrt, r_sqrt, l_sqrt_inv, r_sqrt_inv)
         if set_eta:
             self.eta[n] = sp.sqrt(mm.adot(x, x))
 
         B = sp.empty_like(self.A[n])
         for s in xrange(self.q[n]):
             B[s] = mm.mmul(l_sqrt_inv, x, mm.H(Vsh[s]), r_sqrt_inv)
         return B
     else:
         return None
Пример #4
0
    def _calc_B_r_diss(self, op, K, C, n, set_eta=True):
        if self.q[n] * self.D[n] - self.D[n - 1] > 0:
            l_sqrt, l_sqrt_inv, r_sqrt, r_sqrt_inv = tm.calc_l_r_roots(
                self.l[n - 1],
                self.r[n],
                sanity_checks=self.sanity_checks,
                sc_data=("site", n))
            Vsh = tm.calc_Vsh(self.A[n],
                              r_sqrt,
                              sanity_checks=self.sanity_checks)
            x = self.calc_x(n, Vsh, l_sqrt, r_sqrt, l_sqrt_inv, r_sqrt_inv)
            if set_eta:
                self.eta[n] = sp.sqrt(mm.adot(x, x))

            B = sp.empty_like(self.A[n])
            for s in xrange(self.q[n]):
                B[s] = mm.mmul(l_sqrt_inv, x, mm.H(Vsh[s]), r_sqrt_inv)
            return B
        else:
            return None
Пример #5
0
    def expect_2s_diss(self, op, LC, LK, n, AA=None):
        """Applies a two-site operator to two sites and returns
        the value after the change. In contrast to
        mps_gen.apply_op_2s, this routine does not change the state itself.
        
        Also, this does not perform self.update().
        
        Parameters
        ----------
        op : ndarray or callable
            The two-site operator. See self.expect_2s().
        n: int
            The site to apply the operator to.
            (It's also applied to n-1.)
        """
        #No neighbors, no fun.

        if n is 1:
            return 0
        if n is N:
            return 0

        A = self.A[n - 1]
        Ap1 = self.A[n]
        if AA is None:
            AA = tm.calc_AA(A, Ap1)

        if callable(op):
            op = sp.vectorize(op, otypes=[sp.complex128])
            op = sp.fromfunction(
                op, (A.shape[0], Ap1.shape[0], A.shape[0], Ap1.shape[0]))

        op = op.reshape(4, 4, 4, 4)
        C = tm.calc_C_mat_op_AA(op, AA)
        res = tm.eps_r_op_2s_C12_AA34(self.r[n + 1], LC, AA)
        operand = self.l[n - 1]
        operand = sp.reshape(operand, (1, 16))
        operand = sp.reshape(operand, (2, 8))

        return mm.mmul(operand, res)
        return mm.adot(self.l[n - 1], res)
Пример #6
0
 def expect_2s_diss(self, op, LC, LK, n, AA=None):
     """Applies a two-site operator to two sites and returns
     the value after the change. In contrast to
     mps_gen.apply_op_2s, this routine does not change the state itself.
     
     Also, this does not perform self.update().
     
     Parameters
     ----------
     op : ndarray or callable
         The two-site operator. See self.expect_2s().
     n: int
         The site to apply the operator to.
         (It's also applied to n-1.)
     """
     #No neighbors, no fun.
     
     if n is 1:
         return 0
     if n is N:
         return 0
         
     A = self.A[n-1]
     Ap1 = self.A[n]
     if AA is None:
         AA = tm.calc_AA(A, Ap1)
         
     if callable(op):
         op = sp.vectorize(op, otypes=[sp.complex128])
         op = sp.fromfunction(op, (A.shape[0], Ap1.shape[0], A.shape[0], Ap1.shape[0]))
     
     op = op.reshape(4,4,4,4)
     C = tm.calc_C_mat_op_AA(op, AA)
     res = tm.eps_r_op_2s_C12_AA34(self.r[n + 1], LC, AA)
     operand = self.l[n-1]
     operand = sp.reshape(operand, (1,16))
     operand = sp.reshape(operand, (2,8))
             
     return mm.mmul(operand,res)
     return mm.adot(self.l[n - 1], res)