def step(self, step=None): """ Does one simulation time step.""" activearrays = self.prestep(step) e, g = self.fm(self.beads.q) fdf0 = (e, g) # Do one step. Update the position and force inside the mapper. L_BFGS(activearrays["old_x"], activearrays["d"], self.fm, activearrays["qlist"], activearrays["glist"], fdf0, activearrays["big_step"], self.options["ls_options"]["tolerance"] * self.options["tolerances"]["energy"], self.options["ls_options"]["iter"], self.options["corrections"], self.options["scale"], step) # Update self.optarrays["qlist"][:] = self.fix.get_full_vector(activearrays["qlist"], t=3) self.optarrays["glist"][:] = self.fix.get_full_vector(activearrays["glist"], t=3) self.optarrays["d"][:] = self.fix.get_full_vector(activearrays["d"], t=1) self.update_pos_for() # Print self.print_geo(step) # Check Exit and only then update old arrays d_x_max = np.amax(np.absolute(np.subtract(self.beads.q, self.optarrays["old_x"]))) self.exit = self.exitstep(d_x_max, step) self.update_old_pos_for() # Print current instanton geometry and hessian if (self.save > 0 and np.mod(step, self.save) == 0) or self.exit: print_instanton_geo(self.options["prefix"], step, self.im.dbeads.nbeads, self.im.dbeads.natoms, self.im.dbeads.names, self.im.dbeads.q, self.old_u, self.cell, self.optarrays["energy_shift"], self.output_maker)
def exitstep(self, fx, fx0, x, exitt, step): """ Exits the simulation step. Computes time, checks for convergence. """ self.qtime += time.time() #f = open('STEP', 'a+') #print >>f, 'STEP %i' % step #print >>f, 'Energy difference: %.1e, (condition: %.1e)' % (np.absolute((fx - fx0) / self.beads.natoms), self.tolerances["energy"] ) #print >>f, 'Maximum force component: %.1e, (condition: %.1e)' % (np.amax(np.absolute(self.forces.f+self.im.f)), self.tolerances["force"]) #print >>f, 'Maximum component step component: %.1e, (condition: %.1e)' % (x, self.tolerances["position"]) #print >>f, ' ' #f.close() info( ' @Exit step: Energy difference: %.1e, (condition: %.1e)' % (np.absolute( (fx - fx0) / self.beads.natoms), self.tolerances["energy"]), verbosity.low) info( ' @Exit step: Maximum force component: %.1e, (condition: %.1e)' % (np.amax(np.absolute(self.forces.f + self.im.f)), self.tolerances["force"]), verbosity.low) info( ' @Exit step: Maximum component step component: %.1e, (condition: %.1e)' % (x, self.tolerances["position"]), verbosity.low) if (np.absolute((fx - fx0) / self.beads.natoms) <= self.tolerances["energy"]) \ and ((np.amax(np.absolute(self.forces.f + self.im.f)) <= self.tolerances["force"]) or (np.linalg.norm(self.forces.f.flatten() - self.old_f.flatten()) <= 1e-08)) \ and (x <= self.tolerances["position"]): print_instanton_geo(self.prefix + '_FINAL', step, self.im.dbeads.nbeads, self.im.dbeads.natoms, self.im.dbeads.names, self.im.dbeads.q, self.old_u, self.cell, self.energy_shift) if self.hessian_final != 'true': info("We are not going to compute the final hessian.", verbosity.low) info( "Warning, The current hessian is not the real hessian is only an approximation .", verbosity.low) else: info("We are going to compute the final hessian", verbosity.low) get_hessian(self.hessian, self.gm, self.im.dbeads.q) print_instanton_hess(self.prefix + '_FINAL', step, self.hessian) exitt = True #If we just exit here, the last step (including the last hessian) will not be in the RESTART file return exitt
def exitstep(self, d_x_max, step): """ Exits the simulation step. Computes time, checks for convergence. """ self.qtime += time.time() tolerances = self.options["tolerances"] d_u = self.forces.pot - self.optarrays["old_u"].sum() active_force = self.fix.get_active_vector(self.forces.f, 1) + self.im.f fff = self.fix.get_active_vector(self.forces.f, 1) * (self.im.coef[1:] + self.im.coef[:-1]) / 2 active_force = fff + self.im.f info(' @Exit step: Energy difference: {:4.2e}, (condition: {:4.2e})'.format( np.absolute(d_u / self.im.dbeads.natoms), tolerances["energy"]), verbosity.low) info(' @Exit step: Maximum force component: {:4.2e}, (condition: {:4.2e})'.format( np.amax(np.absolute(active_force)), tolerances["force"]), verbosity.low) info(' @Exit step: Maximum component step component: {:4.2e}, (condition: {:4.2e})'.format( d_x_max, tolerances["position"]), verbosity.low) if (np.absolute(d_u / self.im.dbeads.natoms) <= tolerances["energy"]) \ and ((np.amax(np.absolute(active_force)) <= tolerances["force"]) or (np.linalg.norm(self.forces.f.flatten() - self.optarrays["old_f"].flatten()) <= 1e-08)) \ and (d_x_max <= tolerances["position"]): print_instanton_geo(self.options["prefix"] + '_FINAL', step, self.beads.nbeads, self.beads.natoms, self.beads.names, self.beads.q, self.forces.f, self.forces.pots, self.cell, self.optarrays["energy_shift"], self.output_maker) if self.options["hessian_final"] != 'true': info("We are not going to compute the final hessian.", verbosity.low) info("Warning, The current hessian is not the real hessian is only an approximation .", verbosity.low) else: info("We are going to compute the final hessian", verbosity.low) active_hessian = get_hessian(self.gm, self.beads.q.copy(), self.beads.natoms, self.beads.nbeads, self.fixatoms) self.optarrays["hessian"][:] = self.fix.get_full_vector(active_hessian, 2) print_instanton_hess(self.options["prefix"] + '_FINAL', step, self.optarrays["hessian"], self.output_maker) return True # If we just exit here, the last step (including the last hessian) will not be in the RESTART file return False
def exitstep(self, fx, fx0, x, exitt, step): """ Exits the simulation step. Computes time, checks for convergence. """ self.qtime += time.time() #f = open('STEP', 'a+') #print >>f, 'STEP %i' % step #print >>f, 'Energy difference: %.1e, (condition: %.1e)' % (np.absolute((fx - fx0) / self.beads.natoms), self.tolerances["energy"] ) #print >>f, 'Maximum force component: %.1e, (condition: %.1e)' % (np.amax(np.absolute(self.forces.f+self.im.f)), self.tolerances["force"]) #print >>f, 'Maximum component step component: %.1e, (condition: %.1e)' % (x, self.tolerances["position"]) #print >>f, ' ' # f.close() info(' @Exit step: Energy difference: %.1e, (condition: %.1e)' % (np.absolute((fx - fx0) / self.beads.natoms), self.tolerances["energy"]), verbosity.low) info(' @Exit step: Maximum force component: %.1e, (condition: %.1e)' % (np.amax(np.absolute(self.forces.f + self.im.f)), self.tolerances["force"]), verbosity.low) info(' @Exit step: Maximum component step component: %.1e, (condition: %.1e)' % (x, self.tolerances["position"]), verbosity.low) if (np.absolute((fx - fx0) / self.beads.natoms) <= self.tolerances["energy"]) \ and ((np.amax(np.absolute(self.forces.f + self.im.f)) <= self.tolerances["force"]) or (np.linalg.norm(self.forces.f.flatten() - self.old_f.flatten()) <= 1e-08)) \ and (x <= self.tolerances["position"]): print_instanton_geo(self.prefix + '_FINAL', step, self.im.dbeads.nbeads, self.im.dbeads.natoms, self.im.dbeads.names, self.im.dbeads.q, self.old_u, self.cell, self.energy_shift, self.output_maker) if self.hessian_final != 'true': info("We are not going to compute the final hessian.", verbosity.low) info("Warning, The current hessian is not the real hessian is only an approximation .", verbosity.low) else: info("We are going to compute the final hessian", verbosity.low) get_hessian(self.hessian, self.gm, self.im.dbeads.q, self.output_maker) print_instanton_hess(self.prefix + '_FINAL', step, self.hessian, self.output_maker) exitt = True # If we just exit here, the last step (including the last hessian) will not be in the RESTART file return exitt
def step(self, step=None): """ Does one simulation time step.""" self.qtime = -time.time() info("\n Instanton optimization STEP %d" % step, verbosity.low) if step == 0: info(" @GEOP: Initializing INSTANTON", verbosity.low) if self.beads.nbeads == 1: raise ValueError( "We can not perform an splitting calculation with nbeads =1" ) # get_hessian(self.hessian, self.gm, self.beads.q) else: if ((self.beads.q - self.beads.q[0]) == 0).all( ): # If the coordinates in all the imaginary time slices are the same info( " @GEOP: We stretch the initial geometry with an 'amplitud' of %4.2f" % self.delta, verbosity.low) imvector = get_imvector(self.initial_hessian, self.beads.m3[0].flatten()) for i in range(self.beads.nbeads): self.beads.q[i, :] += self.delta * np.cos( i * np.pi / float(self.beads.nbeads - 1)) * imvector[:] else: info( " @GEOP: Starting from the provided geometry in the extended phase space", verbosity.low) # Update positions and forces self.old_x[:] = self.beads.q self.old_u[:] = self.forces.pots self.old_f[:] = self.forces.f # This must be done after the stretching and before the self.d. if type(self.im.f) == type(None): self.im(self.beads.q, ret=False) # Init instanton mapper # Specific for LBFGS if np.linalg.norm(self.d) == 0.0: f = self.forces.f + self.im.f #ALBERTO1 self.d += dstrip(f) / np.sqrt(np.dot(f.flatten(), f.flatten())) if (self.old_x == np.zeros((self.beads.nbeads, 3 * self.beads.natoms), float)).all(): self.old_x[:] = self.beads.q if self.exit: softexit.trigger( "Geometry optimization converged. Exiting simulation") if len(self.fixatoms) > 0: for dqb in self.old_f: dqb[self.fixatoms * 3] = 0.0 dqb[self.fixatoms * 3 + 1] = 0.0 dqb[self.fixatoms * 3 + 2] = 0.0 e, g = self.fm(self.beads.q) fdf0 = (e, g) # Do one step. Update hessian for the new position. Update the position and force inside the mapper. L_BFGS(self.old_x, self.d, self.fm, self.qlist, self.glist, fdf0, self.big_step, self.ls_options["tolerance"] * self.tolerances["energy"], self.ls_options["iter"], self.corrections, self.scale, step) # ALBERTO2 # Update positions and forces self.beads.q = self.gm.dbeads.q self.forces.transfer_forces( self.gm.dforces) # This forces the update of the forces # Exit simulation step d_x_max = np.amax(np.absolute(np.subtract(self.beads.q, self.old_x))) self.exit = self.exitstep(self.forces.pot, self.old_u.sum(), d_x_max, self.exit, step) # Update positions and forces self.old_x[:] = self.beads.q self.old_u[:] = self.forces.pots self.old_f[:] = self.forces.f # Print current instanton geometry and hessian if (self.save > 0 and np.mod(step, self.save) == 0) or self.exit: print_instanton_geo(self.prefix, step, self.im.dbeads.nbeads, self.im.dbeads.natoms, self.im.dbeads.names, self.im.dbeads.q, self.old_u, self.cell, self.energy_shift)
def step(self, step=None): """ Does one simulation time step.""" self.qtime = -time.time() info("\n Instanton optimization STEP %d" % step, verbosity.low) if step == 0: info(" @GEOP: Initializing INSTANTON", verbosity.low) if self.beads.nbeads == 1: info(" @GEOP: Classical TS search", verbosity.low) if self.hessian_init == 'true': get_hessian(self.hessian, self.gm, self.beads.q) else: if ((self.beads.q - self.beads.q[0]) == 0).all( ): # If the coordinates in all the imaginary time slices are the same info( " @GEOP: We stretch the initial geometry with an 'amplitud' of %4.2f" % self.delta, verbosity.low) imvector = get_imvector(self.initial_hessian, self.beads.m3[0].flatten()) for i in range(self.beads.nbeads): self.beads.q[i, :] += self.delta * np.cos( i * np.pi / float(self.beads.nbeads - 1)) * imvector[:] if self.hessian_init != 'true': info( " @GEOP: Hessian_init isn't true but we have stretched the polymer so we are going to compute the initial hessian anyway.", verbosity.low) self.hessian_init = 'true' else: info( " @GEOP: Starting from the provided geometry in the extended phase space", verbosity.low) if not (self.initial_hessian is None): raise ValueError( " You have to provided a hessian with size (3xnatoms)^2 but also geometry in the extended phase space (nbeads>1). Please check the inputs\n" ) if self.hessian_init == 'true': info(" @GEOP: We are computing the initial hessian", verbosity.low) get_hessian(self.hessian, self.gm, self.beads.q) # Update positions and forces self.old_x[:] = self.beads.q self.old_u[:] = self.forces.pots self.old_f[:] = self.forces.f if type(self.im.f) == type(None): self.im(self.beads.q, ret=False) #Init instanton mapper if (self.old_x == np.zeros((self.beads.nbeads, 3 * self.beads.natoms), float)).all(): self.old_x[:] = self.beads.q if self.exit: softexit.trigger( "Geometry optimization converged. Exiting simulation") if len(self.fixatoms) > 0: for dqb in self.old_f: dqb[self.fixatoms * 3] = 0.0 dqb[self.fixatoms * 3 + 1] = 0.0 dqb[self.fixatoms * 3 + 2] = 0.0 # Do one step. Update hessian for the new position. Update the position and force inside the mapper. Instanton(self.old_x, self.old_f, self.im.f, self.hessian, self.hessian_update, self.hessian_asr, self.im, self.gm, self.big_step, self.opt, self.mode) # Update positions and forces self.beads.q = self.gm.dbeads.q self.forces.transfer_forces( self.gm.dforces) # This forces the update of the forces # Print current instanton geometry and hessian if (self.save > 0 and np.mod(step, self.save) == 0) or self.exit: print_instanton_geo(self.prefix, step, self.im.dbeads.nbeads, self.im.dbeads.natoms, self.im.dbeads.names, self.im.dbeads.q, self.old_u, self.cell, self.energy_shift) print_instanton_hess(self.prefix, step, self.hessian) # Exit simulation step d_x_max = np.amax(np.absolute(np.subtract(self.beads.q, self.old_x))) self.exit = self.exitstep(self.forces.pot, self.old_u.sum(), d_x_max, self.exit, step) # Update positions and forces self.old_x[:] = self.beads.q self.old_u[:] = self.forces.pots self.old_f[:] = self.forces.f
def print_geo(self, step): # Print current instanton geometry if (self.options["save"] > 0 and np.mod(step, self.options["save"]) == 0) or self.exit: print_instanton_geo(self.options["prefix"], step, self.beads.nbeads, self.beads.natoms, self.beads.names, self.beads.q, self.forces.f,self.forces.pots, self.cell, self.optarrays["energy_shift"], self.output_maker)
def step(self, step=None): """ Does one simulation time step.""" self.qtime = -time.time() info("\n Instanton optimization STEP %d" % step, verbosity.low) if step == 0: info(" @GEOP: Initializing instanton", verbosity.low) if self.beads.nbeads == 1: raise ValueError("We can not perform an splitting calculation with nbeads =1") # get_hessian(self.hessian, self.gm, self.beads.q) else: if ((self.beads.q - self.beads.q[0]) == 0).all(): # If the coordinates in all the imaginary time slices are the same info(" @GEOP: We stretch the initial geometry with an 'amplitud' of %4.2f" % self.delta, verbosity.low) imvector = get_imvector(self.initial_hessian, self.beads.m3[0].flatten()) for i in range(self.beads.nbeads): self.beads.q[i, :] += self.delta * np.cos(i * np.pi / float(self.beads.nbeads - 1)) * imvector[:] else: info(" @GEOP: Starting from the provided geometry in the extended phase space", verbosity.low) # Update positions and forces self.old_x[:] = self.beads.q self.old_u[:] = self.forces.pots self.old_f[:] = self.forces.f # This must be done after the stretching and before the self.d. if type(self.im.f) == type(None): self.im(self.beads.q, ret=False) # Init instanton mapper # Specific for LBFGS if np.linalg.norm(self.d) == 0.0: f = self.forces.f + self.im.f # ALBERTO1 self.d += dstrip(f) / np.sqrt(np.dot(f.flatten(), f.flatten())) if (self.old_x == np.zeros((self.beads.nbeads, 3 * self.beads.natoms), float)).all(): self.old_x[:] = self.beads.q if self.exit: softexit.trigger("Geometry optimization converged. Exiting simulation") if len(self.fixatoms) > 0: for dqb in self.old_f: dqb[self.fixatoms * 3] = 0.0 dqb[self.fixatoms * 3 + 1] = 0.0 dqb[self.fixatoms * 3 + 2] = 0.0 e, g = self.fm(self.beads.q) fdf0 = (e, g) # Do one step. Update hessian for the new position. Update the position and force inside the mapper. L_BFGS(self.old_x, self.d, self.fm, self.qlist, self.glist, fdf0, self.big_step, self.ls_options["tolerance"] * self.tolerances["energy"], self.ls_options["iter"], self.corrections, self.scale, step) # ALBERTO2 # Update positions and forces self.beads.q = self.gm.dbeads.q self.forces.transfer_forces(self.gm.dforces) # This forces the update of the forces # Exit simulation step d_x_max = np.amax(np.absolute(np.subtract(self.beads.q, self.old_x))) self.exit = self.exitstep(self.forces.pot, self.old_u.sum(), d_x_max, self.exit, step) # Update positions and forces self.old_x[:] = self.beads.q self.old_u[:] = self.forces.pots self.old_f[:] = self.forces.f # Print current instanton geometry and hessian if (self.save > 0 and np.mod(step, self.save) == 0) or self.exit: print_instanton_geo(self.prefix, step, self.im.dbeads.nbeads, self.im.dbeads.natoms, self.im.dbeads.names, self.im.dbeads.q, self.old_u, self.cell, self.energy_shift, self.output_maker)
def step(self, step=None): """ Does one simulation time step.""" self.qtime = -time.time() info("\n Instanton optimization STEP %d" % step, verbosity.low) if step == 0: info(" @GEOP: Initializing instanton", verbosity.low) if self.beads.nbeads == 1: info(" @GEOP: Classical TS search", verbosity.low) if self.hessian_init == 'true': get_hessian(self.hessian, self.gm, self.beads.q, self.output_maker) else: if ((self.beads.q - self.beads.q[0]) == 0).all(): # If the coordinates in all the imaginary time slices are the same info(" @GEOP: We stretch the initial geometry with an 'amplitud' of %4.2f" % self.delta, verbosity.low) imvector = get_imvector(self.initial_hessian, self.beads.m3[0].flatten()) for i in range(self.beads.nbeads): self.beads.q[i, :] += self.delta * np.cos(i * np.pi / float(self.beads.nbeads - 1)) * imvector[:] if self.hessian_init != 'true': info(" @GEOP: Hessian_init isn't true but we have stretched the polymer so we are going to compute the initial hessian anyway.", verbosity.low) self.hessian_init = 'true' else: info(" @GEOP: Starting from the provided geometry in the extended phase space", verbosity.low) if not (self.initial_hessian is None): raise ValueError(" You have to provided a hessian with size (3xnatoms)^2 but also geometry in the extended phase space (nbeads>1). Please check the inputs\n") if self.hessian_init == 'true': info(" @GEOP: We are computing the initial hessian", verbosity.low) get_hessian(self.hessian, self.gm, self.beads.q, self.output_maker) # Update positions and forces self.old_x[:] = self.beads.q self.old_u[:] = self.forces.pots self.old_f[:] = self.forces.f if type(self.im.f) == type(None): self.im(self.beads.q, ret=False) # Init instanton mapper if (self.old_x == np.zeros((self.beads.nbeads, 3 * self.beads.natoms), float)).all(): self.old_x[:] = self.beads.q if self.exit: softexit.trigger("Geometry optimization converged. Exiting simulation") if len(self.fixatoms) > 0: for dqb in self.old_f: dqb[self.fixatoms * 3] = 0.0 dqb[self.fixatoms * 3 + 1] = 0.0 dqb[self.fixatoms * 3 + 2] = 0.0 # Do one step. Update hessian for the new position. Update the position and force inside the mapper. Instanton(self.old_x, self.old_f, self.im.f, self.hessian, self.hessian_update, self.hessian_asr, self.im, self.gm, self.big_step, self.opt, self.mode, self.output_maker) # Update positions and forces self.beads.q = self.gm.dbeads.q self.forces.transfer_forces(self.gm.dforces) # This forces the update of the forces # Print current instanton geometry and hessian if (self.save > 0 and np.mod(step, self.save) == 0) or self.exit: print_instanton_geo(self.prefix, step, self.im.dbeads.nbeads, self.im.dbeads.natoms, self.im.dbeads.names, self.im.dbeads.q, self.old_u, self.cell, self.energy_shift, self.output_maker) print_instanton_hess(self.prefix, step, self.hessian, self.output_maker) # Exit simulation step d_x_max = np.amax(np.absolute(np.subtract(self.beads.q, self.old_x))) self.exit = self.exitstep(self.forces.pot, self.old_u.sum(), d_x_max, self.exit, step) # Update positions and forces self.old_x[:] = self.beads.q self.old_u[:] = self.forces.pots self.old_f[:] = self.forces.f