Example #1
0
    def rdm(
        self,
        string: str,
        brawfn: Optional['Wavefunction'] = None
    ) -> Union[complex, numpy.ndarray]:
        """ Returns rank-1 RDM. The operator order is specified by string.
        Note that, if the entire RDM is requested for N-broken wave function,
        this returns a packed format.

        Args:
            string (str) - character strings that specify the quantity to be computed

            brawfn (Wavefunction) - bra-side wave function for transition RDM (optional)

        Returns:
            Resulting RDM in numpy.ndarray or element in complex
        """
        rank = len(string.split()) // 2
        if any(char.isdigit() for char in string):
            result = self.apply(sparse_hamiltonian.SparseHamiltonian(string))
            if brawfn is None:
                return vdot(self, result)
            return vdot(brawfn, result)

        fqe_ops_utils.validate_rdm_string(string)
        rdm = list(self._compute_rdm(rank, brawfn))
        return wick(string, rdm, self._conserve_spin)
Example #2
0
    def expectationValue(
            self,
            ops: Union['fqe_operator.FqeOperator', 'hamiltonian.Hamiltonian'],
            brawfn: 'Wavefunction' = None) -> Union[complex, numpy.ndarray]:
        """Calculates expectation values given operators

        Args:
            ops (FqeOperator or Hamiltonian) - operator for which the expectation value is \
                computed

            brawfn (Wavefunction) - bra-side wave function for transition quantity (optional)

        Returns:
            (complex or numpy.ndarray) - resulting expectation value or RDM
        """
        if isinstance(ops, fqe_operator.FqeOperator):
            if brawfn:
                return ops.contract(brawfn, self)
            return ops.contract(self, self)

        if isinstance(ops, str):
            if any(char.isdigit() for char in ops):
                ops = sparse_hamiltonian.SparseHamiltonian(ops)
            else:
                return self.rdm(ops, brawfn=brawfn)

        if not isinstance(ops, hamiltonian.Hamiltonian):
            raise TypeError('Expected an Fqe Hamiltonian or Operator' \
                            ' but recieved {}'.format(type(ops)))
        workwfn = self.apply(ops)

        if brawfn:
            return vdot(brawfn, workwfn)
        return vdot(self, workwfn)
Example #3
0
    def contract(self, brastate: "Wavefunction",
                 ketstate: "Wavefunction") -> complex:
        """Given two wavefunctions, generate the expectation value of the
        operator according to its representation.

        Args:
            brastate: Wavefunction on the bra side.
            ketstate: Wavefunction on the ket side.
        """
        out = copy.deepcopy(ketstate)
        for (nele, nab), sector in out._civec.items():
            nalpha, nbeta = alpha_beta_electrons(nele, nab)
            if nalpha < nbeta:
                if not (nele, nbeta - nalpha) in out._civec.keys():
                    raise ValueError(
                        "The wavefunction space is not closed under "
                        "time reversal.")
                sector2 = out._civec[(nele, nbeta - nalpha)]
                tmp = np.copy(sector.coeff)
                phase = (-1)**(nbeta * (nalpha + 1))
                phase2 = (-1)**(nalpha * (nbeta + 1))
                sector.coeff = sector2.coeff.T.conj() * phase2
                sector2.coeff = tmp.T.conj() * phase
            elif nalpha > nbeta:
                if not (nele, nbeta - nalpha) in out._civec.keys():
                    raise ValueError(
                        "The wavefunction space is not closed under "
                        "time reversal.")
            elif nalpha == nbeta:
                sector.coeff = sector.coeff.T.conj()
        return vdot(brastate, out)
Example #4
0
    def contract(self, brastate: "Wavefunction",
                 ketstate: "Wavefunction") -> complex:
        """Given two wavefunctions, generate the expectation value of the
        operator according to its representation.

        Args:
            brastate: Wavefunction on the bra side.
            ketstate: Wavefunction on the ket side.
        """
        out = copy.deepcopy(ketstate)
        for _, sector in out._civec.items():
            sector.scale((sector.nalpha() - sector.nbeta()) * 0.5)
        return vdot(brastate, out)
Example #5
0
def vdot(wfn1: 'wavefunction.Wavefunction',
         wfn2: 'wavefunction.Wavefunction') -> complex:
    """Calculate the inner product of two wavefunctions using conjugation on
    the elements of wfn1.

    Args:
        wfn1 (wavefunction.Wavefunction) - wavefunction corresponding to the \
            conjugate row vector

        wfn2 (wavefunction.Wavefunction) - wavefunction corresponding to the \
            coumn vector

    Returns:
        (complex) - scalar as result of the dot product
    """
    return util.vdot(wfn1, wfn2)