예제 #1
0
파일: _quench.py 프로젝트: borislavujo/pele
def mylbfgs(coords, pot, **kwargs):
    if not hasattr(pot, "getEnergyGradient"):
        # for compatibility with old quenchers.
        # assume pot is a getEnergyGradient function
        pot = _getEnergyGradientWrapper(pot)
    lbfgs = MYLBFGS(coords, pot, **kwargs)
    return lbfgs.run()
예제 #2
0
    def __init__(self,
                 coords,
                 pot,
                 eigenvec0=None,
                 orthogZeroEigs=0,
                 dx=1e-6,
                 first_order=True,
                 gradient=None,
                 **minimizer_kwargs):

        self.minimizer_kwargs = minimizer_kwargs

        if eigenvec0 is None:
            # this random vector should be distributed uniformly on a hypersphere.
            eigenvec0 = rotations.vec_random_ndim(coords.shape)
        eigenvec0 = eigenvec0 / np.linalg.norm(eigenvec0)

        # change some default in the minimizer unless manually set
        if "nsteps" not in minimizer_kwargs:
            minimizer_kwargs["nsteps"] = 500
        if "logger" not in minimizer_kwargs:
            minimizer_kwargs["logger"] = logging.getLogger(
                "pele.connect.findTS.leig_quench")

        self.eigpot = LowestEigPot(coords,
                                   pot,
                                   orthogZeroEigs=orthogZeroEigs,
                                   dx=dx,
                                   gradient=gradient,
                                   first_order=first_order)
        self.minimizer = MYLBFGS(eigenvec0,
                                 self.eigpot,
                                 rel_energy=True,
                                 **self.minimizer_kwargs)
예제 #3
0
    def setUp1(self, verbose=False, **kwargs):
        np.random.seed(0)
        natoms = 18
        self.system = LJCluster(natoms)
        self.pot = self.system.get_potential()
        x = self.system.get_random_configuration()
        ret = lbfgs_py(x, self.pot, tol=10)
        self.x = ret.coords

        self.kwargs = kwargs
        self.verbose = verbose

        self.M = 4
        if self.verbose: iprint = 1
        else: iprint = -1
        self.myo = MYLBFGS(self.x,
                           self.pot,
                           iprint=iprint,
                           debug=True,
                           M=self.M)
        self.o = LBFGS(self.x,
                       self.pot,
                       iprint=iprint,
                       debug=True,
                       M=self.M,
                       **self.kwargs)
예제 #4
0
def _mylbfgs(coords, pot, **kwargs):
    lbfgs = MYLBFGS(coords, pot, **kwargs)
    
    ret = lbfgs.run()
    
    coords = ret.coords
    e = ret.energy
    rms = ret.rms
    funcalls = ret.nfev
    return coords, e, rms, funcalls, ret
예제 #5
0
 def update_coords(self, coords, energy=None, gradient=None):
     """update the position at which to compute the eigenvector"""
     self.eigpot.update_coords(coords, gradient=gradient)
     state = self.minimizer.get_state()
     ret = self.get_result()
     self.minimizer = MYLBFGS(ret.eigenvec,
                              self.eigpot,
                              rel_energy=True,
                              **self.minimizer_kwargs)
     self.minimizer.set_state(state)
예제 #6
0
    def test_state(self):
        # do several minimization iterations
        for i in range(10):
            self.minimizer.one_iteration()

        # get the state and save it
        ret = self.minimizer.get_result()
        state = self.minimizer.get_state()
        x1 = ret.coords.copy()

        # do several more iteration steps
        for i in range(10):
            self.minimizer.one_iteration()

        # now make a new minimizer and do several iterations
        minimizer2 = MYLBFGS(x1, self.pot)
        minimizer2.set_state(state)
        for i in range(10):
            minimizer2.one_iteration()

        # test that the two minimizers are in the same state
        ret1 = self.minimizer.get_result()
        ret2 = minimizer2.get_result()
        self.assertEqual(ret1.energy, ret2.energy)
        self.assertTrue((ret1.coords == ret2.coords).all())

        state1 = self.minimizer.get_state()
        state2 = minimizer2.get_state()

        self.assertTrue((state1.W == state2.W).all())
        self.assertTrue((state1.dXold == state2.dXold).all())
        self.assertTrue((state1.dGold == state2.dGold).all())
        self.assertEqual(state1.H0, state2.H0)
        self.assertEqual(state1.point, state2.point)
        self.assertEqual(state1.iter, state2.iter)
