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
def pm_nextxms(xms,ds,gms,Fms,t0=None): ''' Calculate next geometry using page-mciver method If fail in calculating t parameter, quadratic Taylor expasion is used. ''' tmethod = "quad" # ("quad" or "trap") natoms = fncs.howmanyatoms(xms) # to numpy arrays if xms is not None: xms = np.matrix(np.array([xms]).transpose()) if gms is not None: gms = np.matrix(np.array([gms]).transpose()) if Fms is not None: Fms = np.matrix(np.array(Fms)) # Get Hessian eigenvalues and eigenvectors alpha, U = np.linalg.eigh(Fms) # Get projection of gradient gp = U.transpose() * gms # Put eigenvectors in diagonal matrix alpha = np.diag(alpha) # check dimensions if gms.shape != (3*natoms, 1): exit("Problems in 'pm_nextxms'") if gp.shape != (3*natoms, 1): exit("Problems in 'pm_nextxms'") if U.shape != (3*natoms,3*natoms): exit("Problems in 'pm_nextxms'") # get t if t0 is None: t = pm_gett(ds,gp,alpha,tmethod) else : t = t0 # apply taylor? if t is None: xms = np.array(xms.transpose().tolist()[0]) gms = np.array(gms.transpose().tolist()[0]) Fms = np.array(Fms.tolist() ) return sd_taylor(xms,ds,gms,Fms), None # Get Mn matrix M = np.identity(3*natoms) for i in range(3*natoms): M[i,i] = (fncs.exp128(- alpha[i,i] * t) - 1.0) / alpha[i,i] # Get D(t) D = U * M * U.transpose() # Get dx vector dx_vector = D * gms # to normal array xms = np.array( xms.transpose().tolist()[0]) dx_vector = np.array(dx_vector.transpose().tolist()[0]) # Get new geom xms_next = xms + dx_vector return xms_next, t
def puckering_coords(xvec,atoms_in_ring=None): ''' Generalized Ring-Puckering Coordinates JACS 1975, 97:6, 1354-1358; eqs (12)-(14) ''' nat = fncs.howmanyatoms(xvec) if atoms_in_ring is None: atoms_in_ring = range(nat) list_Rj, gc = puckering_rjs(xvec,atoms_in_ring) normal = puckering_normal(list_Rj) list_zj = puckering_zjs(list_Rj,normal) N = len(list_zj) if N%2 != 0: mmax = (N-1)//2 else : mmax = N//2 -1 list_qm = [] list_phim = [] for m in range(2,mmax+1,1): qcos = 0.0 qsin = 0.0 for j in range(N): zj = list_zj[j] qcos += zj*np.cos(2*np.pi*m*j/N) qsin += zj*np.sin(2*np.pi*m*j/N) qcos *= +np.sqrt(2.0/N) qsin *= -np.sqrt(2.0/N) # Get q_m and phi_m phi_m = fncs.sincos2angle(qsin,qcos) q_m = qcos / np.cos(phi_m) list_qm.append(q_m) list_phim.append(phi_m) if N%2 == 0: qNhalf = 0.0 for j in range(N): zj = list_zj[j] qNhalf += ((-1)**j) * zj qNhalf *= np.sqrt(1.0/N) list_qm.append(qNhalf) # total puckering amplitude Q = np.sqrt(sum([zj**2 for zj in list_zj])) return list_qm, list_phim, Q