Example #1
0
    def minimize(self, cluster: Cluster, *args, **kwargs) -> Cluster:
        """
        Method to locally minimise a cluster of Lennard-Jones particles.
        Uses the L-BFGS-B method implemented within scipy.minimize.

        Attributes:
            coordinates: np.array(shape=(number_of_particles, 3), dtype=float) array of coordinates
            kwargs: Dict containing any other keyword arguments to be passed to the scipy optimizer
            molecules: list(int), optional,

        Returns
        -------
        result_dict{'coordinates': optimised structure coordinates,
                    'energy': final energy of the cluster,
                    'success': True if successfully minimised}

        """
        positions = list(cluster.get_particle_positions())
        coordinates = positions[0].flatten()

        # args = {"sigma": self.sigma, "epsilon": self.epsilon4, "base_exp": 6}

        result = scipy.optimize.minimize(
            fun=self.get_energy,
            x0=coordinates,  # , args=args,
            method='L-BFGS-B',
            jac=self.get_jacobian)

        positions = (result.x.reshape(
            (self.n_atoms, 3)), positions[1], positions[2])
        cluster.set_particle_positions(positions)
        cluster.cost = result.fun
        return cluster
Example #2
0
    def minimize(self, cluster: Cluster, *args, **kwargs) -> Cluster:
        """
        Method to locally minimise a cluster of Lennard-Jones particles.
        Uses the L-BFGS-B method implemented within scipy.minimize.


        Args:
            cluster: Cluster instance, required, cluster instance to be minimized
            kwargs: Dict containing any other keyword arguments to be passed to the scipy optimizer

        Returns:
            result_dict{'coordinates': optimised structure coordinates,
                    'energy': final energy of the cluster,
                    'success': True if successfully minimised}

        """
        coords, ids, labels = cluster.get_particle_positions()
        coordinates = coords

        result = minimize(fun=self.get_energy,
                          x0=coordinates.flatten(),
                          method='L-BFGS-B',
                          jac=self.get_jacobian,
                          *args,
                          **kwargs)

        if not result.success:
            print("Optimization failed")

        cluster.set_particle_positions(
            (result.x.reshape(coordinates.shape), ids, labels))
        cluster.cost = result.fun
        return cluster
Example #3
0
    def get_energy(self, cluster: Cluster, *args, **kwargs) -> Cluster:
        """Provides the interface between the client and the minimise method of the

        Args:
            cluster: Cluster object, required, the Cluster to be minimised

        Returns:

        """
        self.log.debug("Getting energy for cluster: {}".format(cluster))

        # noinspection PyUnresolvedReferences
        result = self.potential.get_energy(cluster)
        cluster.cost = result
        return cluster
Example #4
0
    pot = LJcPotential(6)
    MC = MonteCarlo(potential=pot,
                    temperature=0.1,
                    update_steps=101,
                    move_classes=[RandomSingleTranslation()])

    c1 = Cluster(molecules=[
        Molecule(coordinates=np.array([[0.0, 0.0, 0.0]]),
                 particle_names=["LJ"]),
        Molecule(coordinates=np.array([[1.0, 1.0, 1.0]]),
                 particle_names=["LJ"]),
        Molecule(coordinates=np.array([[1.0, -1.0, 1.0]]),
                 particle_names=["LJ"]),
        Molecule(coordinates=np.array([[-1.0, 1.0, 1.0]]),
                 particle_names=["LJ"]),
        Molecule(coordinates=np.array([[-1.0, -1.0, 1.0]]),
                 particle_names=["LJ"]),
        Molecule(coordinates=np.array([[-2.0, -2.0, 2.0]]),
                 particle_names=["LJ"])
    ],
                 cost=0.0)
    c1 = pot.minimize(cluster=c1)
    c1.cost = pot.get_energy(c1)
    print(c1.cost)
    print(MC.move_classes[0].random)

    c1 = MC.run(cluster=c1, n_steps=10001)

    print(c1.cost)
    def run_DeMonNano(
            self,
            cluster: Cluster,
            dir_name: str,
            optimize: bool = False):  # TODO move minimize and energy to here
        """Common interface to DeMonNano"""

        if dir_name is not None:
            dir_name = os.path.abspath(dir_name)
        else:
            dir_name = os.path.abspath(self.get_directory())

        inp_fname = dir_name + "/deMon.inp"
        out_fname = dir_name + "/deMon.out"

        shutil.copyfile("SCC-SLAKO", dir_name + "/SCC-SLAKO")
        shutil.copyfile("SLAKO", dir_name + "/SLAKO")

        coords, molecule_ids, atom_labels = cluster.get_particle_positions()

        Natoms = len(molecule_ids)

        xyz_formatted_coordinates = self.format_XYZ(coords, atom_labels)

        with work_dir():

            os.chdir(dir_name)  # Change into the scratch dir.

            tag_dict = {"<XYZ>": xyz_formatted_coordinates}

            if optimize:
                template = self.minimize_template
            else:
                template = self.energy_template

            self.insert_to_template(template=self.work_dir + template,
                                    out_file=inp_fname,
                                    target_dict=tag_dict)

            with open("error_file", "w") as ef:
                # self.run_string should just be the location of the deMonNano executable
                dftb_process = subprocess.Popen([self.run_string],
                                                cwd=dir_name,
                                                shell=True,
                                                stderr=ef,
                                                stdout=ef)

            exit_code = dftb_process.wait()

            # check exit code
            if exit_code != 0:
                try:
                    raise DFTBError(
                        f"DFTB+ exited unexpectedly with exitcode: {exit_code}\n"
                    )
                except DFTBError as error:
                    self.log.exception(error)
                    raise
            else:
                self.log.debug(
                    f"DFTB+ exited successfully. Exit code: {exit_code}")

            if optimize:

                # noinspection PyTypeChecker
                parser = DeMonNanoParser(out_fname,
                                         natoms=Natoms,
                                         logger=self.log)

                result_dict = parser.parse_DeMonNano_output()
                new_coords = result_dict["coordinates"]
                cluster.set_particle_positions(
                    (new_coords, molecule_ids, atom_labels))

            else:

                # noinspection PyTypeChecker
                parser = DeMonNanoParser(out_fname,
                                         natoms=Natoms,
                                         geometry_opt=False,
                                         logger=self.log)

                result_dict = parser.parse_DeMonNano_output()

            energy = result_dict["energy"]
            cluster.cost = energy
            # os.chdir("..")  # Come back out of the scratch dir.

            return cluster