예제 #7
0
 def update_coords(self, coords, energy=None, gradient=None):
     """update the position at which to compute the eigenvector"""
     self.eigpot.update_coords(coords, gradient=gradient)
     state = self.minimizer.get_state()
     ret = self.get_result()
     self.minimizer = MYLBFGS(ret.eigenvec, self.eigpot, rel_energy=True, **self.minimizer_kwargs)
     self.minimizer.set_state(state)
예제 #8
0
    def __init__(
        self,
        coords,
        pot,
        eigenvec0=None,
        orthogZeroEigs=0,
        dx=1e-6,
        first_order=True,
        gradient=None,
        **minimizer_kwargs
    ):

        self.minimizer_kwargs = minimizer_kwargs

        if eigenvec0 is None:
            # this random vector should be distributed uniformly on a hypersphere.
            eigenvec0 = rotations.vec_random_ndim(coords.shape)
        eigenvec0 = eigenvec0 / np.linalg.norm(eigenvec0)

        # change some default in the minimizer unless manually set
        if "nsteps" not in minimizer_kwargs:
            minimizer_kwargs["nsteps"] = 500
        if "logger" not in minimizer_kwargs:
            minimizer_kwargs["logger"] = logging.getLogger("pele.connect.findTS.leig_quench")

        self.eigpot = LowestEigPot(
            coords, pot, orthogZeroEigs=orthogZeroEigs, dx=dx, gradient=gradient, first_order=first_order
        )
        self.minimizer = MYLBFGS(eigenvec0, self.eigpot, rel_energy=True, **self.minimizer_kwargs)
예제 #9
0
 def setUp1(self, verbose=False, **kwargs):
     np.random.seed(0)
     natoms = 18
     self.system = LJCluster(natoms)
     self.pot = self.system.get_potential()
     x = self.system.get_random_configuration()
     ret = lbfgs_py(x, self.pot, tol=10)
     self.x = ret.coords
     
     self.kwargs = kwargs
     self.verbose = verbose
 
     self.M = 4
     if self.verbose: iprint=1
     else: iprint = -1
     self.myo = MYLBFGS(self.x, self.pot, iprint=iprint, debug=True, M=self.M)
     self.o = LBFGS(self.x, self.pot, iprint=iprint, debug=True, M=self.M, **self.kwargs)
예제 #10
0
class TestMYLBFGS_State(unittest.TestCase):
    def setUp(self):
        self.system = LJCluster(13)
        self.x = self.system.get_random_configuration()
        self.pot = self.system.get_potential()
        self.minimizer = MYLBFGS(self.x, self.pot)

    def test_state(self):
        # do several minimization iterations
        for i in range(10):
            self.minimizer.one_iteration()

        # get the state and save it
        ret = self.minimizer.get_result()
        state = self.minimizer.get_state()
        x1 = ret.coords.copy()

        # do several more iteration steps
        for i in range(10):
            self.minimizer.one_iteration()

        # now make a new minimizer and do several iterations
        minimizer2 = MYLBFGS(x1, self.pot)
        minimizer2.set_state(state)
        for i in range(10):
            minimizer2.one_iteration()

        # test that the two minimizers are in the same state
        ret1 = self.minimizer.get_result()
        ret2 = minimizer2.get_result()
        self.assertEqual(ret1.energy, ret2.energy)
        self.assertTrue((ret1.coords == ret2.coords).all())

        state1 = self.minimizer.get_state()
        state2 = minimizer2.get_state()

        self.assertTrue((state1.W == state2.W).all())
        self.assertTrue((state1.dXold == state2.dXold).all())
        self.assertTrue((state1.dGold == state2.dGold).all())
        self.assertEqual(state1.H0, state2.H0)
        self.assertEqual(state1.point, state2.point)
        self.assertEqual(state1.iter, state2.iter)
예제 #11
0
    def _minimize_transverse(self, nsteps, transverse_energy=None, transverse_gradient=None):
        # must update
        minimizer = MYLBFGS(self.coords, self.transverse_potential,
                            nsteps=self.nsteps_tangent,
                            energy=transverse_energy, gradient=transverse_gradient,
                            **self.transverse_kwargs)

        if self._transverse_walker_state is not None:
            minimizer.set_state(self._transverse_walker_state)
        ret = minimizer.run()
        self._transverse_walker_state = minimizer.get_state()
        self._stop_criterion_satisfied = minimizer.stop_criterion_satisfied()

        return ret
