コード例 #1
0
def calculate_v1(xms,
                 v0,
                 Fms,
                 symbols,
                 masses,
                 mu,
                 d3,
                 spc_fnc,
                 spc_args,
                 parallel=False):
    natoms = fncs.howmanyatoms(xms)
    # Calculation of hessian at close structures
    xbw_3rd = fncs.ms2cc_x(sd_taylor(xms, d3, v0=-v0), masses, mu)
    xfw_3rd = fncs.ms2cc_x(sd_taylor(xms, d3, v0=+v0), masses, mu)
    t3rd_bw = (xbw_3rd, symbols, True, "thirdBw", spc_args)
    t3rd_fw = (xfw_3rd, symbols, True, "thirdFw", spc_args)
    # calculation with software
    if fncs.do_parallel(parallel):
        import multiprocessing
        pool = multiprocessing.Pool()
        out = [
            pool.apply_async(spc_fnc, args=args)
            for args in [t3rd_bw, t3rd_fw]
        ]
        #outbw, outfw = Parallel(n_jobs=-1)(delayed(spc_fnc)(*inp) for inp in [t3rd_bw,t3rd_fw])
        outbw = out[0].get()
        outfw = out[1].get()
        # clean up pool
        pool.close()
        pool.join()
    else:
        outbw = spc_fnc(*t3rd_bw)
        outfw = spc_fnc(*t3rd_fw)
    xcc_bw, atnums, ch, mtp, V0_bw, gcc_bw, Fcc_bw, dummy = outbw
    xcc_fw, atnums, ch, mtp, V0_fw, gcc_fw, Fcc_fw, dummy = outfw
    # In mass-scaled
    Fms_bw = fncs.cc2ms_F(fncs.lowt2matrix(Fcc_bw), masses, mu)
    Fms_fw = fncs.cc2ms_F(fncs.lowt2matrix(Fcc_fw), masses, mu)
    # Convert numpy matrices
    Fms = np.matrix(Fms)
    Fms_bw = np.matrix(Fms_bw)
    Fms_fw = np.matrix(Fms_fw)
    # Matriz of third derivatives
    m3der = (Fms_fw - Fms_bw) / (2.0 * d3)
    # Calculation of curvature, i.e. v^(1) (or small c)  A = B * c --> c = B^-1 * A
    LF = np.matrix([v0]).transpose()
    A = m3der * LF - float(LF.transpose() * m3der * LF) * LF
    B = 2.0 * float(LF.transpose() * Fms * LF) * np.identity(3 * natoms) - Fms
    v1 = np.linalg.inv(B) * A
    # Convert to (normal) array
    v1 = np.array(v1.transpose().tolist()[0])
    return v1
コード例 #2
0
def mep_first(xcc,
              gcc,
              Fcc,
              symbols,
              masses,
              var_first,
              spc_fnc,
              spc_args,
              drst={},
              parallel=False):

    #global PARALLEL, delayed, multiprocessing, Parallel
    #PARALLEL, delayed, multiprocessing, Parallel = fncs.set_parallel(parallel)
    ds, mu, cubic, idir = var_first

    # convert cubic variable to d3 (in bohr)
    d3 = cubic2float(cubic)

    # mass-scaled
    xcc = fncs.shift2com(xcc, masses)
    xms = fncs.cc2ms_x(xcc, masses, mu)
    gms = fncs.cc2ms_g(gcc, masses, mu)
    Fms = fncs.cc2ms_F(Fcc, masses, mu)

    # Data in backup?
    if TSLABEL in drst.keys():
        si, E, xms2, gms, Fms, v0, v1, t = drst[TSLABEL]
        gms = np.array(gms)
        Fms = np.array(Fms)
        v0 = np.array(v0)
        if v1 is not None: v1 = np.array(v1)
        same = fncs.same_geom(xms, xms2)
        if not same: raise Exc.RstDiffTS(Exception)
    else:
        # Calculation of v0
        freqs, evals, evecs = fncs.calc_ccfreqs(Fcc, masses, xcc)
        ifreq, Lms = get_imagfreq(freqs, evecs)
        v0 = fncs.normalize_vec(Lms)
        v0 = correctdir_v0(xms, v0, idir, masses, mu)

        # Calculation of v1
        if d3 is None: v1 = None
        else:
            v1 = calculate_v1(xms, v0, Fms, symbols, masses, mu, d3, spc_fnc,
                              spc_args, parallel)
    # Final structures
    if d3 is None:
        xms_bw = sd_taylor(xms, ds, v0=-v0)
        xms_fw = sd_taylor(xms, ds, v0=+v0)
    else:
        xms_bw = sd_taylor(xms, ds, v0=-v0, v1=-v1)
        xms_fw = sd_taylor(xms, ds, v0=+v0, v1=+v1)

    return (xms, gms, Fms), (v0, v1), (xms_bw, xms_fw)
