def build_dfmp2(e, qpx, qyz, chempot=0.0, **kwargs): ''' Builds a set of auxiliaries representing all (i,j,a) and (a,b,i) diagrams. Output is controlled by input dimensions: If e is (n,) and qpx (q,n,m): restricted, return single `Aux` If e is (2,n) and qpx (2,q,n,m): unrestricted, return both `Aux` Parameters ---------- See either auxgf.aux.build_rmp2.build_rmp2 or auxgf.aux.build_ump2.build_ump2 Returns ------- poles : Aux auxiliaries ''' ndim = util.iter_depth(e) if ndim == 1: return build_dfrmp2(e, qpx, qyz, chempot=chempot, **kwargs) elif ndim == 2: a = build_dfump2(e, qpx, qyz, chempot=chempot, **kwargs) b = build_dfump2(e[::-1], qpx[::-1], qyz[::-1], chempot=chempot[::-1], **kwargs) return a, b else: raise ValueError
def build_mp2_iter(se, h_phys, eri_mo, **kwargs): ''' Builds a set of auxiliaries representing all (i,j,a) and (a,b,i) diagrams by iterating the current set of auxiliaries according to the eigenvalue form of the Dyson equation. Parameters ---------- se : Aux auxiliaries of previous iteration eri_mo : (n,n,n,n) ndarray two-electron repulsion integrals in MO basis wtol : float, optional threshold for an eigenvalue to be considered zero ss_factor : float, optional same spin factor, default 1.0 os_factor : float, optional opposite spin factor, default 1.0 Returns ------- poles : Aux auxiliaries ''' ndim = util.iter_depth(se) if ndim == 0: return build_rmp2_iter(se, h_phys, eri_mo, **kwargs) elif ndim == 1: return build_ump2_iter(se, h_phys, eri_mo, **kwargs) else: raise ValueError
def build_mp2_part(eo, ev, xija, **kwargs): ''' Builds a set of auxiliaries representing all (i,j,a) or (a,b,i) diagrams. Parameters ---------- See either auxgf.aux.build_rmp2.build_rmp2_part or auxgf.aux.build_ump2.build_ump2_part Returns ------- e : (m) ndarray auxiliary energies v : (n,m) ndarray auxiliary couplings ''' ndim = util.iter_depth(eo) if ndim == 1: return build_rmp2_part(eo, ev, xija, **kwargs) elif ndim == 2: return build_ump2_part(eo, ev, xija, **kwargs) else: raise ValueError
def energy_mp2_aux(mo, se, both_sides=False): ''' Calculates the two-body contribution to the electronic energy using the MOs and the auxiliary representation of the self-energy according the the MP2 form of the Galitskii-Migdal formula. Parameters ---------- mo : (n) ndarray MO energies se : Aux auxiliary representation of self-energy both_sides : bool, optional if True, calculate both halves of the functional and return the mean, default False Returns ------- e2b : float two-body contribution to electronic energy ''' if isinstance(se, (tuple, list)): n = len(se) if util.iter_depth(mo) == 2: return sum([ energy_mp2_aux(mo[i], se[i], both_sides=both_sides) for i in range(n) ]) / n else: return sum([ energy_mp2_aux(mo, se[i], both_sides=both_sides) for i in range(n) ]) / n nphys = se.nphys occ = mo < se.chempot vir = mo >= se.chempot vxk = se.v_vir[occ] dxk = 1.0 / util.outer_sum([mo[occ], -se.e_vir]) e2b = util.einsum('xk,xk,xk->', vxk, vxk.conj(), dxk) if both_sides: vxk = se.v_occ[vir] dxk = -1.0 / util.outer_sum([mo[vir], -se.e_occ]) e2b += util.einsum('xk,xk,xk->', vxk, vxk.conj(), dxk) e2b *= 0.5 return np.ravel(e2b.real)[0]