예제 #12
0
    def _minimize_transverse(self,
                             nsteps,
                             transverse_energy=None,
                             transverse_gradient=None):
        # must update
        minimizer = MYLBFGS(self.coords,
                            self.transverse_potential,
                            nsteps=self.nsteps_tangent,
                            energy=transverse_energy,
                            gradient=transverse_gradient,
                            **self.transverse_kwargs)

        if self._transverse_walker_state is not None:
            minimizer.set_state(self._transverse_walker_state)
        ret = minimizer.run()
        self._transverse_walker_state = minimizer.get_state()
        self._stop_criterion_satisfied = minimizer.stop_criterion_satisfied()

        return ret
예제 #13
0
파일: _quench.py 프로젝트: yangxi1209/pele
def mylbfgs(coords, pot, **kwargs):
    lbfgs = MYLBFGS(coords, pot, **kwargs)
    return lbfgs.run()
예제 #14
0
파일: _quench.py 프로젝트: pele-python/pele
def mylbfgs(coords, pot, **kwargs):
    lbfgs = MYLBFGS(coords, pot, **kwargs)
    return lbfgs.run()
예제 #15
0
class FindLowestEigenVector(object):
    """A class to compute the lowest eigenvector of the Hessian using Rayleigh-Ritz minimization
    
    Parameters
    ----------
    coords : float array
        the point in space at which to compute the lowest eigenvector
    pot : Potential object
        the potential energy function
    eigenvec0 : float array
        the initial guess for the lowest eigenvector
    orthogZeroEigs : callable
        The function which makes a vector orthogonal to the known
        eigenvectors with zero eigenvalues.  The default assumes global
        translational and rotational symmetry
    dx : float
        the local curvature is approximated using points separated by dx
    first_order : bool
        use the first order forward finite differences approximation for
        the curvature rather than the second order central differences
        approximation.  This is less accurate, but requires one fewer
        potential call per iteration.
    gradient : float array
        the true gradient at coords.  If first_order is true and gradient
        is not None then one potential call will be saved.
    minimizer_kwargs : kwargs
        these kwargs are passed to the optimizer which finds the direction 
        of least curvature
    """
    def __init__(self,
                 coords,
                 pot,
                 eigenvec0=None,
                 orthogZeroEigs=0,
                 dx=1e-6,
                 first_order=True,
                 gradient=None,
                 **minimizer_kwargs):

        self.minimizer_kwargs = minimizer_kwargs

        if eigenvec0 is None:
            # this random vector should be distributed uniformly on a hypersphere.
            eigenvec0 = rotations.vec_random_ndim(coords.shape)
        eigenvec0 = eigenvec0 / np.linalg.norm(eigenvec0)

        # change some default in the minimizer unless manually set
        if "nsteps" not in minimizer_kwargs:
            minimizer_kwargs["nsteps"] = 500
        if "logger" not in minimizer_kwargs:
            minimizer_kwargs["logger"] = logging.getLogger(
                "pele.connect.findTS.leig_quench")

        self.eigpot = LowestEigPot(coords,
                                   pot,
                                   orthogZeroEigs=orthogZeroEigs,
                                   dx=dx,
                                   gradient=gradient,
                                   first_order=first_order)
        self.minimizer = MYLBFGS(eigenvec0,
                                 self.eigpot,
                                 rel_energy=True,
                                 **self.minimizer_kwargs)

    def stop_criterion_satisfied(self):
        """test if the stop criterion is satisfied"""
        return self.minimizer.stop_criterion_satisfied()

    def update_coords(self, coords, energy=None, gradient=None):
        """update the position at which to compute the eigenvector"""
        self.eigpot.update_coords(coords, gradient=gradient)
        state = self.minimizer.get_state()
        ret = self.get_result()
        self.minimizer = MYLBFGS(ret.eigenvec,
                                 self.eigpot,
                                 rel_energy=True,
                                 **self.minimizer_kwargs)
        self.minimizer.set_state(state)

    def one_iteration(self):
        """do one iteration of the minimizer"""
        self.minimizer.one_iteration()

    def run(self, niter=None):
        """do niter iterations, or until the stop criterion is satisfied"""
        if niter is None:
            self.minimizer.run()
            return self.get_result()
        else:
            for i in xrange(niter):
                if self.minimizer.stop_criterion_satisfied():
                    break
                self.one_iteration()
            return self.get_result()

    def get_result(self):
        """return the results object"""
        res = self.minimizer.get_result()
        res.eigenval = res.energy
        res.eigenvec = res.coords / np.linalg.norm(res.coords)
        delattr(res, "energy")
        delattr(res, "coords")
        # res.minimizer_state = self.minimizer.get_state()
        res.nfev = self.eigpot.nfev
        return res