コード例 #3
0
ファイル: Molecule.py プロジェクト: cathedralpkg/Pilgrim
    def setup(self, mu=1.0 / AMU, projgrad=False):
        self._mu = mu
        # derivated magnitudes (again, in case sth was modified)
        # for example, when set from gts and masses are added latter
        self.genderivates()
        # shift to center of mass and reorientate molecule
        idata = (self._xcc, self._gcc, self._Fcc, self._masses)
        self._xcc, self._gcc, self._Fcc = fncs.center_and_orient(*idata)
        # symmetry
        self.calc_pgroup(force=False)
        # Generate mass-scaled arrays
        self._xms = fncs.cc2ms_x(self._xcc, self._masses, self._mu)
        self._gms = fncs.cc2ms_g(self._gcc, self._masses, self._mu)
        self._Fms = fncs.cc2ms_F(self._Fcc, self._masses, self._mu)
        #-------------#
        # Atomic case #
        #-------------#
        if self._natoms == 1:
            self._nvdof = 0
            self._linear = False
            #self._xms      = list(self._xcc)
            #self._gms      = list(self._gcc)
            #self._Fms      = list(self._Fcc)
            self._ccfreqs = []
            self._ccFevals = []
            self._ccFevecs = []
        #----------------#
        # Molecular case #
        #----------------#
        else:
            # Calculate inertia
            self._itensor = fncs.get_itensor_matrix(self._xcc, self._masses)
            self._imoms, self._rotTs, self._rtype, self._linear = \
                    fncs.get_itensor_evals(self._itensor)
            # Vibrational degrees of freedom
            if self._linear: self._nvdof = 3 * self._natoms - 5
            else: self._nvdof = 3 * self._natoms - 6
            # calculate frequencies
            if self._Fcc is None: return
            if len(self._Fcc) == 0: return
            if self._ccfreqs is not None: return

            v0 = self._gms if projgrad else None
            data = fncs.calc_ccfreqs(self._Fcc,
                                     self._masses,
                                     self._xcc,
                                     self._mu,
                                     v0=v0)
            self._ccfreqs, self._ccFevals, self._ccFevecs = data
            # Scale frequencies
            self._ccfreqs = fncs.scale_freqs(self._ccfreqs, self._fscal)
コード例 #4
0
def steepest(xcc0,s0,symbols,masses,pathdata,spc_fnc,spc_args,drst={},lFms=None,pf="%i"):
    '''
    x0 should not be a saddle point
    pathdata: tuple made of:
        * method
          pm for Page-McIver
          es for Euler
        * mu
        * ds
        * nsteps
        * hsteps
        * epse
        * epsg
    pf: point format
    '''
    # expand pathdata
    method,mu,ds,sfinal,hsteps,epse,epsg = pathdata
    nsteps = int(round(abs(sfinal/ds)))
    # Check some staff
    if lFms is None and method == "pm": raise Exc.SDpmNoHess(Exception)
    # loop
    s_i   = s0
    xcc_i = xcc0
    listE = []
    listg = []
    for step in range(1,nsteps+1):
        point = pf%step
        # calculate hessian?
        if step%hsteps == 0: bhessian = True
        else               : bhessian = False
        # previously calculated vs single-point calculation
        if point in drst.keys():
            s_ii, E_i, xms_i, gms_i, Fms_i, v0, v1, t_i = drst[point]
            # in cc
            gcc_i = fncs.ms2cc_g(gms_i,masses,mu)
            # compare geometry
            exception = Exc.RstDiffPoint(Exception)
            exception._var = (point,s_i)
            if abs(s_ii-s_i) > EPS_MEPS: raise exception
            same = fncs.same_geom(fncs.cc2ms_x(xcc_i,masses,mu),xms_i)
            if not same: raise exception
        else:
            spc_data = spc_fnc(xcc_i,symbols,bhessian,point,spc_args)
            xcc_i, atnums, ch, mtp, E_i, gcc_i, Fcc_i, dummy = spc_data
            # Data in mass-scaled and correct format
            Fcc_i = fncs.lowt2matrix(Fcc_i)
            xms_i = fncs.cc2ms_x(xcc_i,masses,mu)
            gms_i = fncs.cc2ms_g(gcc_i,masses,mu)
            Fms_i = fncs.cc2ms_F(Fcc_i,masses,mu)
            t_i   = None
        # keep data for eps
        listE.append(E_i)
        listg.append(fncs.norm(gcc_i))
        # Last Fms
        if Fms_i not in [[],None]: lFms = Fms_i
        # Calculate new geometry (step+1)
        if   method == "es":
           xms_j, t_i = sd_taylor(xms_i,ds,gms=gms_i), None # to check format
        elif method == "pm":
           xms_j, t_i = pm_nextxms(xms_i,ds,gms=gms_i,Fms=lFms,t0=t_i)
        # check real ds value
        diff_ds2 = sum([(ii-jj)**2 for (ii,jj) in zip(xms_j,xms_i)]) - ds**2
        if diff_ds2 > EPS_FLOAT: raise Exc.SDdiffds(Exception)
        # Yield updated data for step
        yield (point,s_i), E_i, xms_i, gms_i, Fms_i, t_i
        # update
        xcc_i = fncs.ms2cc_x(xms_j,masses,mu)
        if   s_i >= 0.0: s_i += ds
        else           : s_i -= ds
        # Check eps
        if len(listE) > 2 and step > 2*hsteps:
            diffE = abs(listE[-1]-listE[-2])
            #diffg = abs(listg[-1]-listg[-2])
            crit1 = diffE     < epse
            crit2 = listg[-1] < epsg
            if crit1 and crit2: break