def newton(mf): '''augmented hessian for Newton Raphson Examples: >>> mol = gto.M(atom='H 0 0 0; H 0 0 1.1', basis='cc-pvdz') >>> mf = scf.RHF(mol).run(conv_tol=.5) >>> mf = scf.newton(mf).set(conv_tol=1e-9) >>> mf.kernel() -1.0811707843774987 ''' return newton_ah.newton(mf)
def newton(mf): from pyscf.scf import newton_ah from pyscf.pbc import scf as pscf if not isinstance(mf, (pscf.khf.KRHF, pscf.kuhf.KUHF)): # Note for single k-point other than gamma point (mf.kpt != 0) mf object, # orbital hessian is approximated by gamma point hessian. return newton_ah.newton(mf) KSCF = newton_ah.newton_SCF_class(mf) if isinstance(mf, pscf.kuhf.KUHF): class KUHF(KSCF): def build(self, cell=None): KSCF.build(self, cell) gen_g_hop = gen_g_hop_uhf def update_rotate_matrix(self, dx, mo_occ, u0=1): nkpts = len(mo_occ[0]) p0 = 0 u = [] for occ in mo_occ: ua = [] for k in range(nkpts): occidx = occ[k] > 0 viridx = ~occidx nocc = occidx.sum() nvir = viridx.sum() nmo = nocc + nvir dr = numpy.zeros((nmo, nmo), dtype=dx.dtype) dr[viridx[:, None] & occidx] = dx[p0:p0 + nocc * nvir] dr = dr - dr.T.conj() p0 += nocc * nvir u1 = newton_ah.expmat(dr) if isinstance(u0, int) and u0 == 1: ua.append(u1) else: ua.append(numpy.dot(u0[k], u1)) u.append(ua) return lib.asarray(u) def rotate_mo(self, mo_coeff, u, log=None): mo = ([ numpy.dot(mo, u[0][k]) for k, mo in enumerate(mo_coeff[0]) ], [ numpy.dot(mo, u[1][k]) for k, mo in enumerate(mo_coeff[1]) ]) return lib.asarray(mo) return KUHF() else: class KRHF(KSCF): def build(self, cell=None): KSCF.build(self, cell) gen_g_hop = gen_g_hop_rhf def update_rotate_matrix(self, dx, mo_occ, u0=1): p0 = 0 u = [] for k, occ in enumerate(mo_occ): occidx = occ > 0 viridx = ~occidx nocc = occidx.sum() nvir = viridx.sum() nmo = nocc + nvir dr = numpy.zeros((nmo, nmo), dtype=dx.dtype) dr[viridx[:, None] & occidx] = dx[p0:p0 + nocc * nvir] dr = dr - dr.T.conj() p0 += nocc * nvir u1 = newton_ah.expmat(dr) if isinstance(u0, int) and u0 == 1: u.append(u1) else: u.append(numpy.dot(u0[k], u1)) return lib.asarray(u) def rotate_mo(self, mo_coeff, u, log=None): return lib.asarray( [numpy.dot(mo, u[k]) for k, mo in enumerate(mo_coeff)]) return KRHF()
def newton(mf): '''augmented hessian for Newton Raphson''' return newton_ah.newton(mf)