예제 #16
0
 def setUp(self):
     self.system = LJCluster(13)
     self.x = self.system.get_random_configuration()
     self.pot = self.system.get_potential()
     self.minimizer = MYLBFGS(self.x, self.pot)
예제 #17
0
class FindLowestEigenVector(object):
    """A class to compute the lowest eigenvector of the Hessian using Rayleigh-Ritz minimization
    
    Parameters
    ----------
    coords : float array
        the point in space at which to compute the lowest eigenvector
    pot : Potential object
        the potential energy function
    eigenvec0 : float array
        the initial guess for the lowest eigenvector
    orthogZeroEigs : callable
        The function which makes a vector orthogonal to the known
        eigenvectors with zero eigenvalues.  The default assumes global
        translational and rotational symmetry
    dx : float
        the local curvature is approximated using points separated by dx
    first_order : bool
        use the first order forward finite differences approximation for
        the curvature rather than the second order central differences
        approximation.  This is less accurate, but requires one fewer
        potential call per iteration.
    gradient : float array
        the true gradient at coords.  If first_order is true and gradient
        is not None then one potential call will be saved.
    minimizer_kwargs : kwargs
        these kwargs are passed to the optimizer which finds the direction 
        of least curvature
    """
    def __init__(self, coords, pot, eigenvec0=None, orthogZeroEigs=0, dx=1e-6,
                  first_order=True, gradient=None, **minimizer_kwargs):
        
        self.minimizer_kwargs = minimizer_kwargs
        
        if eigenvec0 is None:
            # this random vector should be distributed uniformly on a hypersphere.
            eigenvec0 = rotations.vec_random_ndim(coords.shape)
        eigenvec0 = eigenvec0 / np.linalg.norm(eigenvec0)

        # change some default in the minimizer unless manually set
        if "nsteps" not in minimizer_kwargs:
            minimizer_kwargs["nsteps"] = 500
        if "logger" not in minimizer_kwargs:
            minimizer_kwargs["logger"] = logging.getLogger("pele.connect.findTS.leig_quench")


        self.eigpot = LowestEigPot(coords, pot, orthogZeroEigs=orthogZeroEigs, dx=dx,
                                   gradient=gradient,
                                   first_order=first_order)
        self.minimizer = MYLBFGS(eigenvec0, self.eigpot, rel_energy=True, 
                                 **self.minimizer_kwargs)

    def stop_criterion_satisfied(self):
        """test if the stop criterion is satisfied"""
        return self.minimizer.stop_criterion_satisfied()
    
    def update_coords(self, coords, energy=None, gradient=None):
        """update the position at which to compute the eigenvector"""
        self.eigpot.update_coords(coords, gradient=gradient)
        state = self.minimizer.get_state()
        ret = self.get_result()
        self.minimizer = MYLBFGS(ret.eigenvec, self.eigpot, rel_energy=True,
                                 **self.minimizer_kwargs)
        self.minimizer.set_state(state)
    
    def one_iteration(self):
        """do one iteration of the minimizer"""
        self.minimizer.one_iteration()
    
    def run(self, niter=None):
        """do niter iterations, or until the stop criterion is satisfied"""
        if niter is None:
            self.minimizer.run()
            return self.get_result()
        else:
            for i in xrange(niter):
                if self.minimizer.stop_criterion_satisfied():
                    break
                self.one_iteration()
            return self.get_result()
        
    def get_result(self):
        """return the results object"""
        res = self.minimizer.get_result()
        res.eigenval = res.energy
        res.eigenvec = res.coords / np.linalg.norm(res.coords)
        delattr(res, "energy")
        delattr(res, "coords")
#        res.minimizer_state = self.minimizer.get_state()
        res.nfev = self.eigpot.nfev
        return res
예제 #18
0
class TestMYLBFGS_LBFGS(unittest.TestCase):
    def setUp(self):
        self.setUp1(verbose=False)

    def setUp1(self, verbose=False, **kwargs):
        np.random.seed(0)
        natoms = 18
        self.system = LJCluster(natoms)
        self.pot = self.system.get_potential()
        x = self.system.get_random_configuration()
        ret = lbfgs_py(x, self.pot, tol=10)
        self.x = ret.coords

        self.kwargs = kwargs
        self.verbose = verbose

        self.M = 4
        if self.verbose: iprint = 1
        else: iprint = -1
        self.myo = MYLBFGS(self.x,
                           self.pot,
                           iprint=iprint,
                           debug=True,
                           M=self.M)
        self.o = LBFGS(self.x,
                       self.pot,
                       iprint=iprint,
                       debug=True,
                       M=self.M,
                       **self.kwargs)

    def test(self):
        N = self.x.size
        M = self.M
        myo = self.myo
        o = self.o

        # do one iteration
        for i in range(3 * self.M):
            myo.one_iteration()
            o.one_iteration()
            if self.verbose:
                print("")
                print("H0", myo.H0, o.H0)
                print("rho  ", o.rho[:])
                print("myrho", myo.W[N:N + M])

        myret = myo.get_result()
        ret = o.get_result()

        self.assertAlmostEqual(ret.energy, myret.energy, 4)
        self.assertLess(np.max(np.abs(myret.coords - ret.coords)), 1e-6)

        # do a second iteration
        for i in range(1):
            myo.one_iteration()
            o.one_iteration()
        myret = myo.get_result()
        ret = o.get_result()

        if self.verbose:
            print("H0", myret.H0, ret.H0)
            print("rho  ", o.rho[:])
            print("myrho", myo.W[N:N + M])

        self.assertAlmostEqual(ret.energy, myret.energy, 4)
        self.assertLess(np.max(np.abs(myret.coords - ret.coords)), 1e-6)

    def test_complete(self):
        myret = self.myo.run()
        ret = self.o.run()
        self.assertEqual(ret.nfev, myret.nfev)
        self.assertEqual(ret.nsteps, myret.nsteps)
        self.assertAlmostEqual(ret.energy, myret.energy, 4)
        self.assertLess(np.max(np.abs(myret.coords - ret.coords)), 1e-6)
예제 #19
0
class TestMYLBFGS_LBFGS(unittest.TestCase):
    def setUp(self):
        self.setUp1(verbose=False)

    def setUp1(self, verbose=False, **kwargs):
        np.random.seed(0)
        natoms = 18
        self.system = LJCluster(natoms)
        self.pot = self.system.get_potential()
        x = self.system.get_random_configuration()
        ret = lbfgs_py(x, self.pot, tol=10)
        self.x = ret.coords
        
        self.kwargs = kwargs
        self.verbose = verbose
    
        self.M = 4
        if self.verbose: iprint=1
        else: iprint = -1
        self.myo = MYLBFGS(self.x, self.pot, iprint=iprint, debug=True, M=self.M)
        self.o = LBFGS(self.x, self.pot, iprint=iprint, debug=True, M=self.M, **self.kwargs)

    def test(self):
        N = self.x.size
        M = self.M
        myo = self.myo
        o = self.o

        # do one iteration
        for i in xrange(3 * self.M):   
            myo.one_iteration()
            o.one_iteration()
            if self.verbose:
                print ""
                print "H0", myo.H0, o.H0
                print "rho  ", o.rho[:]
                print "myrho", myo.W[N:N+M]

        myret = myo.get_result()
        ret = o.get_result()
        
        self.assertAlmostEqual(ret.energy, myret.energy, 4)
        self.assertLess(np.max(np.abs(myret.coords - ret.coords)), 1e-6)
    
        # do a second iteration
        for i in xrange(1):
            myo.one_iteration()
            o.one_iteration()
        myret = myo.get_result()
        ret = o.get_result()
        
        if self.verbose:
            print "H0", myret.H0, ret.H0
            print "rho  ", o.rho[:]
            print "myrho", myo.W[N:N+M]

        self.assertAlmostEqual(ret.energy, myret.energy, 4)
        self.assertLess(np.max(np.abs(myret.coords - ret.coords)), 1e-6)
    
    def test_complete(self):
        myret = self.myo.run()
        ret = self.o.run()
        self.assertEqual(ret.nfev, myret.nfev)
        self.assertEqual(ret.nsteps, myret.nsteps)
        self.assertAlmostEqual(ret.energy, myret.energy, 4)
        self.assertLess(np.max(np.abs(myret.coords - ret.coords)), 1e-6)