diff --git a/.github/workflows/cmake.yml b/.github/workflows/cmake.yml index dd79e9c7..b4a33caf 100644 --- a/.github/workflows/cmake.yml +++ b/.github/workflows/cmake.yml @@ -37,6 +37,7 @@ jobs: python-version: [ "3.11", "3.12", "3.13" ] toolchain: - {fortran-compiler: gcc, fc-version: 13} + - {fortran-compiler: gcc, fc-version: 14} # - {fortran-compiler: intel, fc-version: '2024.1'} # - {fortran-compiler: intel-classic,fc- version: '2021.10'} # exclude: diff --git a/.github/workflows/coverage.yml b/.github/workflows/coverage.yml index 40cc0e38..7ceeefeb 100644 --- a/.github/workflows/coverage.yml +++ b/.github/workflows/coverage.yml @@ -101,13 +101,19 @@ jobs: - name: upload artifact uses: actions/upload-pages-artifact@v3 with: - path: './build/coverage/' + path: './build/coverage/' - # Deploy to GitHub Pages: uniform pattern for all branches + deploy: + environment: + name: github-pages + url: ${{ steps.deployment.outputs.page_url }} + runs-on: ubuntu-latest + needs: run-code-coverage + if: ${{ github.ref == 'refs/heads/main' }} + steps: - name: deploy to Github Pages (main branch) - if: ${{ github.ref == 'refs/heads/main' }} - uses: actions/deploy-pages@v2 id: deployment + uses: actions/deploy-pages@v4 # - name: deploy to Github Pages (development branch) # if: ${{ github.ref != 'refs/heads/main' }} diff --git a/.github/workflows/formatting.yml b/.github/workflows/formatting.yml index d6d681ba..ad354318 100644 --- a/.github/workflows/formatting.yml +++ b/.github/workflows/formatting.yml @@ -51,12 +51,10 @@ jobs: - name: Comment on PR if script failed if: github.event_name == 'pull_request' && steps.run_format_checker.outcome != 'success' + env: + GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} run: | - github.rest.issues.createComment({ - issue_number: context.issue.number, - owner: context.repo.owner, - repo: context.repo.repo, - body: '⚠️ The format checker failed. - Please check the formatting of your code by running tools/check_indentation.py locally.' - }) + gh pr comment ${{ github.event.pull_request.number }} --body "⚠️ The format checker failed. + Please check the formatting of your code by running tools/check_indentation.py locally." + \ No newline at end of file diff --git a/.github/workflows/fpm.yml b/.github/workflows/fpm.yml index 0ee5f263..66b5d407 100644 --- a/.github/workflows/fpm.yml +++ b/.github/workflows/fpm.yml @@ -36,6 +36,7 @@ jobs: os: [ubuntu-latest, macos-latest] toolchain: - {compiler: gcc, version: 13} + - {fortran-compiler: gcc, fc-version: 14} # - {compiler: intel, version: '2024.1'} # - {compiler: intel-classic, version: '2021.10'} # exclude: diff --git a/.github/workflows/publish-to-test-pypi.yml b/.github/workflows/publish-to-test-pypi.yml index b9b8a3a7..d2b13e5d 100644 --- a/.github/workflows/publish-to-test-pypi.yml +++ b/.github/workflows/publish-to-test-pypi.yml @@ -12,6 +12,37 @@ on: workflow_dispatch: jobs: + check-version-matches: + name: Check if version numbers match the GitHub tag + runs-on: ubuntu-latest + steps: + - name: Checkout repository + uses: actions/checkout@v4 + + - name: Extract version from fpm.toml + id: fpm_version + run: echo "RAFFLE_FPM_VERSION=$(grep -oP '(?<=version = ")[^"]+' fpm.toml)" >> "$GITHUB_ENV" + + - name: Extract version from mod_io_utils.F90 + id: fortran_version + run: echo "RAFFLE_FORTRAN_VERSION=$(grep -oP '(?<=raffle__version__ = ")[^"]+' src/fortran/lib/mod_io_utils.F90)" >> "$GITHUB_ENV" + + - name: Extract GitHub tag version + id: github_tag + run: echo "TAG_VERSION=${GITHUB_REF#refs/tags/v}" >> "$GITHUB_ENV" + + - name: Verify version consistency + run: | + if [[ "$FPM_VERSION" != "$TAG_VERSION" ]]; then + echo "❌ Version mismatch: fpm.toml ($FPM_VERSION) does not match GitHub tag ($TAG_VERSION)" + exit 1 + fi + if [[ "$FORTRAN_VERSION" != "$TAG_VERSION" ]]; then + echo "❌ Version mismatch: mod_io_utils.F90 ($FORTRAN_VERSION) does not match GitHub tag ($TAG_VERSION)" + exit 1 + fi + echo "✅ Version numbers match!" + build_wheel: name: Build wheel distribution 📦 runs-on: ${{ matrix.platform[0] }} @@ -24,6 +55,8 @@ jobs: python-version: [ "3.12" ] # cibuildwheel automatically runs on all versions of Python toolchain: - {fortran-compiler: gcc, fc-version: 13} + needs: + - check-version-matches steps: - name: checkout repo @@ -127,6 +160,14 @@ jobs: id-token: write # IMPORTANT: mandatory for sigstore steps: + - name: Check if GitHub release already exists + env: + GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} + run: | + if gh release view '${{ github.ref_name }}' --repo '${{ github.repository }}' > /dev/null 2>&1; then + echo "Release already exists for tag '${{ github.ref_name }}'. Skipping release creation." + exit 0 + fi - name: Download all the dists uses: actions/download-artifact@v4 with: diff --git a/.gitignore b/.gitignore index 231f6e17..ac2602a9 100644 --- a/.gitignore +++ b/.gitignore @@ -48,4 +48,9 @@ REPORT vasprun.xml DVASP_MACE_comparison/ pca_model*.pkl -.benchmarks/ \ No newline at end of file +.benchmarks/ +.local-pre-commit-config.yaml +*.tgz +.ipynb_checkpoints +*.model +*.vasp \ No newline at end of file diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml new file mode 100644 index 00000000..5973b653 --- /dev/null +++ b/.pre-commit-config.yaml @@ -0,0 +1,11 @@ +repos: +- repo: https://github.com/pre-commit/pre-commit-hooks + rev: v5.0.0 # Use the ref you want to point at + hooks: + - id: trailing-whitespace + - id: end-of-file-fixer +- repo: https://github.com/nedtaylor/fortran-format-hooks + rev: 5400a80b67ac12f16dd70d1200d6c5a06dbf8855 + hooks: + - id: check-fortran-indentation + args: [--line-length=80, --ignore-directories 'src/wrapper'] diff --git a/CITATION.cff b/CITATION.cff index 1d8ceb6d..4b83ab7b 100644 --- a/CITATION.cff +++ b/CITATION.cff @@ -31,6 +31,6 @@ keywords: - structure prediction - random structure search license: GPL-3.0 -commit: 4cdf115d5d43d6f97037f6cb15c036dc9615eacb -version: 0.5.0 -date-released: '2024-12-18' +commit: 1a4e7aacf07b4d9623d846df30aa7ac3a5e98e81 +version: 1.0.0 +date-released: '2025-03-03' diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md new file mode 100644 index 00000000..62238b68 --- /dev/null +++ b/CONTRIBUTING.md @@ -0,0 +1,117 @@ +# Contributing Guidelines + +Thank you for considering contributing to the RAFFLE project! We appreciate your time and effort. To ensure a smooth collaboration, please follow the guidelines provided below. + +Please first discuss potential changes you wish to make to the project via issue (preferably), or email. + +> And if you like the project, but just don't have time to contribute, that's fine. There are other easy ways to support the project and show your appreciation, which we would also be very happy about: +> - Star the project +> - Mention it on social media platforms +> - Refer this project in your project's readme +> - Mention the project at local meetups and tell your friends/colleagues + + + +## Table of Contents +- [Code of Conduct](#code-of-conduct) +- [I Have a Question](#i-have-a-question) +- [I Want to Contribute](#i-want-to-contribute) +- [Reporting Bugs](#reporting-bugs) +- [Suggesting Enhancements](#suggesting-enhancements) +- [Code Style](#code-style) +- [Testing](#testing) +- [Documentation](#documentation) +- [Contact](#contact) +- [License](#license) + + +## Code of Conduct + +This project and everyone participating in it is governed by the +[RAFFLE Code of Conduct](CODE_OF_CONDUCT.md). +By participating, you are expected to uphold this code. +Please report unacceptable behavior to the RAFFLE developers: [Ned Taylor](mailto:n.t.taylor@exeter.ac.uk?subject=RAFFLE%20-%behaviour) or [Steve Hepplestone](mailto:s.p.hepplestone@exeter.ac.uk?subject=RAFFLE%20-%behaviour). + +## I Have a Question + +> If you want to ask a question, we assume that you have read the available [Documentation](README.md). + +Before you ask a question, it is best to search for existing [Issues](https://github.com/ExeQuantCode/RAFFLE/issues) that might help you. +In case you have found a suitable issue and still need clarification, you can write your question in this issue. It is also advisable to search the internet for answers first. + +If you then still feel the need to ask a question and need clarification, we recommend the following: + +- Open an [Issue](https://github.com/ExeQuantCode/RAFFLE/issues/new). +- Provide as much context as you can about what you're running into. +- Provide project and platform versions (python, fortran, pip), depending on what seems relevant. + +We will then take care of the issue as soon as possible. + +## I Want To Contribute + +> ### Legal Notice +> When contributing to this project, you must agree that you have authored 100% of the content, that you have the necessary rights to the content and that the content you contribute may be provided under the project license. + +### Reporting Bugs +If you encounter any issues or have suggestions for improvement, please open an [Issue](https://github.com/ExeQuantCode/RAFFLE/issues/new) on the repository's issue tracker. + +When reporting, please provide as much context as possible and describe the reproduction steps that someone else can follow to recreate the issue on their own. +This usually includes your code. +For good bug reports you should isolate the problem and create a reduced test case. + + + +### Suggesting Enhancements + +This section guides you through submitting an enhancement suggestion for RAFFLE, **including completely new features and minor improvements to existing functionality**. +Following these guidelines will help maintainers and the community to understand your suggestion and find related suggestions. + + +#### Before Submitting an Enhancement + +- Make sure that you are using the latest version. +- Read the compilable documentation carefully and find out if the functionality is already covered. +- Perform a [search](https://github.com/ExeQuantCode/RAFFLE/issues) to see if the enhancement has already been suggested. If it has, add a comment to the existing issue instead of opening a new one. +- Find out whether your idea fits with the scope and aims of the project. It's up to you to make a strong case to convince the project's developers of the merits of this feature. Keep in mind that we want features that will be useful to the majority of our users and not just a small subset. If you're just targeting a minority of users, consider writing an add-on/plugin library. + + +### Contributing Code + +This guide provides the recommended route to contributing to RAFFLE: + +1. Fork the repository. +2. Clone the forked repository to your local machine. +3. Create a new branch for your changes. +4. Make your changes and commit them. +5. Push the changes to your forked repository. +6. Open a pull request to the main repository. + +When submitting your contributions, please ensure the following: +- Provide a clear and descriptive title for your pull request. +- Include a detailed description of the changes made. +- Reference any related issues or pull requests, if applicable. +- Write unit tests for your contributions +- Ensure all existing tests pass before submitting your changes. +- Update the documentation to reflect your changes, if necessary (i.e. through FORD style commenting). +- Provide examples and usage instructions, if applicable. + +Follow the [Code Style](#code-style) when contributing code to this project to ensure compatibility and a uniform format to the project. + + +### Code Style +- Follow the existing code style and conventions. +- Use meaningful variable and function names. +- Write clear and concise comments. For the Fortran library, use comments compatible with the [FORD Fortran Documenter](https://forddocs.readthedocs.io/en/stable/). For the Python wrapper, use comments compatible with [pandoc](https://pandoc.org). + + + +## Contact +If you have any questions or need further assistance, feel free to contact [Ned Taylor](mailto:n.t.taylor@exeter.ac.uk?subject=RAFFLE%20-%query) or [Steve Hepplestone](mailto:s.p.hepplestone@exeter.ac.uk?subject=RAFFLE%20-%query). + +## License +This project is licensed under the [GPL-3.0 License](LICENSE). + + +## Attribution +This guide is based on the **contributing-gen** and has been copied from the [graphstruc](https://github.com/nedtaylor/graphstruc) repository, with permission from the creator (Ned Taylor). +[Make your own](https://github.com/bttger/contributing-gen)! diff --git a/Placement.tar b/Placement.tar new file mode 100644 index 00000000..0a27c404 Binary files /dev/null and b/Placement.tar differ diff --git a/README.md b/README.md index 0b879da6..81efbc91 100644 --- a/README.md +++ b/README.md @@ -28,6 +28,9 @@ Tutorials and documentation are provided on the [docs](http://raffle-fortran.rea The methodology is detailed in the [Phys Rev B paper](https://link.aps.org/doi/10.1103/PhysRevLett.132.066201). The software package will be submitted for publication soon. +Refer to the [API Documentation section](#api-documentation) later in this document to see how to access the API-specific documentation. + + ## Requirements @@ -47,21 +50,38 @@ Python-specific installation: - ASE (optional) The library bas been developed and tested using the following Fortran compilers: +- gfortran -- gcc 11.4.0 - gfortran -- gcc 13.2.0 - gfortran -- gcc 14.1.0 +- gfortran -- gcc 14.2.0 The library is known to not currently work with the intel Fortran compilers. ## Installation -To install RAFFLE, the source must be obtained from the git repository. Use the following commands to get started: +For the Python library, the easiest method of installation is to install it directly from pip: + +``` +pip install raffle +``` + +or + +``` +pip install 'raffle[ase]' +``` + +Once this is done, RAFFLE is ready to be used. + +Alternatively, to download development versions or, if, for some reason, the pip method does not work, then RAFFLE can be installed from the source. +To do so, the source must be obtained from the git repository. +Use the following commands to get started: ``` git clone https://github.com/ExeQuantCode/raffle.git cd raffle ``` - -Depending on what language will be used in, installation will fary from this point. +Depending on what language will be used in, installation will vary from this point. ### Python @@ -150,36 +170,31 @@ Now follow the instructions for the [Python](#python) build methods. After the library has been installed, a set of example programs can be found in the `example` directory (note, the `test` directory is for unit tests to ensure each procedure in the library produces expected outputs after compilation, they are not really needed to be looked at by potential users). -The `example/executable` example uses a shell script to run the Fortran installed application. +The `example/fortran_exe` example uses a shell script to run the Fortran installed application. It uses a user-editable input file `param.in` in the same directory to change values of the RAFFLE generator and provided database. -The `example/wrapper` directory contains a set of `run_*.py` files that show how RAFFLE can be called using Python to implement it into existing random structure search workflows. +The `example/python_pkg` directory contains a set of subdirectories `MATERIAL_learn` that show how RAFFLE can be called using Python to implement it into existing structure search workflows. These examples are the recommended ones to run. -To successfully run them, follow the above installation instructions for Python, then go to the `example/wrapper` directory and run one of the scripts. - - - +API documentation can be generated using FORD (Fortran Documenter). +To do so, follow the installation guide on the [FORD website](https://forddocs.readthedocs.io/en/stable/) to ensure FORD is installed. +Once FORD is installed, run the following command in the root directory of the git repository: +``` + ford ford.md +``` Contributing ------------ -If you have any questions, bug reports, or feature requests, please post then in [issues](https://github.com/ExeQuantCode/RAFFLE/issues). +Please note that this project adheres to the [Contributing Guide](CONTRIBUTING.md). +If you want to contribute to this project, please first read through the guide. +If you have any questions, bug reports, or feature requests, please either discuss then in [issues](https://github.com/nedtaylor/athena/issues). License diff --git a/app/inputs.f90 b/app/inputs.f90 index d1cd56f6..09dc9833 100644 --- a/app/inputs.f90 +++ b/app/inputs.f90 @@ -9,11 +9,11 @@ module inputs use raffle__constants, only: real32, pi use raffle__io_utils implicit none - + private - public :: grid, grid_spacing, method_probab + public :: grid, grid_spacing, method_ratio public :: seed public :: num_structures, task public :: stoich @@ -60,9 +60,9 @@ module inputs !! Grid dimensions. real(real32) :: grid_spacing = 0._real32 !! Grid spacing. - real(real32), dimension(5) :: method_probab = & + real(real32), dimension(5) :: method_ratio = & [1._real32, 0.1_real32, 0.5_real32, 0.5_real32, 1._real32] - !! Placement method probabilities. + !! Placement method ratios. character(1024), dimension(:), allocatable :: database_list !! List of directories containing input database. @@ -93,7 +93,7 @@ subroutine set_global_vars() !! Character variables. logical :: skip, empty !! Logical variables. - integer, dimension(:), allocatable :: seed_arr + integer, dimension(:), allocatable :: seed_arr !! Random seed array. @@ -217,7 +217,7 @@ subroutine read_input_file(file_name) real(real32), dimension(3) :: width, sigma !! Width and sigma values for distribution functions. real(real32) :: void, rand, walk, grow, min - !! Placement method probabilities. + !! Placement method ratios. character(50), dimension(3) :: cutoff_min, cutoff_max !! Cutoff values for distribution functions. @@ -308,9 +308,9 @@ subroutine read_input_file(file_name) end do end if - method_probab = [void, rand, walk, grow, min] - if(all(abs(method_probab).lt.1.E-6))then - method_probab = & + method_ratio = [void, rand, walk, grow, min] + if(all(abs(method_ratio).lt.1.E-6))then + method_ratio = & [1._real32, 0.1_real32, 0.5_real32, 0.5_real32, 1._real32] end if @@ -370,11 +370,11 @@ subroutine read_input_file(file_name) end do end if - + do i = 1, 3 cutoff_min_list(i) = read_value_from_string(cutoff_min(i)) - cutoff_max_list(i) = read_value_from_string(cutoff_max(i)) - write(*,*) "Cutoff: ",cutoff_min_list(i),cutoff_max_list(i) + cutoff_max_list(i) = read_value_from_string(cutoff_max(i)) + write(*,*) "Cutoff: ",cutoff_min_list(i),cutoff_max_list(i) end do width_list = width @@ -458,4 +458,4 @@ function read_value_from_string(string) result(output) end function read_value_from_string !############################################################################### -end module inputs \ No newline at end of file +end module inputs diff --git a/app/main.f90 b/app/main.f90 index 60fc5544..40bf8320 100644 --- a/app/main.f90 +++ b/app/main.f90 @@ -126,7 +126,7 @@ program raffle_program write(*,*) "Generating structures" call generator%generate( num_structures, & stoich, & - method_probab ) + method_ratio ) write(*,*) "Structures have been successfully generated" diff --git a/docs/source/index.rst b/docs/source/index.rst index 9b89486a..2776a729 100644 --- a/docs/source/index.rst +++ b/docs/source/index.rst @@ -15,8 +15,10 @@ An example .. code-block:: python - # A simple example of how to use RAFFLE to generate 10 structures of diamond + # A simple example of how to use RAFFLE to generate 10 structures of diamond and write them to a single file from ase import Atoms + from ase.io import write + from ase.calculators.singlepoint import SinglePointCalculator from raffle.generator import raffle_generator from mace.calculators import mace_mp @@ -41,6 +43,16 @@ An example generator.distributions.update(structures[num_structures_old:]) num_structures_old = len(structures) + structures = generator.get_structures(calc) + for structure in structures: + structure.calc = SinglePointCalculator( + structure, + energy=structure.get_potential_energy(), + forces=structure.get_forces() + ) + + write('structures.traj', structures) + .. toctree:: :maxdepth: 3 :caption: Contents: diff --git a/docs/source/install.rst b/docs/source/install.rst index 46428495..aacf74fe 100644 --- a/docs/source/install.rst +++ b/docs/source/install.rst @@ -4,6 +4,23 @@ Installation ============ +For the Python library, the easiest method of installation is to install it directly from pip: + +.. code-block:: bash + + pip install raffle + +or + +.. code-block:: bash + + pip install 'raffle[ase]' + +Once this is done, RAFFLE is ready to be used. + +Alternatively, to install RAFFLE from source, follow the instructions below. + + RAFFLE can be installed in one of three ways; as a Python package, as a Fortran library, or as a standalone Fortran executable. All versions rely on the core Fortran code, with the Python package and standalone executable wrapping this code in a Python and Fortran interface, respectively. diff --git a/docs/source/tutorials/BaTiO3_tutorial.rst b/docs/source/tutorials/BaTiO3_tutorial.rst deleted file mode 100644 index 3c136a68..00000000 --- a/docs/source/tutorials/BaTiO3_tutorial.rst +++ /dev/null @@ -1,5 +0,0 @@ -.. BaTiO3: - -======================== -BaTiO\ :sub:`3` tutorial -======================== diff --git a/docs/source/tutorials/C-MgO_tutorial.rst b/docs/source/tutorials/C-MgO_tutorial.rst deleted file mode 100644 index 7a9b11e3..00000000 --- a/docs/source/tutorials/C-MgO_tutorial.rst +++ /dev/null @@ -1,5 +0,0 @@ -.. C-MgO: - -========================= -Graphene-encapsulated MgO -========================= \ No newline at end of file diff --git a/docs/source/tutorials/Si-Ge_tutorial.rst b/docs/source/tutorials/Si-Ge_tutorial.rst new file mode 100644 index 00000000..2da2b308 --- /dev/null +++ b/docs/source/tutorials/Si-Ge_tutorial.rst @@ -0,0 +1,116 @@ +.. si-ge: + +======================== +Si|Ge interface tutorial +======================== + +This tutorial will guide you through the process of performing RAFFLE-based structure search for an Si|Ge interface. + +The tutorial is designed to show how a RAFFLE generator given no prior knowledge can learn bonding and statistically available interface configurations. +Statistically available configurations are those that are likely to exist due to energetic values close to the ground state, within thermal and entropy conditions. + +The example script can be found in the following directory: + +.. code-block:: bash + + raffle/example/python_pkg/Si-Ge_learn/learn.py + +We recommend reading through the file and running it to understand the process of learning and generating structures. +However, we will provide a brief overview of the script here. + +First, we must import the required packages: + +.. code-block:: python + + from ase import Atoms + from raffle.generator import raffle_generator + from mace.calculators import mace_mp + import numpy as np + +Next, we need to set up the RAFFLE generator and the calculator to calculate the energies of the structures. +In this example, we use the CHGNet calculator: + +.. code-block:: python + + generator = raffle_generator() + + calc = mace_mp(model="mace-mpa-0-medium.model") + +Note, choice of calculator is important. +The calculator should be valid within and near the chemical environment of the structures being generated; in this case, Si and Ge bonding. +If this is the case, it can accurately identify local minima and provide a good representation of the energy landscape. +For this example, we use the [MACE-MPA-0 calculator](https://github.com/ACEsuit/mace-mp/releases/tag/mace_mpa_0), which, from preliminary testing, has been found to be suitable for Si and Ge bonding. +To use the MACE-MPA-0 calculator, you will need to download the model file from the link provided and place it in the same directory as the script (and install the MACE package using `pip install mace-torch`, version 0.3.10 or later). +The CHGNet calculator was not found to be suitable for Si and Ge interface bonding. + +Then, we need to create the host structure. +Here, an abrupt Si|Ge interface is generated. +This is the base structure that will be added to in order to generate the structures. +A vacuum region of 5.54 Å is set up between the Si and Ge regions, in which the atoms will be placed by RAFFLE. + +.. code-block:: python + + Si_bulk = build.bulk("Si", crystalstructure="diamond", a=5.43) + Si_cubic = build.make_supercell(Si_bulk, [[-1, 1, 1], [1, -1, 1], [1, 1, -1]]) + Ge_bulk = build.bulk("Ge", crystalstructure="diamond", a=5.65) + Ge_cubic = build.make_supercell(Ge_bulk, [[-1, 1, 1], [1, -1, 1], [1, 1, -1]]) + + Si_supercell = build.make_supercell(Si_cubic, [[2, 0, 0], [0, 2, 0], [0, 0, 1]]) + Ge_supercell = build.make_supercell(Ge_cubic, [[2, 0, 0], [0, 2, 0], [0, 0, 1]]) + + Si_surface = build.surface(Si_supercell, indices=(0, 0, 1), layers=2) + Ge_surface = build.surface(Ge_supercell, indices=(0, 0, 1), layers=2) + + host = build.stack(Si_surface, Ge_surface, axis=2, distance= 5.43/2 + 5.65/2) + cell[2, 2] -= 3.8865 + host.set_cell(cell, scale_atoms=False) + + +The script then sets parameters for the generator and provides an initial database. +Note, this database only contains prior information of Si-Si and Ge-Ge bonding, and no information about Si-Ge bonding. +This is to demonstrate the ability of RAFFLE to learn from scratch. + +.. code-block:: python + + Si_bulk.calc = calc + Ge_bulk.calc = calc + generator.distributions.set_element_energies( + { + 'Si': Si_bulk.get_potential_energy() / len(Si_bulk), + 'Ge': Ge_bulk.get_potential_energy() / len(Ge_bulk), + } + ) + + # set energy scale + generator.distributions.set_kBT(0.2) + + # set the distribution function widths (2-body, 3-body, 4-body) + generator.distributions.set_width([0.04, np.pi/160.0, np.pi/160.0]) + + # set the initial database + initial_database = [Si_bulk, Ge_bulk] + generator.distributions.create(initial_database) + +Finally, the script generates structures using the generator. +The generator is given the host structures. +Finally, the generator is run for each host structure, providing a unique stoichiometry each time and using a custom method ratio. +The + +.. code-block:: python + + generator.set_host(host) + generator.set_bounds([[0, 0, 0.34], [1, 1, 0.52]]) + for iter in range(40): + # generate the structures + structures, exit_code = generator.generate( + num_structures = 5, + stoichiometry = { 'Si': 16, 'Ge': 16 }, + seed = iter, + method_ratio = {"void": 0.1, "rand": 0.01, "walk": 0.25, "grow": 0.25, "min": 1.0}, + verbose = 0, + calc = calc + ) + generator.distributions.update(structures) + + structures = generator.get_structures() + write('structures.traj', structures) diff --git a/docs/source/tutorials/aluminium_tutorial.rst b/docs/source/tutorials/aluminium_tutorial.rst new file mode 100644 index 00000000..cea6c158 --- /dev/null +++ b/docs/source/tutorials/aluminium_tutorial.rst @@ -0,0 +1,86 @@ +.. aluminium: + +================== +Aluminium tutorial +================== + +This tutorial will guide you through the process of performing RAFFLE-based structure search for the bulk phases of aluminium. + +The tutorial is designed to show how a RAFFLE generator given no prior knowledge can learn bonding and identify known phases. +This is not an expected use-case of RAFFLE due to its application to a bulk system, but still demonstrates the expected workflow and capabilities. + +The example script can be found in the following directory: + +.. code-block:: bash + + raffle/example/python_pkg/Al_learn/learn.py + +We recommend reading through the file and running it to understand the process of learning and generating structures. +However, we will provide a brief overview of the script here. + +First, we must import the required packages: + +.. code-block:: python + + from ase import Atoms + from raffle.generator import raffle_generator + from chgnet.model import CHGNetCalculator + import numpy as np + +Next, we need to set up the RAFFLE generator and the calculator to calculate the energies of the structures. +In this example, we use the CHGNet calculator: + +.. code-block:: python + + generator = raffle_generator() + + calc = CHGNetCalculator() + +Then, we need to create the host structure. +Here, a set of host cells are generated to represent the multiple potential bulk phases of aluminium. +These are then used to generate the structures. + +.. code-block:: python + + crystal_structures = ['orthorhombic', 'hcp'] + hosts = [] + for crystal_structure in crystal_structures: + for a in np.linspace(3.1, 5.4, num=6): + atom = build.bulk( + name = 'Al', + crystalstructure = crystal_structure, + a = a, b = a, c = a, + ) + hosts.append(Atoms( + 'Al', + positions = [(0, 0, 0)], + cell = atom.get_cell(), + pbc = True, + calculator = calc + )) + +The script then sets parameters for the generator and provides an initial database. +Note, this database is effectively empty, as it only contains a single structure, which is an isolated aluminium atom. + +.. code-block:: python + + initial_database = [Atoms('Al', positions=[(0, 0, 0)], cell=[8, 8, 8], pbc=True)] + initial_database[0].calc = calc + generator.distributions.create(initial_database) + +Finally, the script generates structures using the generator. +The generator is given the host structures. +Finally, the generator is run for each host structure, providing a unique stoichiometry each time and using a custom method ratio. + +.. code-block:: python + + for host in hosts: + generator.set_host(host) + generator.generate( + num_structures = 5, + stoichiometry = { 'Al': num_atoms }, + method_ratio = {"void": 0.5, "rand": 0.001, "walk": 0.5, "grow": 0.0, "min": 1.0}, + ) + + structures = generator.get_structures() + write('structures.traj', structures) diff --git a/docs/source/tutorials/diamond_tutorial.rst b/docs/source/tutorials/diamond_tutorial.rst index 21f894dc..90dbb2b8 100644 --- a/docs/source/tutorials/diamond_tutorial.rst +++ b/docs/source/tutorials/diamond_tutorial.rst @@ -1,4 +1,4 @@ -.. diamond: +.. _diamond: ================ Diamond tutorial @@ -20,7 +20,7 @@ This will be used to initialise the generalised distribution functions, which wi Here, we detail two routes: 1) using an ASE object of bulk diamond and 2) using the Materials Project database. Here, we will simply use the ASE object of bulk diamond. -If you wish to use the Materials Project database, please refer to the `Databases tutorial `_. +If you wish to use the Materials Project database, please refer to the :doc:`Databases tutorial `. First, we must import the required packages: @@ -61,7 +61,6 @@ This is the base structure that will be added to in order to generate the struct 3.5607451090903233, 3.5607451090903233, 7.1214902182 ], pbc=True ) - ) host.calc = calc generator.set_host(host) @@ -121,12 +120,12 @@ We are now ready to generate structures using the database of structures. .. code-block:: python num_structures_old = 0 - generator.generate( + structures, exit_code = generator.generate( num_structures = 1, stoichiometry = { 'C': 8 }, - method_probab = {"void":0.0001, "min":1.0}, + method_ratio = {"void":0.0001, "min":1.0}, + calc = calc ) - structures = generator.get_structures(calc) We should now have a structure of diamond. This structure can be visualised using the ASE package. diff --git a/docs/source/tutorials/graphite_tutorial.rst b/docs/source/tutorials/graphite_tutorial.rst index 0a2e6aa4..1748b1da 100644 --- a/docs/source/tutorials/graphite_tutorial.rst +++ b/docs/source/tutorials/graphite_tutorial.rst @@ -2,4 +2,128 @@ ================= Graphite tutorial -================= \ No newline at end of file +================= + +This tutorial will guide you through the process of reconstructing graphite from a defected graphite cell (one missing layer). +This tutorial follows the same structure as the :doc:`Diamond tutorial `. + +The tutorial is designed to show how RAFFLE learns from a database and uses this information to generate structures. +This is not an expected use-case of RAFFLE, but merely a demonstration of its capabilities to rebuild a structure from a defected cell. + +The example files can be found in the following directory: + +.. code-block:: bash + + raffle/example/python_pkg/graphite + +First, we need to establish an initial database of structures. +This will be used to initialise the generalised distribution functions, which will inform the placement of atoms in the generated structures. +Here, we detail two routes: 1) using an ASE object of bulk graphite and 2) using the Materials Project database. + +Here, we will simply use the ASE object of bulk graphite. +If you wish to use the Materials Project database, please refer to the :doc:`Databases tutorial `. + +First, we must import the required packages: + +.. code-block:: python + + from ase import Atoms + from raffle.generator import raffle_generator + from mace.calculators import mace_mp + import numpy as np + +Next, we need to set up the RAFFLE generator and the calculator to calculate the energies of the structures. +In this example, we use the MACE-MP-0 calculator: + +.. code-block:: python + + generator = raffle_generator() + + calc = mace_mp(model="medium", dispersion=False, default_dtype="float32", device='cpu') + + +Then, we need to create the host structure. +This is the base structure that will be added to in order to generate the structures. + +.. code-block:: python + + host = Atoms( + "C6", + scaled_positions=[ + [0.000000000, 0.000000000, 0.125000000], + [0.000000000, 0.000000000, 0.375000000], + [0.000000000, 0.000000000, 0.875000000], + [0.333333333, 0.666666667, 0.125000000], + [0.666666667, 0.333333333, 0.375000000], + [0.666666667, 0.333333333, 0.875000000], + ], cell=[ + 2.4672912616, 2.4672912616, 15.606146000 + ], pbc=True + ) + + host.calc = calc + generator.set_host(host) + +Next, we need to set any variables we want to use for the distributions. +None should be required other than the element energies, which will be used as reference energies to calculate the formation energies of the structures. +However, for completeness, we will set other variables here. +Because there is only one element in this structure, the reference energy is meaningless, so we set it to ``0.0`` here. +This is due to all structures will have the same stoichiometry and thus use the exact same reference energy, so choice of this value is a global shift. + +.. code-block:: python + + generator.distributions.set_element_energies( { 'C': 0.0 } ) + generator.distributions.set_kBT(0.2) + generator.distributions.set_width([0.025, np.pi/200.0, np.pi/200.0]) + generator.distributions.set_radius_distance_tol([1.5, 2.5, 3.0, 6.0]) + +Now we need to generate the database of structures. +We will provide bulk diamond as the only database entry here. + +.. code-block:: python + + database = [] + database.append( + Atoms("C4", + positions=[ + [0.0, 0.0, 1.95076825], + [0.0, 0.0, 5.85230475], + [1.2336456308015413, 0.7122456370278755, 1.95076825], + [1.2336456308015415, -0.7122456370278757, 5.85230475] + ], cell=[ + [1.2336456308015413, -2.1367369110836267, 0.0], + [1.2336456308015413, 2.1367369110836267, 0.0], + [0.0, 0.0, 7.803073] + ], pbc=True + ) + ) + +This database will now be used to initialise the generalised distribution functions in RAFFLE. + +.. code-block:: python + + generator.distributions.create(database) + +Finally, we can set the grid on which atom searches are performed (this grid is applied to the host cell). +By default, the grid is generated using a spacing of 0.1 Å. + +.. code-block:: python + + generator.set_grid(grid_spacing=0.1, grid_offset=[0.0, 0.0, 0.0]) + +We are now ready to generate structures using the database of structures. + +.. code-block:: python + + num_structures_old = 0 + structures, status = generator.generate( + num_structures = 1, + stoichiometry = { 'C': 2 }, + method_ratio = {"void":0.0001, "min":1.0}, + calc = calc + ) + +We should now have a structure of layered graphite. +This structure can be visualised using the ASE package. +But this can also be verified energetically. +The generated structure should have double the energy of bulk graphite, found in ```database[0]```. \ No newline at end of file diff --git a/docs/source/tutorials/index.rst b/docs/source/tutorials/index.rst index e0bb1311..6f458851 100644 --- a/docs/source/tutorials/index.rst +++ b/docs/source/tutorials/index.rst @@ -18,6 +18,5 @@ Whilst RAFFLE is a random sturcture search package designed primarlily for inter databases_tutorial diamond_tutorial graphite_tutorial - BaTiO3_tutorial - perovskites_tutorial - C-MgO_tutorial + aluminium_tutorial + Si-Ge_tutorial diff --git a/docs/source/tutorials/perovskites_tutorial.rst b/docs/source/tutorials/perovskites_tutorial.rst deleted file mode 100644 index d378b21f..00000000 --- a/docs/source/tutorials/perovskites_tutorial.rst +++ /dev/null @@ -1,5 +0,0 @@ -.. perovskites: - -==================================================== -BaTiO\ :sub:`3`\|SrTiO\ :sub:`3` interface tutorial -==================================================== \ No newline at end of file diff --git a/example/python_pkg/Al_learn/DRAFFLE/DOutput/energies_rlxd_seed0.txt b/example/python_pkg/Al_learn/DRAFFLE/DOutput/energies_rlxd_seed0.txt new file mode 100644 index 00000000..718c6bb6 --- /dev/null +++ b/example/python_pkg/Al_learn/DRAFFLE/DOutput/energies_rlxd_seed0.txt @@ -0,0 +1,1200 @@ +0 -3.5716137886047363 +1 -3.5715627670288086 +2 -3.5716135501861572 +3 -3.5716137886047363 +4 -3.5716135501861572 +5 -3.1652393341064453 +6 -3.1652517318725586 +7 -3.1651487350463867 +8 -3.165148973464966 +9 -3.165148973464966 +10 -3.6630747318267822 +11 -3.663264513015747 +12 -3.663318157196045 +13 -3.6631953716278076 +14 -3.663180351257324 +15 -3.4232192039489746 +16 -3.4232325553894043 +17 -3.423236131668091 +18 -3.423246383666992 +19 -3.42323637008667 +20 -3.601855754852295 +21 -3.601801633834839 +22 -3.601071834564209 +23 -3.5707027912139893 +24 -3.588728189468384 +25 -3.6210718154907227 +26 -3.62060546875 +27 -3.6208720207214355 +28 -3.6209614276885986 +29 -3.6211633682250977 +30 -2.821124315261841 +31 -2.8210995197296143 +32 -2.821117401123047 +33 -2.82112455368042 +34 -2.8210971355438232 +35 -3.507002592086792 +36 -3.506941556930542 +37 -3.5070369243621826 +38 -3.5070018768310547 +39 -3.5070371627807617 +40 -3.4776599407196045 +41 -3.477694272994995 +42 -3.231524705886841 +43 -3.4776809215545654 +44 -3.477694272994995 +45 -3.449756145477295 +46 -3.4498302936553955 +47 -3.449821949005127 +48 -3.449744701385498 +49 -3.4100518226623535 +50 -3.6584155559539795 +51 -3.65523624420166 +52 -3.655170202255249 +53 -3.6550159454345703 +54 -3.6549179553985596 +55 -3.6499762535095215 +56 -3.6487932205200195 +57 -3.6455790996551514 +58 -3.6478114128112793 +59 -3.6497392654418945 +60 -3.571617841720581 +61 -3.571525812149048 +62 -3.571617841720581 +63 -3.571617841720581 +64 -3.571617841720581 +65 -3.165250778198242 +66 -3.1653385162353516 +67 -3.1652157306671143 +68 -3.16532826423645 +69 -3.1652305126190186 +70 -3.6631038188934326 +71 -3.6632256507873535 +72 -3.6633903980255127 +73 -3.6632139682769775 +74 -3.663205146789551 +75 -3.423287868499756 +76 -3.423185348510742 +77 -3.4232280254364014 +78 -3.423247814178467 +79 -3.2763075828552246 +80 -3.5885684490203857 +81 -3.6008121967315674 +82 -3.60058331489563 +83 -3.5886690616607666 +84 -3.5887506008148193 +85 -3.6210153102874756 +86 -3.6210110187530518 +87 -3.6209869384765625 +88 -3.62079119682312 +89 -3.6212375164031982 +90 -2.8210976123809814 +91 -2.8211073875427246 +92 -2.8211145401000977 +93 -2.8210999965667725 +94 -2.8210973739624023 +95 -3.5070369243621826 +96 -3.5070173740386963 +97 -3.236889123916626 +98 -3.236888885498047 +99 -3.236888885498047 +100 -3.4777276515960693 +101 -3.2315244674682617 +102 -3.2312707901000977 +103 -2.5505456924438477 +104 -3.4776971340179443 +105 -3.4100661277770996 +106 -3.449841260910034 +107 -3.449822187423706 +108 -3.4498190879821777 +109 -3.4498183727264404 +110 -3.6549980640411377 +111 -3.6565351486206055 +112 -3.6558916568756104 +113 -3.6587512493133545 +114 -3.6546266078948975 +115 -3.6391003131866455 +116 -3.6458659172058105 +117 -3.649670124053955 +118 -3.647498369216919 +119 -3.6491167545318604 +120 -3.571617603302002 +121 -3.5715553760528564 +122 -3.571617603302002 +123 -3.571617603302002 +124 -3.571617603302002 +125 -3.165212631225586 +126 -3.1652462482452393 +127 -2.340482234954834 +128 -3.1653316020965576 +129 -3.1653106212615967 +130 -3.6628899574279785 +131 -3.272861957550049 +132 -3.6628124713897705 +133 -3.6631059646606445 +134 -3.663093090057373 +135 -3.423293352127075 +136 -3.404693126678467 +137 -3.4231815338134766 +138 -3.253333330154419 +139 -3.423215389251709 +140 -3.5886332988739014 +141 -3.601760149002075 +142 -3.6018645763397217 +143 -3.588876247406006 +144 -3.6016685962677 +145 -3.604057788848877 +146 -3.621320962905884 +147 -3.621098518371582 +148 -3.620966672897339 +149 -3.6203434467315674 +150 -2.1230642795562744 +151 -2.821120262145996 +152 -2.8210973739624023 +153 -2.1230642795562744 +154 -2.1230642795562744 +155 -3.236888885498047 +156 -3.5069336891174316 +157 -3.5069901943206787 +158 -3.506939172744751 +159 -3.236888885498047 +160 -3.4776084423065186 +161 -3.4776508808135986 +162 -3.4776546955108643 +163 -3.2312707901000977 +164 -2.5505456924438477 +165 -3.449843645095825 +166 -3.449733018875122 +167 -3.4498062133789062 +168 -3.449671506881714 +169 -3.4498322010040283 +170 -3.6570043563842773 +171 -3.654799461364746 +172 -3.6571662425994873 +173 -3.6565029621124268 +174 -3.655885696411133 +175 -3.647756576538086 +176 -3.648719310760498 +177 -3.6452722549438477 +178 -3.647303819656372 +179 -3.6487183570861816 +180 -3.571617603302002 +181 -3.571594476699829 +182 -3.5715861320495605 +183 -3.571617603302002 +184 -3.571617603302002 +185 -3.16532039642334 +186 -2.340481758117676 +187 -3.165311098098755 +188 -3.1651909351348877 +189 -3.1653354167938232 +190 -3.663292169570923 +191 -3.6633758544921875 +192 -3.6632044315338135 +193 -3.6628854274749756 +194 -3.6632046699523926 +195 -3.4232165813446045 +196 -3.4232780933380127 +197 -3.4231960773468018 +198 -3.4232535362243652 +199 -3.2764201164245605 +200 -3.601950168609619 +201 -3.601685047149658 +202 -3.6012823581695557 +203 -3.6017189025878906 +204 -3.601862668991089 +205 -3.620990753173828 +206 -3.6209704875946045 +207 -3.6208741664886475 +208 -3.606673002243042 +209 -3.601080894470215 +210 -2.1230640411376953 +211 -2.821101188659668 +212 -2.8211090564727783 +213 -2.1230640411376953 +214 -2.1230640411376953 +215 -3.236888885498047 +216 -3.5069243907928467 +217 -3.236889123916626 +218 -3.506969928741455 +219 -3.5069708824157715 +220 -3.4777209758758545 +221 -3.4777286052703857 +222 -2.550546169281006 +223 -3.47769832611084 +224 -2.5505456924438477 +225 -3.4497342109680176 +226 -3.410092830657959 +227 -3.4025015830993652 +228 -3.4497573375701904 +229 -3.449688673019409 +230 -3.65710186958313 +231 -3.6569206714630127 +232 -3.6570465564727783 +233 -3.657693862915039 +234 -3.655339241027832 +235 -3.6449382305145264 +236 -3.649230480194092 +237 -3.6490492820739746 +238 -3.649911403656006 +239 -3.6473805904388428 +240 -3.571617841720581 +241 -3.5715200901031494 +242 -3.571617841720581 +243 -3.5715627670288086 +244 -3.571617841720581 +245 -3.165332794189453 +246 -3.165147066116333 +247 -3.165175437927246 +248 -3.1653318405151367 +249 -2.3404831886291504 +250 -3.2728183269500732 +251 -3.6633591651916504 +252 -3.6633758544921875 +253 -3.2728612422943115 +254 -3.6633763313293457 +255 -3.423203945159912 +256 -3.423222064971924 +257 -3.4232192039489746 +258 -3.276106357574463 +259 -3.4232096672058105 +260 -3.601749897003174 +261 -3.5889391899108887 +262 -3.588897228240967 +263 -3.6016080379486084 +264 -3.601713180541992 +265 -3.6209471225738525 +266 -3.620558500289917 +267 -3.6207873821258545 +268 -3.6209661960601807 +269 -3.620965003967285 +270 -2.8210973739624023 +271 -2.8211071491241455 +272 -2.1230640411376953 +273 -2.1230642795562744 +274 -2.8210973739624023 +275 -3.5070369243621826 +276 -3.5070106983184814 +277 -3.5070343017578125 +278 -3.236888885498047 +279 -3.506995677947998 +280 -3.4777066707611084 +281 -3.4775707721710205 +282 -3.2312233448028564 +283 -3.4777021408081055 +284 -3.4776480197906494 +285 -3.4498062133789062 +286 -3.409766674041748 +287 -3.449841260910034 +288 -3.449561595916748 +289 -3.4498372077941895 +290 -3.6553337574005127 +291 -3.6579246520996094 +292 -3.655064344406128 +293 -3.6550891399383545 +294 -3.656351089477539 +295 -3.648447036743164 +296 -3.646556854248047 +297 -3.6475963592529297 +298 -3.645359992980957 +299 -3.647789716720581 +300 -3.5716121196746826 +301 -3.571617841720581 +302 -3.571617841720581 +303 -3.571617841720581 +304 -3.571617841720581 +305 -3.1652820110321045 +306 -3.1651389598846436 +307 -3.1653318405151367 +308 -2.3404855728149414 +309 -2.340484142303467 +310 -3.6628332138061523 +311 -3.2728402614593506 +312 -3.663398027420044 +313 -3.272840976715088 +314 -3.663412094116211 +315 -3.4232869148254395 +316 -3.253333330154419 +317 -3.4232068061828613 +318 -3.4232029914855957 +319 -3.4232325553894043 +320 -3.588754177093506 +321 -3.6018078327178955 +322 -3.570457696914673 +323 -3.601551055908203 +324 -3.558896780014038 +325 -3.60489559173584 +326 -3.6210474967956543 +327 -3.6208207607269287 +328 -3.6204893589019775 +329 -3.6206066608428955 +330 -2.821096897125244 +331 -2.8210973739624023 +332 -2.1230640411376953 +333 -2.1230640411376953 +334 -2.1230640411376953 +335 -3.507006883621216 +336 -3.5070364475250244 +337 -3.236888885498047 +338 -3.236888885498047 +339 -3.236889123916626 +340 -3.477736473083496 +341 -2.550546169281006 +342 -3.2312231063842773 +343 -2.5505456924438477 +344 -3.2315244674682617 +345 -3.4497809410095215 +346 -3.449795961380005 +347 -3.44974946975708 +348 -3.409297227859497 +349 -3.4497058391571045 +350 -3.6584136486053467 +351 -3.6586716175079346 +352 -3.657674789428711 +353 -3.6540451049804688 +354 -3.655919313430786 +355 -3.64967679977417 +356 -3.64894962310791 +357 -3.6505136489868164 +358 -3.6468591690063477 +359 -3.648402452468872 +360 -3.571617841720581 +361 -3.5715508460998535 +362 -3.571617603302002 +363 -3.571617603302002 +364 -3.571537733078003 +365 -3.1652462482452393 +366 -3.165127992630005 +367 -3.1652228832244873 +368 -3.1651389598846436 +369 -3.1653318405151367 +370 -3.663093328475952 +371 -3.6632704734802246 +372 -3.6630935668945312 +373 -3.2728207111358643 +374 -3.6631007194519043 +375 -3.2763524055480957 +376 -3.4221062660217285 +377 -3.423243761062622 +378 -3.4232261180877686 +379 -3.2762131690979004 +380 -3.6011252403259277 +381 -3.6016082763671875 +382 -3.570615291595459 +383 -3.6017420291900635 +384 -3.5959079265594482 +385 -3.6210203170776367 +386 -3.600931406021118 +387 -3.6207385063171387 +388 -3.6023759841918945 +389 -3.601595640182495 +390 -2.1230642795562744 +391 -2.82110595703125 +392 -2.1230642795562744 +393 -2.821107864379883 +394 -2.1230642795562744 +395 -3.236889123916626 +396 -3.506993293762207 +397 -3.236888885498047 +398 -3.236888885498047 +399 -3.236888885498047 +400 -3.4776926040649414 +401 -3.2312705516815186 +402 -3.231524705886841 +403 -3.4776041507720947 +404 -3.477733850479126 +405 -3.4498062133789062 +406 -3.4496803283691406 +407 -3.449739933013916 +408 -3.4497954845428467 +409 -3.4497649669647217 +410 -3.6576039791107178 +411 -3.655805826187134 +412 -3.6581785678863525 +413 -3.6580865383148193 +414 -3.655064344406128 +415 -3.6450576782226562 +416 -3.6488234996795654 +417 -3.64688777923584 +418 -3.6446759700775146 +419 -3.6477954387664795 +420 -3.571617841720581 +421 -3.571540594100952 +422 -3.571617841720581 +423 -3.571603775024414 +424 -3.571617841720581 +425 -3.1653225421905518 +426 -3.1651909351348877 +427 -3.1651389598846436 +428 -2.340482234954834 +429 -3.1651389598846436 +430 -3.2728610038757324 +431 -3.663111686706543 +432 -3.66310977935791 +433 -3.663205146789551 +434 -3.663233995437622 +435 -3.2762179374694824 +436 -3.2762093544006348 +437 -3.4232566356658936 +438 -3.4218850135803223 +439 -3.4231903553009033 +440 -3.588719129562378 +441 -3.5888679027557373 +442 -3.601778030395508 +443 -3.588777542114258 +444 -3.519819736480713 +445 -3.620469331741333 +446 -3.6210529804229736 +447 -3.6019160747528076 +448 -3.6213297843933105 +449 -3.621068000793457 +450 -2.8210973739624023 +451 -2.821108818054199 +452 -2.1230640411376953 +453 -2.821110248565674 +454 -2.1230640411376953 +455 -3.5070371627807617 +456 -3.50701642036438 +457 -3.5070371627807617 +458 -3.236888885498047 +459 -3.236889123916626 +460 -3.477597236633301 +461 -3.4774763584136963 +462 -3.477670669555664 +463 -2.5505456924438477 +464 -3.2312231063842773 +465 -3.4498062133789062 +466 -3.449805736541748 +467 -3.4497978687286377 +468 -3.4496092796325684 +469 -3.4498372077941895 +470 -3.655604124069214 +471 -3.6581695079803467 +472 -3.6550910472869873 +473 -3.658266067504883 +474 -3.6543216705322266 +475 -3.646261692047119 +476 -3.6453568935394287 +477 -3.6490426063537598 +478 -3.648223638534546 +479 -3.6501007080078125 +480 -3.5716028213500977 +481 -3.571617841720581 +482 -3.571575164794922 +483 -3.5715527534484863 +484 -3.571617841720581 +485 -3.1651344299316406 +486 -2.3404831886291504 +487 -2.340484142303467 +488 -3.165156602859497 +489 -3.165302276611328 +490 -3.6634573936462402 +491 -3.6631617546081543 +492 -3.6633951663970947 +493 -3.663228750228882 +494 -3.6632046699523926 +495 -3.423243761062622 +496 -3.423262119293213 +497 -3.421663761138916 +498 -3.423274517059326 +499 -3.4227747917175293 +500 -3.588698148727417 +501 -3.601435422897339 +502 -3.6016199588775635 +503 -3.6009678840637207 +504 -3.5888588428497314 +505 -3.62088942527771 +506 -3.6211183071136475 +507 -3.621020793914795 +508 -3.5827908515930176 +509 -3.62100887298584 +510 -2.8211145401000977 +511 -2.8211114406585693 +512 -2.8210973739624023 +513 -2.8210973739624023 +514 -2.821110725402832 +515 -3.5069637298583984 +516 -3.5070371627807617 +517 -3.236888885498047 +518 -3.507068634033203 +519 -3.236889362335205 +520 -3.4775054454803467 +521 -3.2312705516815186 +522 -2.5505456924438477 +523 -3.4775123596191406 +524 -3.477736234664917 +525 -3.4497618675231934 +526 -3.4498276710510254 +527 -3.449751377105713 +528 -3.4498085975646973 +529 -3.449718952178955 +530 -3.655341863632202 +531 -3.6585865020751953 +532 -3.655541181564331 +533 -3.657862424850464 +534 -3.658381700515747 +535 -3.650303602218628 +536 -3.649017572402954 +537 -3.6477208137512207 +538 -3.6432180404663086 +539 -3.6343140602111816 +540 -3.571617603302002 +541 -3.571587324142456 +542 -3.571591854095459 +543 -3.5715458393096924 +544 -3.571617603302002 +545 -3.165337562561035 +546 -3.1652097702026367 +547 -2.340482711791992 +548 -3.1651580333709717 +549 -3.165292739868164 +550 -3.662942409515381 +551 -3.662931203842163 +552 -3.6630098819732666 +553 -3.6631219387054443 +554 -3.6630873680114746 +555 -3.4232165813446045 +556 -3.276210069656372 +557 -3.4232592582702637 +558 -3.423182964324951 +559 -3.276383876800537 +560 -3.6015701293945312 +561 -3.5886478424072266 +562 -3.6018917560577393 +563 -3.5887033939361572 +564 -3.5888023376464844 +565 -3.620833158493042 +566 -3.603971242904663 +567 -3.620839834213257 +568 -3.6211225986480713 +569 -3.601818561553955 +570 -2.1230640411376953 +571 -2.821117401123047 +572 -2.1230640411376953 +573 -2.1230640411376953 +574 -2.1230640411376953 +575 -3.236889123916626 +576 -3.5070748329162598 +577 -3.5070674419403076 +578 -3.236889123916626 +579 -3.507070302963257 +580 -3.4776923656463623 +581 -2.5505456924438477 +582 -3.4774796962738037 +583 -3.4774796962738037 +584 -2.5505456924438477 +585 -3.449688673019409 +586 -3.4496169090270996 +587 -3.44981050491333 +588 -3.449821949005127 +589 -3.449664354324341 +590 -3.657954454421997 +591 -3.6580591201782227 +592 -3.6557862758636475 +593 -3.6574313640594482 +594 -3.6553614139556885 +595 -3.64878249168396 +596 -3.6484737396240234 +597 -3.6351513862609863 +598 -3.6490893363952637 +599 -3.647813081741333 +600 -3.571617603302002 +601 -3.5715839862823486 +602 -3.571617603302002 +603 -3.571617603302002 +604 -3.571617603302002 +605 -3.16532826423645 +606 -3.1651251316070557 +607 -2.3404831886291504 +608 -3.1651909351348877 +609 -2.340482234954834 +610 -3.6632046699523926 +611 -3.663255214691162 +612 -3.6634247303009033 +613 -3.663228750228882 +614 -3.6629831790924072 +615 -3.4222359657287598 +616 -3.276268482208252 +617 -3.4231982231140137 +618 -3.423264741897583 +619 -3.4231743812561035 +620 -3.5885748863220215 +621 -3.5889065265655518 +622 -3.6008312702178955 +623 -3.5888028144836426 +624 -3.5889110565185547 +625 -3.602971315383911 +626 -3.620955228805542 +627 -3.62084698677063 +628 -3.6210598945617676 +629 -3.6205008029937744 +630 -2.8210973739624023 +631 -2.821115016937256 +632 -2.1230642795562744 +633 -2.8211121559143066 +634 -2.821103572845459 +635 -3.5070366859436035 +636 -3.5069847106933594 +637 -3.236888885498047 +638 -3.507000207901001 +639 -3.507037401199341 +640 -3.477703332901001 +641 -3.2312707901000977 +642 -3.4775640964508057 +643 -2.550546646118164 +644 -3.2312705516815186 +645 -3.449749708175659 +646 -3.4498183727264404 +647 -3.4025402069091797 +648 -3.449735641479492 +649 -3.4497973918914795 +650 -3.657486915588379 +651 -3.657686233520508 +652 -3.6568305492401123 +653 -3.655820846557617 +654 -3.655428886413574 +655 -3.6507420539855957 +656 -3.6483325958251953 +657 -3.6479241847991943 +658 -3.6484081745147705 +659 -3.6486799716949463 +660 -3.5716147422790527 +661 -3.571617603302002 +662 -3.5716145038604736 +663 -3.571617603302002 +664 -3.571617603302002 +665 -3.165295362472534 +666 -3.165225028991699 +667 -3.1650772094726562 +668 -3.1651296615600586 +669 -3.1653316020965576 +670 -3.272860050201416 +671 -3.6630966663360596 +672 -3.663254499435425 +673 -3.663093328475952 +674 -3.663238525390625 +675 -3.4231858253479004 +676 -3.423203229904175 +677 -3.4227683544158936 +678 -3.4229893684387207 +679 -3.4231581687927246 +680 -3.601200819015503 +681 -3.5888900756835938 +682 -3.6017444133758545 +683 -3.5835330486297607 +684 -3.601715564727783 +685 -3.6213150024414062 +686 -3.620697498321533 +687 -3.6208348274230957 +688 -3.6210086345672607 +689 -3.6021690368652344 +690 -2.8211190700531006 +691 -2.8211193084716797 +692 -2.1230640411376953 +693 -2.8210980892181396 +694 -2.1230640411376953 +695 -3.5069921016693115 +696 -3.236889123916626 +697 -3.507045030593872 +698 -3.506930112838745 +699 -3.5069661140441895 +700 -3.4776289463043213 +701 -3.231524705886841 +702 -3.477548360824585 +703 -3.4776275157928467 +704 -3.4776837825775146 +705 -3.4498467445373535 +706 -3.4498062133789062 +707 -3.44974946975708 +708 -3.411095380783081 +709 -3.410107135772705 +710 -3.6585798263549805 +711 -3.6567599773406982 +712 -3.6578807830810547 +713 -3.6557257175445557 +714 -3.58199405670166 +715 -3.647224187850952 +716 -3.6487603187561035 +717 -3.6461431980133057 +718 -3.6503543853759766 +719 -3.6481072902679443 +720 -3.571617841720581 +721 -3.571537971496582 +722 -3.571617841720581 +723 -3.571617841720581 +724 -3.571617841720581 +725 -3.1651830673217773 +726 -3.1653316020965576 +727 -2.340484142303467 +728 -3.1653316020965576 +729 -3.1653318405151367 +730 -3.6631319522857666 +731 -3.6633760929107666 +732 -3.6630778312683105 +733 -3.6632955074310303 +734 -3.6631226539611816 +735 -3.4232401847839355 +736 -3.4231600761413574 +737 -3.423276424407959 +738 -3.42321515083313 +739 -3.423264265060425 +740 -3.6016132831573486 +741 -3.5883641242980957 +742 -3.6016201972961426 +743 -3.5885024070739746 +744 -3.601062059402466 +745 -3.6211864948272705 +746 -3.621100425720215 +747 -3.6209123134613037 +748 -3.6012449264526367 +749 -3.6210131645202637 +750 -2.1230642795562744 +751 -2.82110595703125 +752 -2.1230642795562744 +753 -2.8210973739624023 +754 -2.1230642795562744 +755 -3.236888885498047 +756 -3.2369086742401123 +757 -3.236888885498047 +758 -3.5070064067840576 +759 -3.5070080757141113 +760 -3.4775867462158203 +761 -2.5505452156066895 +762 -2.5505456924438477 +763 -3.477684259414673 +764 -3.477710008621216 +765 -3.449657917022705 +766 -3.449817657470703 +767 -3.449805736541748 +768 -3.4496498107910156 +769 -3.449700117111206 +770 -3.655259847640991 +771 -3.6572182178497314 +772 -3.6547977924346924 +773 -3.65856671333313 +774 -3.6583375930786133 +775 -3.6463894844055176 +776 -3.646596908569336 +777 -3.650233030319214 +778 -3.644831657409668 +779 -3.6434903144836426 +780 -3.571617603302002 +781 -3.5715250968933105 +782 -3.5715584754943848 +783 -3.571617603302002 +784 -3.5715279579162598 +785 -3.1652138233184814 +786 -3.165328025817871 +787 -3.1653318405151367 +788 -3.165339231491089 +789 -2.340484619140625 +790 -3.66329288482666 +791 -3.272861957550049 +792 -3.662963390350342 +793 -3.6631698608398438 +794 -3.66328763961792 +795 -3.4232616424560547 +796 -3.276141405105591 +797 -3.423184871673584 +798 -3.423203229904175 +799 -3.423201084136963 +800 -3.588879108428955 +801 -3.5889079570770264 +802 -3.588858127593994 +803 -3.570490598678589 +804 -3.601654052734375 +805 -3.6209707260131836 +806 -3.6210508346557617 +807 -3.601168394088745 +808 -3.620689868927002 +809 -3.605241537094116 +810 -2.1230640411376953 +811 -2.8211185932159424 +812 -2.8211216926574707 +813 -2.1230640411376953 +814 -2.1230640411376953 +815 -3.236889123916626 +816 -3.5069615840911865 +817 -3.5070369243621826 +818 -3.236888885498047 +819 -3.5070369243621826 +820 -3.477595567703247 +821 -2.5505456924438477 +822 -3.4776875972747803 +823 -3.477725028991699 +824 -3.2312233448028564 +825 -3.449671506881714 +826 -3.4495577812194824 +827 -3.449754238128662 +828 -3.410080671310425 +829 -3.4495463371276855 +830 -3.6548798084259033 +831 -3.6572329998016357 +832 -3.656057357788086 +833 -3.6584274768829346 +834 -3.658681869506836 +835 -3.647397041320801 +836 -3.6474595069885254 +837 -3.6466469764709473 +838 -3.647390365600586 +839 -3.6472394466400146 +840 -3.571599245071411 +841 -3.571617841720581 +842 -3.571617841720581 +843 -3.571617841720581 +844 -3.571617841720581 +845 -3.1653125286102295 +846 -3.1651599407196045 +847 -3.1653318405151367 +848 -3.1651909351348877 +849 -3.1652157306671143 +850 -3.663191795349121 +851 -3.663315773010254 +852 -3.6630940437316895 +853 -3.6632044315338135 +854 -3.6631059646606445 +855 -3.4232590198516846 +856 -3.423203706741333 +857 -3.423203229904175 +858 -3.4232020378112793 +859 -3.4232494831085205 +860 -3.570551633834839 +861 -3.5887374877929688 +862 -3.601039409637451 +863 -3.6018452644348145 +864 -3.601754665374756 +865 -3.6208348274230957 +866 -3.6207990646362305 +867 -3.6212282180786133 +868 -3.601935386657715 +869 -3.6212093830108643 +870 -2.8211092948913574 +871 -2.1230640411376953 +872 -2.82110595703125 +873 -2.8210973739624023 +874 -2.1230640411376953 +875 -3.5070276260375977 +876 -3.5070369243621826 +877 -3.236889123916626 +878 -3.236889123916626 +879 -3.5070371627807617 +880 -3.477508544921875 +881 -3.2312231063842773 +882 -3.2312233448028564 +883 -2.550546169281006 +884 -3.477471113204956 +885 -3.449705123901367 +886 -3.449744701385498 +887 -3.449712038040161 +888 -3.4498229026794434 +889 -3.4497368335723877 +890 -3.658459424972534 +891 -3.658611297607422 +892 -3.6568849086761475 +893 -3.656935930252075 +894 -3.6558916568756104 +895 -3.6498680114746094 +896 -3.6463170051574707 +897 -3.6496496200561523 +898 -3.6489343643188477 +899 -3.6469836235046387 +900 -3.571617841720581 +901 -3.5715956687927246 +902 -3.571617841720581 +903 -3.571566104888916 +904 -3.571526288986206 +905 -3.1651744842529297 +906 -3.1653034687042236 +907 -3.1653239727020264 +908 -3.1651382446289062 +909 -3.16532039642334 +910 -3.6631526947021484 +911 -3.663184404373169 +912 -3.6631932258605957 +913 -3.6632044315338135 +914 -3.663360834121704 +915 -3.423142910003662 +916 -3.423264265060425 +917 -3.4053916931152344 +918 -3.4231905937194824 +919 -3.423161029815674 +920 -3.6014697551727295 +921 -3.5885937213897705 +922 -3.601090908050537 +923 -3.5886459350585938 +924 -3.6018624305725098 +925 -3.6210148334503174 +926 -3.6211090087890625 +927 -3.6207685470581055 +928 -3.6021358966827393 +929 -3.60131573677063 +930 -2.1230642795562744 +931 -2.8211143016815186 +932 -2.821104049682617 +933 -2.8210971355438232 +934 -2.1230642795562744 +935 -3.236888885498047 +936 -3.507047176361084 +937 -3.5070605278015137 +938 -3.236889362335205 +939 -3.5069541931152344 +940 -3.477595329284668 +941 -3.477572202682495 +942 -3.477708101272583 +943 -3.2312705516815186 +944 -3.2312231063842773 +945 -3.4100375175476074 +946 -3.4498462677001953 +947 -3.449766159057617 +948 -3.449733018875122 +949 -3.449841260910034 +950 -3.656477928161621 +951 -3.658452272415161 +952 -3.658599615097046 +953 -3.655763626098633 +954 -3.6584348678588867 +955 -3.6479310989379883 +956 -3.6509671211242676 +957 -3.6469366550445557 +958 -3.6503353118896484 +959 -3.634552478790283 +960 -3.571617841720581 +961 -3.571617841720581 +962 -3.571617841720581 +963 -3.571617841720581 +964 -3.571617841720581 +965 -3.165311098098755 +966 -3.1653194427490234 +967 -2.6274352073669434 +968 -3.165127992630005 +969 -3.1652958393096924 +970 -3.6630232334136963 +971 -3.272841453552246 +972 -3.6632747650146484 +973 -3.663365602493286 +974 -3.663205146789551 +975 -3.423095226287842 +976 -3.4052207469940186 +977 -3.42329478263855 +978 -3.4231879711151123 +979 -3.2759315967559814 +980 -3.6017661094665527 +981 -3.5887374877929688 +982 -3.588864803314209 +983 -3.601865768432617 +984 -3.5886638164520264 +985 -3.6017863750457764 +986 -3.620697498321533 +987 -3.6208386421203613 +988 -3.5825021266937256 +989 -3.620919942855835 +990 -2.1230642795562744 +991 -2.1230642795562744 +992 -2.1230642795562744 +993 -2.1230642795562744 +994 -2.1230642795562744 +995 -3.236889123916626 +996 -3.236889123916626 +997 -3.236888885498047 +998 -3.236889123916626 +999 -3.236889123916626 +1000 -3.47757887840271 +1001 -3.2316970825195312 +1002 -2.550546169281006 +1003 -2.550546169281006 +1004 -3.2316970825195312 +1005 -3.4496264457702637 +1006 -3.4496707916259766 +1007 -3.449749708175659 +1008 -3.410034656524658 +1009 -3.449842929840088 +1010 -3.658482551574707 +1011 -3.584578275680542 +1012 -3.655841827392578 +1013 -3.6542294025421143 +1014 -3.656132936477661 +1015 -3.6475744247436523 +1016 -3.6486976146698 +1017 -3.647439479827881 +1018 -3.6474392414093018 +1019 -3.648254156112671 +1020 -3.571617603302002 +1021 -3.571617603302002 +1022 -3.571617603302002 +1023 -3.571617603302002 +1024 -3.571617603302002 +1025 -3.1653013229370117 +1026 -3.1653079986572266 +1027 -3.165266752243042 +1028 -3.165144920349121 +1029 -2.627434730529785 +1030 -3.2728428840637207 +1031 -3.663501501083374 +1032 -3.663093328475952 +1033 -3.6632046699523926 +1034 -3.66318941116333 +1035 -3.4046459197998047 +1036 -3.4232287406921387 +1037 -3.4053196907043457 +1038 -3.4232425689697266 +1039 -3.4232311248779297 +1040 -3.601524829864502 +1041 -3.6015734672546387 +1042 -3.6016080379486084 +1043 -3.6017327308654785 +1044 -3.5886154174804688 +1045 -3.6029956340789795 +1046 -3.5708837509155273 +1047 -3.621170997619629 +1048 -3.6026179790496826 +1049 -3.6213488578796387 +1050 -2.1230640411376953 +1051 -2.1230640411376953 +1052 -2.1230640411376953 +1053 -2.1230640411376953 +1054 -2.8210973739624023 +1055 -3.236889123916626 +1056 -3.236889123916626 +1057 -3.236889123916626 +1058 -3.236889123916626 +1059 -3.5070369243621826 +1060 -3.4777190685272217 +1061 -2.5505456924438477 +1062 -3.2316970825195312 +1063 -3.2316977977752686 +1064 -2.5505456924438477 +1065 -3.4498062133789062 +1066 -3.4496922492980957 +1067 -3.449754238128662 +1068 -3.4496047496795654 +1069 -3.4498279094696045 +1070 -3.6549384593963623 +1071 -3.6555817127227783 +1072 -3.6574697494506836 +1073 -3.6586616039276123 +1074 -3.6565887928009033 +1075 -3.6479172706604004 +1076 -3.6488265991210938 +1077 -3.646094799041748 +1078 -3.648672580718994 +1079 -3.6472244262695312 +1080 -3.5715830326080322 +1081 -3.571617603302002 +1082 -3.571617603302002 +1083 -3.5716090202331543 +1084 -3.571617603302002 +1085 -3.165323257446289 +1086 -2.6274352073669434 +1087 -3.1653318405151367 +1088 -3.1653339862823486 +1089 -3.1653318405151367 +1090 -3.6631903648376465 +1091 -3.6632561683654785 +1092 -3.2728428840637207 +1093 -3.663278579711914 +1094 -3.272843360900879 +1095 -3.423130512237549 +1096 -3.423229932785034 +1097 -3.4232590198516846 +1098 -3.422647476196289 +1099 -3.4232144355773926 +1100 -3.588519811630249 +1101 -3.6018309593200684 +1102 -3.588454484939575 +1103 -3.601733684539795 +1104 -3.5888161659240723 +1105 -3.6210081577301025 +1106 -3.601571798324585 +1107 -3.620894432067871 +1108 -3.621028423309326 +1109 -3.621007204055786 +1110 -2.8211116790771484 +1111 -2.8210971355438232 +1112 -2.1230645179748535 +1113 -2.1230645179748535 +1114 -2.1230645179748535 +1115 -3.5069360733032227 +1116 -3.5070278644561768 +1117 -3.5070371627807617 +1118 -3.5070366859436035 +1119 -3.5069141387939453 +1120 -3.4776437282562256 +1121 -3.4777190685272217 +1122 -3.47778058052063 +1123 -3.47761607170105 +1124 -3.4776782989501953 +1125 -3.4099717140197754 +1126 -3.4498062133789062 +1127 -3.449662446975708 +1128 -3.4498143196105957 +1129 -3.4498372077941895 +1130 -3.658496141433716 +1131 -3.658539056777954 +1132 -3.6572494506835938 +1133 -3.6585168838500977 +1134 -3.655263662338257 +1135 -3.647125482559204 +1136 -3.647597312927246 +1137 -3.6436569690704346 +1138 -3.641592025756836 +1139 -3.650475025177002 +1140 -3.571617603302002 +1141 -3.571617603302002 +1142 -3.571610689163208 +1143 -3.571617603302002 +1144 -3.571617603302002 +1145 -3.1653316020965576 +1146 -2.340482234954834 +1147 -2.340484142303467 +1148 -3.1653318405151367 +1149 -3.165278196334839 +1150 -3.663200616836548 +1151 -3.6630325317382812 +1152 -3.6632747650146484 +1153 -3.663318157196045 +1154 -3.2728421688079834 +1155 -3.405524730682373 +1156 -3.423229932785034 +1157 -3.423205852508545 +1158 -3.4232449531555176 +1159 -3.4232277870178223 +1160 -3.58872389793396 +1161 -3.5888309478759766 +1162 -3.588419198989868 +1163 -3.519878387451172 +1164 -3.5888020992279053 +1165 -3.6204638481140137 +1166 -3.620880603790283 +1167 -3.6210641860961914 +1168 -3.621166229248047 +1169 -3.621060609817505 +1170 -2.1230640411376953 +1171 -2.1230640411376953 +1172 -2.821096897125244 +1173 -2.821096658706665 +1174 -2.1230640411376953 +1175 -3.236889123916626 +1176 -3.236889362335205 +1177 -3.5069193840026855 +1178 -3.5070364475250244 +1179 -3.5070369243621826 +1180 -3.4776408672332764 +1181 -3.2316970825195312 +1182 -3.477749824523926 +1183 -3.231524705886841 +1184 -3.231525421142578 +1185 -3.4496891498565674 +1186 -3.449664354324341 +1187 -3.449803113937378 +1188 -3.449662446975708 +1189 -3.4495856761932373 +1190 -3.656522035598755 +1191 -3.658363103866577 +1192 -3.6585447788238525 +1193 -3.6562108993530273 +1194 -3.6549184322357178 +1195 -3.647984027862549 +1196 -3.648190498352051 +1197 -3.6496777534484863 +1198 -3.650991439819336 +1199 -3.648083209991455 diff --git a/example/python_pkg/Al_learn/DRAFFLE/DOutput/energies_unrlxd_seed0.txt b/example/python_pkg/Al_learn/DRAFFLE/DOutput/energies_unrlxd_seed0.txt new file mode 100644 index 00000000..0e9675a8 --- /dev/null +++ b/example/python_pkg/Al_learn/DRAFFLE/DOutput/energies_unrlxd_seed0.txt @@ -0,0 +1,1200 @@ +0 -3.2833518981933594 +1 -3.062154769897461 +2 -3.2833518981933594 +3 -3.2833518981933594 +4 -3.2833518981933594 +5 -1.3760532140731812 +6 -1.1772372722625732 +7 -1.2733359336853027 +8 -1.2733359336853027 +9 -1.2733359336853027 +10 -1.1720147132873535 +11 -2.761749267578125 +12 -1.9936747550964355 +13 -3.249187469482422 +14 -3.1237685680389404 +15 -2.4238734245300293 +16 -2.5822486877441406 +17 -2.4074714183807373 +18 -2.595069408416748 +19 -2.974985122680664 +20 -1.9759480953216553 +21 -2.969287872314453 +22 -3.31194806098938 +23 -2.217053174972534 +24 -3.2409729957580566 +25 -2.944082260131836 +26 -3.033931255340576 +27 -2.477809429168701 +28 -2.1534361839294434 +29 -2.597721576690674 +30 -0.15073251724243164 +31 -2.3116116523742676 +32 -2.1812517642974854 +33 -0.15073251724243164 +34 -2.1214702129364014 +35 -2.555790424346924 +36 -1.7481238842010498 +37 -3.236339807510376 +38 -2.555790901184082 +39 -3.236339807510376 +40 -1.263207197189331 +41 -2.6288952827453613 +42 -1.997178554534912 +43 -1.9077868461608887 +44 -2.628894805908203 +45 -1.2864336967468262 +46 -2.7819933891296387 +47 -3.2739272117614746 +48 -3.1408042907714844 +49 -2.78594708442688 +50 -2.1231744289398193 +51 -2.768644332885742 +52 -2.986499071121216 +53 -2.3307480812072754 +54 -2.0793559551239014 +55 -3.4812161922454834 +56 -2.300509214401245 +57 -2.6654744148254395 +58 -2.4505679607391357 +59 -2.367136001586914 +60 -3.571617841720581 +61 -3.5075523853302 +62 -3.571617841720581 +63 -3.571617841720581 +64 -3.571617841720581 +65 -0.6345417499542236 +66 -2.0774521827697754 +67 -0.5414118766784668 +68 -0.38671374320983887 +69 -0.7706606388092041 +70 -1.270287275314331 +71 -1.38960862159729 +72 -1.7287952899932861 +73 -1.562049388885498 +74 -2.868849277496338 +75 -3.2965006828308105 +76 -2.782909870147705 +77 -2.310737133026123 +78 -2.0288338661193848 +79 -2.7269113063812256 +80 -2.7531967163085938 +81 -3.039541721343994 +82 -2.77933931350708 +83 -2.250332832336426 +84 -0.7876870036125183 +85 -3.192920207977295 +86 -1.7198023796081543 +87 -2.7116470336914062 +88 -2.7613823413848877 +89 -2.5379562377929688 +90 -2.1214699745178223 +91 -2.754514455795288 +92 -0.45919156074523926 +93 -1.3673017024993896 +94 -2.1214699745178223 +95 -3.236339807510376 +96 -2.33260178565979 +97 -1.7662382125854492 +98 -1.7662382125854492 +99 -1.7662382125854492 +100 -1.011950969696045 +101 -1.9971786737442017 +102 -2.335090160369873 +103 -1.5836683511734009 +104 -2.7987658977508545 +105 -2.714503526687622 +106 -3.1061651706695557 +107 -3.3337302207946777 +108 -2.7581958770751953 +109 -3.395397901535034 +110 -0.9336240291595459 +111 -2.15370512008667 +112 -3.2169599533081055 +113 -2.6871578693389893 +114 -2.487466335296631 +115 -3.1473355293273926 +116 -2.186947822570801 +117 -1.9674668312072754 +118 -1.5563161373138428 +119 -2.0352563858032227 +120 -3.571617603302002 +121 -3.52871036529541 +122 -3.571617603302002 +123 -3.571617603302002 +124 -3.571617603302002 +125 -1.3611598014831543 +126 -0.8776834011077881 +127 -2.3207483291625977 +128 -2.268547773361206 +129 -0.8264477252960205 +130 -2.450653553009033 +131 -2.718295097351074 +132 -2.1558051109313965 +133 -2.8296780586242676 +134 -2.104591131210327 +135 -2.657792329788208 +136 -3.271568775177002 +137 -2.75842022895813 +138 -2.7366857528686523 +139 -2.5885870456695557 +140 -3.0682263374328613 +141 -3.2822163105010986 +142 -2.9225449562072754 +143 -2.464120388031006 +144 -1.890486717224121 +145 -3.1359963417053223 +146 -2.917819023132324 +147 -2.4565796852111816 +148 -3.0096731185913086 +149 -1.8137760162353516 +150 -2.1230642795562744 +151 -1.388071060180664 +152 -2.1214704513549805 +153 -2.1230642795562744 +154 -2.1230642795562744 +155 -1.766235589981079 +156 -1.6675024032592773 +157 -0.9790771007537842 +158 -1.961426019668579 +159 -1.766235589981079 +160 -1.3565460443496704 +161 -1.8305116891860962 +162 -2.0724313259124756 +163 -2.335090160369873 +164 -1.5836683511734009 +165 -2.9995813369750977 +166 -2.959794521331787 +167 -3.367095470428467 +168 -2.8625776767730713 +169 -2.693312168121338 +170 -0.7912552356719971 +171 -3.0065624713897705 +172 -2.7180092334747314 +173 -2.3742122650146484 +174 -2.460084915161133 +175 -2.627204418182373 +176 -2.1630594730377197 +177 -2.7177915573120117 +178 -2.199366569519043 +179 -2.453944206237793 +180 -3.571617603302002 +181 -3.4453463554382324 +182 -3.365487813949585 +183 -3.571617603302002 +184 -3.571617603302002 +185 -2.036259412765503 +186 -2.320748805999756 +187 -0.40667200088500977 +188 -1.1171329021453857 +189 -0.9702532291412354 +190 -1.8586971759796143 +191 -2.983976125717163 +192 -2.0613436698913574 +193 -2.5860066413879395 +194 -2.0613436698913574 +195 -2.845252752304077 +196 -2.0948383808135986 +197 -1.918658971786499 +198 -2.816528797149658 +199 -2.2501702308654785 +200 -1.9921214580535889 +201 -2.893561840057373 +202 -1.6678781509399414 +203 -1.935516119003296 +204 -1.2966163158416748 +205 -2.2338085174560547 +206 -2.080613136291504 +207 -2.285007953643799 +208 -1.7172770500183105 +209 -2.205925941467285 +210 -2.1230640411376953 +211 -1.8632206916809082 +212 -1.9090876579284668 +213 -2.1230640411376953 +214 -2.1230640411376953 +215 -1.7662353515625 +216 -2.3985605239868164 +217 -1.766235589981079 +218 -1.9342823028564453 +219 -1.816450595855713 +220 -2.113084316253662 +221 -2.8544559478759766 +222 -1.5836683511734009 +223 -1.825413703918457 +224 -1.5836683511734009 +225 -2.441676378250122 +226 -1.704634428024292 +227 -3.3804755210876465 +228 -2.3424620628356934 +229 -2.6328909397125244 +230 -1.5049587488174438 +231 -0.40517401695251465 +232 -1.2950797080993652 +233 -2.7466630935668945 +234 -2.3317084312438965 +235 -3.0166995525360107 +236 -2.190067768096924 +237 -2.385070323944092 +238 -2.594202995300293 +239 -1.658663034439087 +240 -3.571617841720581 +241 -3.2709763050079346 +242 -3.571617841720581 +243 -3.5383729934692383 +244 -3.571617841720581 +245 -0.9542930126190186 +246 -0.8157293796539307 +247 -2.2550578117370605 +248 -2.2685484886169434 +249 -2.320748805999756 +250 -1.899134874343872 +251 -1.4352335929870605 +252 -2.983976125717163 +253 -2.7182953357696533 +254 -2.983976364135742 +255 -2.246950626373291 +256 -1.7672351598739624 +257 -2.670700788497925 +258 -2.309792995452881 +259 -2.0290205478668213 +260 -2.0675833225250244 +261 -2.2165772914886475 +262 -3.4871127605438232 +263 -2.4721832275390625 +264 -2.5625758171081543 +265 -3.238255262374878 +266 -2.8430733680725098 +267 -2.839388370513916 +268 -2.710996150970459 +269 -2.397177219390869 +270 -2.1214704513549805 +271 -2.0553157329559326 +272 -2.1230640411376953 +273 -2.1230642795562744 +274 -2.1214704513549805 +275 -3.236339807510376 +276 -1.5227751731872559 +277 -1.365544319152832 +278 -1.7662353515625 +279 -2.16275954246521 +280 -2.415790557861328 +281 -2.0478403568267822 +282 -2.222398519515991 +283 -1.7617145776748657 +284 -1.2788455486297607 +285 -3.367095470428467 +286 -1.9587228298187256 +287 -3.1061649322509766 +288 -2.6369030475616455 +289 -3.0873637199401855 +290 -2.1906142234802246 +291 -2.614169120788574 +292 -1.5711122751235962 +293 -1.7468618154525757 +294 -1.0597920417785645 +295 -1.8743863105773926 +296 -2.479581356048584 +297 -2.2797727584838867 +298 -2.04752254486084 +299 -3.2486515045166016 +300 -3.40425968170166 +301 -2.3124759197235107 +302 -3.571617841720581 +303 -3.571617841720581 +304 -3.571617841720581 +305 -1.005272388458252 +306 -0.9798462390899658 +307 -2.268547773361206 +308 -2.3207483291625977 +309 -2.320748805999756 +310 -1.3544867038726807 +311 -2.5709192752838135 +312 -1.6898784637451172 +313 -2.5709190368652344 +314 -2.9738717079162598 +315 -1.671656608581543 +316 -2.7366857528686523 +317 -2.9130115509033203 +318 -1.751225471496582 +319 -2.902623414993286 +320 -3.3058841228485107 +321 -1.4306920766830444 +322 -2.8616747856140137 +323 -1.9118512868881226 +324 -1.5397212505340576 +325 -2.8878164291381836 +326 -1.8245010375976562 +327 -2.6750659942626953 +328 -1.6693546772003174 +329 -1.917248249053955 +330 -2.3039636611938477 +331 -2.1214702129364014 +332 -2.1230640411376953 +333 -2.1230640411376953 +334 -2.1230640411376953 +335 -1.9687633514404297 +336 -3.236339807510376 +337 -1.766235589981079 +338 -1.766235589981079 +339 -1.766235589981079 +340 -2.596576690673828 +341 -1.5836683511734009 +342 -2.222398281097412 +343 -1.5836683511734009 +344 -1.997178554534912 +345 -2.386080503463745 +346 -2.0652410984039307 +347 -3.3893585205078125 +348 -2.6676435470581055 +349 -3.0599288940429688 +350 -1.5014187097549438 +351 -1.7658323049545288 +352 -1.729687213897705 +353 -2.3017635345458984 +354 -3.374717950820923 +355 -2.596762180328369 +356 -1.5794262886047363 +357 -2.746983051300049 +358 -2.160102367401123 +359 -2.760223865509033 +360 -3.571617841720581 +361 -3.5376744270324707 +362 -3.571617603302002 +363 -3.571617603302002 +364 -3.5275025367736816 +365 -0.2657470703125 +366 -1.0518577098846436 +367 -1.619442343711853 +368 -0.9798464775085449 +369 -2.2685487270355225 +370 -2.104591131210327 +371 -2.3905277252197266 +372 -2.1045913696289062 +373 -1.8991343975067139 +374 -2.1469969749450684 +375 -2.2489705085754395 +376 -1.7974636554718018 +377 -2.2008728981018066 +378 -2.983839511871338 +379 -2.2489705085754395 +380 -2.6957294940948486 +381 -1.87808358669281 +382 -2.2153186798095703 +383 -1.3011125326156616 +384 -2.561950922012329 +385 -1.5488605499267578 +386 -2.105896472930908 +387 -2.6850428581237793 +388 -2.2969627380371094 +389 -2.07460355758667 +390 -2.1230642795562744 +391 -2.241070032119751 +392 -2.1230642795562744 +393 -1.112264633178711 +394 -2.1230642795562744 +395 -1.7662382125854492 +396 -3.5049147605895996 +397 -1.7662382125854492 +398 -1.7662382125854492 +399 -1.7662382125854492 +400 -1.8041883707046509 +401 -2.335090160369873 +402 -1.997179388999939 +403 -2.190237522125244 +404 -1.9139293432235718 +405 -3.367095470428467 +406 -2.7037434577941895 +407 -3.3106913566589355 +408 -3.0796124935150146 +409 -3.2386555671691895 +410 -2.658139228820801 +411 -1.8881163597106934 +412 -0.9995296001434326 +413 -3.27121639251709 +414 -1.571113109588623 +415 -2.688117742538452 +416 -1.3874337673187256 +417 -1.8763813972473145 +418 -1.9214832782745361 +419 -2.555396556854248 +420 -3.571617841720581 +421 -3.1549501419067383 +422 -3.571617841720581 +423 -3.434377670288086 +424 -3.571617841720581 +425 -1.4450336694717407 +426 -1.117133378982544 +427 -0.9798464775085449 +428 -2.320748805999756 +429 -0.9798462390899658 +430 -2.718295097351074 +431 -3.4737601280212402 +432 -1.5056569576263428 +433 -2.061343193054199 +434 -1.7650964260101318 +435 -2.2489709854125977 +436 -2.2489705085754395 +437 -2.4740986824035645 +438 -1.5832452774047852 +439 -2.9482028484344482 +440 -2.9227638244628906 +441 -2.2036526203155518 +442 -2.656705141067505 +443 -2.9355061054229736 +444 -2.083967447280884 +445 -2.0806803703308105 +446 -3.387289047241211 +447 -3.3277361392974854 +448 -2.955982208251953 +449 -1.78580904006958 +450 -2.1214702129364014 +451 -2.1388630867004395 +452 -2.1230640411376953 +453 -2.1020114421844482 +454 -2.1230640411376953 +455 -3.236340045928955 +456 -1.473026990890503 +457 -3.236340045928955 +458 -1.766237735748291 +459 -1.766237735748291 +460 -2.6675865650177 +461 -1.314148187637329 +462 -0.9667296409606934 +463 -1.5836690664291382 +464 -2.2223987579345703 +465 -3.367095470428467 +466 -3.367095470428467 +467 -2.602419137954712 +468 -2.9369120597839355 +469 -3.0873632431030273 +470 -3.2845184803009033 +471 -1.4568637609481812 +472 -2.0641672611236572 +473 -1.0377414226531982 +474 -2.5590314865112305 +475 -2.019411087036133 +476 -2.997849464416504 +477 -2.7748632431030273 +478 -2.5835318565368652 +479 -2.7191972732543945 +480 -3.468503475189209 +481 -3.571617841720581 +482 -1.7775647640228271 +483 -3.5366439819335938 +484 -3.571617841720581 +485 -1.6512218713760376 +486 -2.3207483291625977 +487 -2.3207483291625977 +488 -0.6307883262634277 +489 -1.9799753427505493 +490 -1.3824853897094727 +491 -2.1816720962524414 +492 -0.6780860424041748 +493 -0.41050100326538086 +494 -2.06134295463562 +495 -2.76924729347229 +496 -2.8519535064697266 +497 -1.3973751068115234 +498 -2.4990453720092773 +499 -1.3973751068115234 +500 -1.8621938228607178 +501 -1.2360808849334717 +502 -1.6012709140777588 +503 -2.3365349769592285 +504 -3.065516233444214 +505 -1.2176663875579834 +506 -1.8441017866134644 +507 -2.973780870437622 +508 -3.008756637573242 +509 -1.9793200492858887 +510 -1.39300537109375 +511 -1.8848662376403809 +512 -2.1214702129364014 +513 -2.1214704513549805 +514 -1.2826642990112305 +515 -2.0696752071380615 +516 -3.236339807510376 +517 -1.766235589981079 +518 -2.211881637573242 +519 -1.766235589981079 +520 -1.9155136346817017 +521 -2.3350892066955566 +522 -1.5836683511734009 +523 -2.2149956226348877 +524 -2.921566963195801 +525 -2.7208473682403564 +526 -3.143681764602661 +527 -2.5203399658203125 +528 -2.8663687705993652 +529 -2.845716953277588 +530 -1.4034284353256226 +531 -3.2360637187957764 +532 -1.0661427974700928 +533 -2.9732627868652344 +534 -1.8145442008972168 +535 -2.573681592941284 +536 -2.951907157897949 +537 -2.790632724761963 +538 -1.3088998794555664 +539 -2.291517734527588 +540 -3.571617603302002 +541 -2.07757830619812 +542 -3.3747506141662598 +543 -3.5191760063171387 +544 -3.571617603302002 +545 -3.1509697437286377 +546 -0.7457003593444824 +547 -2.3207483291625977 +548 -2.2847704887390137 +549 -1.5491832494735718 +550 -2.1863560676574707 +551 -1.0482354164123535 +552 -1.6471095085144043 +553 -2.0048301219940186 +554 -3.661088705062866 +555 -2.4396555423736572 +556 -2.2489705085754395 +557 -3.015045642852783 +558 -2.437440872192383 +559 -2.5444517135620117 +560 -2.7025604248046875 +561 -3.01495099067688 +562 -1.4850553274154663 +563 -2.727733850479126 +564 -2.6727828979492188 +565 -1.967383861541748 +566 -2.4725122451782227 +567 -2.506258964538574 +568 -2.6498234272003174 +569 -2.963364839553833 +570 -2.1230640411376953 +571 -2.200982093811035 +572 -2.1230640411376953 +573 -2.1230640411376953 +574 -2.1230640411376953 +575 -1.7662382125854492 +576 -1.689922571182251 +577 -2.1002230644226074 +578 -1.766237735748291 +579 -1.7745795249938965 +580 -2.2954158782958984 +581 -1.5836683511734009 +582 -1.3481364250183105 +583 -3.2068586349487305 +584 -1.5836683511734009 +585 -3.08138108253479 +586 -2.471921920776367 +587 -2.740708827972412 +588 -2.0717947483062744 +589 -2.5932958126068115 +590 -2.2679061889648438 +591 -2.8114917278289795 +592 -2.5934877395629883 +593 -2.508145809173584 +594 -1.815416932106018 +595 -2.327547311782837 +596 -2.828098773956299 +597 -1.919119119644165 +598 -2.418349266052246 +599 -2.0549378395080566 +600 -3.571617603302002 +601 -3.468860626220703 +602 -3.571617603302002 +603 -3.571617603302002 +604 -3.571617603302002 +605 -2.0455334186553955 +606 -2.358741283416748 +607 -2.3207483291625977 +608 -1.117133617401123 +609 -2.320748805999756 +610 -2.0613434314727783 +611 -3.6433441638946533 +612 -2.8852856159210205 +613 -1.5253090858459473 +614 -1.3910086154937744 +615 -1.3973753452301025 +616 -2.7837865352630615 +617 -1.8069785833358765 +618 -2.2947187423706055 +619 -2.8048765659332275 +620 -1.577709436416626 +621 -1.7275583744049072 +622 -1.7613351345062256 +623 -2.1000640392303467 +624 -2.6755499839782715 +625 -2.024632692337036 +626 -2.748007297515869 +627 -1.6863882541656494 +628 -3.104628562927246 +629 -2.13458514213562 +630 -2.1214699745178223 +631 -2.1030707359313965 +632 -2.1230642795562744 +633 -1.6893532276153564 +634 -2.2429051399230957 +635 -3.236340045928955 +636 -1.2927231788635254 +637 -1.766237735748291 +638 -1.8408923149108887 +639 -3.236340045928955 +640 -1.6939998865127563 +641 -2.335089683532715 +642 -2.2391464710235596 +643 -1.5836683511734009 +644 -2.335089683532715 +645 -3.3893589973449707 +646 -3.340594530105591 +647 -3.377049207687378 +648 -2.9685072898864746 +649 -2.773576498031616 +650 -2.867659330368042 +651 -2.3218765258789062 +652 -1.8722251653671265 +653 -3.6381101608276367 +654 -2.646301746368408 +655 -1.8275580406188965 +656 -2.8077175617218018 +657 -1.9282691478729248 +658 -3.100131034851074 +659 -1.3715250492095947 +660 -2.0931663513183594 +661 -3.571617603302002 +662 -2.489423990249634 +663 -3.571617603302002 +664 -3.571617603302002 +665 -2.2113723754882812 +666 -2.266435384750366 +667 -2.3502111434936523 +668 -2.0173866748809814 +669 -2.268547773361206 +670 -2.718295097351074 +671 -1.9717693328857422 +672 -2.9799087047576904 +673 -2.1045916080474854 +674 -1.8010029792785645 +675 -2.8441407680511475 +676 -2.246950387954712 +677 -1.3973748683929443 +678 -2.953774929046631 +679 -2.5350356101989746 +680 -1.8907356262207031 +681 -2.7810657024383545 +682 -2.7722630500793457 +683 -3.1786510944366455 +684 -1.817723035812378 +685 -2.2682151794433594 +686 -3.281651735305786 +687 -2.5388379096984863 +688 -2.325413942337036 +689 -2.890261650085449 +690 -2.2010080814361572 +691 -1.7407481670379639 +692 -2.1230640411376953 +693 -2.1214699745178223 +694 -2.1230640411376953 +695 -1.697216510772705 +696 -1.7662382125854492 +697 -1.9713432788848877 +698 -2.0381526947021484 +699 -1.6857504844665527 +700 -3.1722192764282227 +701 -1.997178554534912 +702 -2.4742794036865234 +703 -1.9138721227645874 +704 -1.398836612701416 +705 -2.89937686920166 +706 -3.367095470428467 +707 -3.3893585205078125 +708 -3.0678348541259766 +709 -2.4222095012664795 +710 -2.6654248237609863 +711 -3.2179195880889893 +712 -1.944742202758789 +713 -3.4015986919403076 +714 -3.2274742126464844 +715 -1.8452513217926025 +716 -2.3038699626922607 +717 -2.211483955383301 +718 -1.3404874801635742 +719 -2.941880702972412 +720 -3.571617841720581 +721 -3.4827423095703125 +722 -3.571617841720581 +723 -3.571617841720581 +724 -3.571617841720581 +725 -1.8886874914169312 +726 -2.2685487270355225 +727 -2.3207483291625977 +728 -2.2685484886169434 +729 -2.268547773361206 +730 -2.7053866386413574 +731 -2.927622079849243 +732 -2.083828926086426 +733 -2.676377058029175 +734 -2.927597761154175 +735 -2.5062408447265625 +736 -2.9018208980560303 +737 -1.1534943580627441 +738 -3.007495641708374 +739 -2.6939125061035156 +740 -1.8853838443756104 +741 -2.515230894088745 +742 -1.601271629333496 +743 -3.0430855751037598 +744 -2.537325620651245 +745 -1.7737059593200684 +746 -2.9029414653778076 +747 -2.788236618041992 +748 -1.9423834085464478 +749 -1.7355196475982666 +750 -2.1230642795562744 +751 -1.8545870780944824 +752 -2.1230642795562744 +753 -2.1214704513549805 +754 -2.1230642795562744 +755 -1.766237735748291 +756 -3.175137758255005 +757 -1.766237735748291 +758 -2.012279510498047 +759 -1.9718279838562012 +760 -2.1401619911193848 +761 -1.5836683511734009 +762 -1.5836683511734009 +763 -2.2969894409179688 +764 -2.598033905029297 +765 -3.112121820449829 +766 -2.943584680557251 +767 -3.367095470428467 +768 -1.7837800979614258 +769 -2.844237804412842 +770 -2.978999376296997 +771 -1.8926531076431274 +772 -1.6943620443344116 +773 -1.9112176895141602 +774 -1.9334512948989868 +775 -2.5739293098449707 +776 -2.8287906646728516 +777 -2.579946756362915 +778 -2.288266658782959 +779 -1.611250400543213 +780 -3.571617603302002 +781 -3.526185989379883 +782 -2.856163501739502 +783 -3.571617603302002 +784 -3.2193286418914795 +785 -0.41343069076538086 +786 -2.3013954162597656 +787 -2.2685484886169434 +788 -0.9595015048980713 +789 -2.320748805999756 +790 -1.7198050022125244 +791 -2.718295097351074 +792 -2.835692882537842 +793 -2.2400968074798584 +794 -1.4230270385742188 +795 -3.257641315460205 +796 -2.731081962585449 +797 -2.8441407680511475 +798 -2.246950387954712 +799 -1.8608009815216064 +800 -1.9707374572753906 +801 -1.6902828216552734 +802 -3.0456032752990723 +803 -1.7971267700195312 +804 -1.5572240352630615 +805 -2.38127064704895 +806 -2.3458611965179443 +807 -1.452106237411499 +808 -2.2544875144958496 +809 -2.8435466289520264 +810 -2.1230640411376953 +811 -1.8989603519439697 +812 -1.574063777923584 +813 -2.1230640411376953 +814 -2.1230640411376953 +815 -1.766237735748291 +816 -2.266789197921753 +817 -3.236339807510376 +818 -1.766237497329712 +819 -3.236339807510376 +820 -1.668108582496643 +821 -1.5836690664291382 +822 -2.0969362258911133 +823 -2.4500222206115723 +824 -2.222398519515991 +825 -2.862577438354492 +826 -3.345576047897339 +827 -2.3599207401275635 +828 -1.8140108585357666 +829 -2.7334866523742676 +830 -2.1518232822418213 +831 -2.743290901184082 +832 -1.9379955530166626 +833 -2.1560184955596924 +834 -3.228734016418457 +835 -1.45157790184021 +836 -2.2167158126831055 +837 -2.112170696258545 +838 -2.6111936569213867 +839 -3.0218377113342285 +840 -3.447175979614258 +841 -3.571617841720581 +842 -3.571617841720581 +843 -3.571617841720581 +844 -3.571617841720581 +845 -1.4146838188171387 +846 -0.587782621383667 +847 -2.2685487270355225 +848 -1.1171329021453857 +849 -2.330087184906006 +850 -1.8229827880859375 +851 -1.7929213047027588 +852 -2.104590892791748 +853 -2.0613434314727783 +854 -2.8296780586242676 +855 -2.8949215412139893 +856 -2.246950626373291 +857 -2.246950387954712 +858 -2.794407844543457 +859 -2.3467931747436523 +860 -2.052908182144165 +861 -2.0556106567382812 +862 -3.2686431407928467 +863 -2.1954166889190674 +864 -1.8234550952911377 +865 -3.1893351078033447 +866 -2.4596376419067383 +867 -1.9058576822280884 +868 -2.465284824371338 +869 -1.7076587677001953 +870 -2.156062126159668 +871 -2.1230640411376953 +872 -1.941680908203125 +873 -2.1214702129364014 +874 -2.1230640411376953 +875 -1.1293010711669922 +876 -3.236340045928955 +877 -1.766237735748291 +878 -1.7662382125854492 +879 -3.236340045928955 +880 -3.1998252868652344 +881 -2.222398281097412 +882 -2.222398281097412 +883 -1.5836683511734009 +884 -1.9019972085952759 +885 -2.7641119956970215 +886 -3.299609422683716 +887 -2.03873348236084 +888 -3.3423213958740234 +889 -3.033452033996582 +890 -3.331232786178589 +891 -1.5647903680801392 +892 -2.980797529220581 +893 -2.230996608734131 +894 -3.2169580459594727 +895 -2.7054731845855713 +896 -2.865551233291626 +897 -3.263214588165283 +898 -2.211060047149658 +899 -2.4553747177124023 +900 -3.571617841720581 +901 -1.8199119567871094 +902 -3.571617841720581 +903 -3.4933741092681885 +904 -3.516775131225586 +905 -2.325676441192627 +906 -2.0289337635040283 +907 -2.304347038269043 +908 -0.9798464775085449 +909 -1.9084243774414062 +910 -1.144399881362915 +911 -2.756546974182129 +912 -1.2617969512939453 +913 -2.06134295463562 +914 -2.8634531497955322 +915 -2.9061107635498047 +916 -2.6939120292663574 +917 -2.423372745513916 +918 -2.621553421020508 +919 -1.76120924949646 +920 -2.818192958831787 +921 -1.9509515762329102 +922 -2.9950804710388184 +923 -3.359668731689453 +924 -1.296616792678833 +925 -2.034372568130493 +926 -2.367431402206421 +927 -2.8490359783172607 +928 -2.9243273735046387 +929 -2.6991701126098633 +930 -2.1230642795562744 +931 -2.055792808532715 +932 -0.9693200588226318 +933 -2.1214702129364014 +934 -2.1230642795562744 +935 -1.766237735748291 +936 -2.389953851699829 +937 -1.4229753017425537 +938 -1.766237735748291 +939 -3.1294898986816406 +940 -1.7948020696640015 +941 -1.4006381034851074 +942 -3.013115644454956 +943 -2.335089683532715 +944 -2.222398519515991 +945 -2.8061814308166504 +946 -2.899376392364502 +947 -2.5403456687927246 +948 -2.4049832820892334 +949 -3.1061649322509766 +950 -1.9657281637191772 +951 -2.9608871936798096 +952 -3.276655912399292 +953 -2.9434280395507812 +954 -1.6642462015151978 +955 -2.139009475708008 +956 -1.6603138446807861 +957 -3.3279898166656494 +958 -2.525853395462036 +959 -1.2082650661468506 +960 -3.571617841720581 +961 -3.571617841720581 +962 -3.571617841720581 +963 -3.571617841720581 +964 -3.571617841720581 +965 -2.2866954803466797 +966 -2.1831557750701904 +967 -0.9586875438690186 +968 -0.9925858974456787 +969 -2.313286781311035 +970 -3.6597886085510254 +971 -2.5709190368652344 +972 -2.8916616439819336 +973 -1.2865643501281738 +974 -2.061343193054199 +975 -2.9263253211975098 +976 -2.6507956981658936 +977 -2.0318751335144043 +978 -2.982475996017456 +979 -3.020564079284668 +980 -2.548281192779541 +981 -1.96209716796875 +982 -2.0503146648406982 +983 -2.3732476234436035 +984 -2.1281704902648926 +985 -2.4427576065063477 +986 -3.1776604652404785 +987 -2.2467784881591797 +988 -2.4590649604797363 +989 -1.4277009963989258 +990 -2.1230642795562744 +991 -2.1230642795562744 +992 -2.1230642795562744 +993 -2.1230642795562744 +994 -2.1230642795562744 +995 -1.766237735748291 +996 -1.766237735748291 +997 -1.766237735748291 +998 -1.766237735748291 +999 -1.766237735748291 +1000 -1.8514140844345093 +1001 -2.773534059524536 +1002 -1.5836690664291382 +1003 -1.5836690664291382 +1004 -2.773534059524536 +1005 -2.0343852043151855 +1006 -2.860123634338379 +1007 -3.3893585205078125 +1008 -2.429969310760498 +1009 -1.6403179168701172 +1010 -2.760422468185425 +1011 -1.23769211769104 +1012 -2.1276204586029053 +1013 -2.143666982650757 +1014 -2.3657093048095703 +1015 -3.141280174255371 +1016 -2.086041212081909 +1017 -3.535724639892578 +1018 -2.430938243865967 +1019 -2.9772708415985107 +1020 -3.571617603302002 +1021 -3.571617603302002 +1022 -3.571617603302002 +1023 -3.571617603302002 +1024 -3.571617603302002 +1025 -2.1436522006988525 +1026 -2.1896212100982666 +1027 -0.6506352424621582 +1028 -0.9687716960906982 +1029 -0.9586880207061768 +1030 -2.5709190368652344 +1031 -2.6400701999664307 +1032 -2.1045913696289062 +1033 -2.0613436698913574 +1034 -2.836297035217285 +1035 -2.438842296600342 +1036 -2.944209575653076 +1037 -2.738107442855835 +1038 -2.7121407985687256 +1039 -1.8332008123397827 +1040 -2.3719546794891357 +1041 -2.0157487392425537 +1042 -2.364360809326172 +1043 -1.536206603050232 +1044 -2.327833652496338 +1045 -2.8869781494140625 +1046 -1.6974384784698486 +1047 -1.691847324371338 +1048 -1.9502168893814087 +1049 -2.9922008514404297 +1050 -2.1230640411376953 +1051 -2.1230640411376953 +1052 -2.1230640411376953 +1053 -2.1230640411376953 +1054 -2.1214704513549805 +1055 -1.766237735748291 +1056 -1.766237497329712 +1057 -1.766237735748291 +1058 -1.766237497329712 +1059 -3.236340045928955 +1060 -1.5519719123840332 +1061 -1.5836701393127441 +1062 -2.773533821105957 +1063 -2.773533821105957 +1064 -1.5836683511734009 +1065 -3.367095470428467 +1066 -2.444425106048584 +1067 -2.907655715942383 +1068 -3.028158187866211 +1069 -3.0226898193359375 +1070 -2.846450090408325 +1071 -1.2564969062805176 +1072 -2.956615447998047 +1073 -3.1069533824920654 +1074 -1.452236533164978 +1075 -2.124152898788452 +1076 -2.267350912094116 +1077 -1.9906845092773438 +1078 -2.9111530780792236 +1079 -1.7767703533172607 +1080 -3.4231247901916504 +1081 -3.571617603302002 +1082 -3.571617603302002 +1083 -3.480212926864624 +1084 -3.571617603302002 +1085 -0.7761778831481934 +1086 -0.9586882591247559 +1087 -2.2685489654541016 +1088 -0.9283716678619385 +1089 -2.268547773361206 +1090 -1.693495750427246 +1091 -1.4618494510650635 +1092 -2.5709190368652344 +1093 -1.2986693382263184 +1094 -2.5709190368652344 +1095 -2.9838812351226807 +1096 -1.471736192703247 +1097 -2.676737070083618 +1098 -1.3973748683929443 +1099 -2.8349528312683105 +1100 -2.251940965652466 +1101 -1.817791223526001 +1102 -2.6838340759277344 +1103 -2.6685214042663574 +1104 -2.7622339725494385 +1105 -2.119955539703369 +1106 -2.1936676502227783 +1107 -1.9895708560943604 +1108 -1.9844319820404053 +1109 -2.0238025188446045 +1110 -1.9784135818481445 +1111 -2.1214704513549805 +1112 -2.1230645179748535 +1113 -2.1230645179748535 +1114 -2.1230645179748535 +1115 -1.9144022464752197 +1116 -1.9930603504180908 +1117 -3.236339807510376 +1118 -3.236340045928955 +1119 -1.906372308731079 +1120 -2.030559778213501 +1121 -2.376096248626709 +1122 -3.0130605697631836 +1123 -1.850340485572815 +1124 -1.4885735511779785 +1125 -1.7297792434692383 +1126 -3.367095470428467 +1127 -2.7782342433929443 +1128 -3.359673261642456 +1129 -3.0873632431030273 +1130 -0.7415530681610107 +1131 -2.292388916015625 +1132 -2.4378557205200195 +1133 -2.2252824306488037 +1134 -2.7635374069213867 +1135 -2.009634256362915 +1136 -3.2040109634399414 +1137 -1.7867367267608643 +1138 -2.8780205249786377 +1139 -3.208345413208008 +1140 -3.571617603302002 +1141 -3.571617603302002 +1142 -3.3458266258239746 +1143 -3.571617603302002 +1144 -3.571617603302002 +1145 -0.7573158740997314 +1146 -2.3207483291625977 +1147 -2.3207483291625977 +1148 -2.263355016708374 +1149 -0.21486902236938477 +1150 -1.3948132991790771 +1151 -1.911501169204712 +1152 -1.8260653018951416 +1153 -1.5762698650360107 +1154 -2.5709190368652344 +1155 -2.5773823261260986 +1156 -2.398129463195801 +1157 -2.5857183933258057 +1158 -2.483295202255249 +1159 -2.736482858657837 +1160 -2.67492413520813 +1161 -1.9858455657958984 +1162 -1.7822983264923096 +1163 -2.1857388019561768 +1164 -2.949188232421875 +1165 -2.814458131790161 +1166 -2.126734495162964 +1167 -2.170524835586548 +1168 -2.9107556343078613 +1169 -2.621906042098999 +1170 -2.1230640411376953 +1171 -2.1230640411376953 +1172 -1.0722248554229736 +1173 -2.202331066131592 +1174 -2.1230640411376953 +1175 -1.766237497329712 +1176 -1.766237497329712 +1177 -1.6401419639587402 +1178 -3.236339807510376 +1179 -3.236339807510376 +1180 -1.9849439859390259 +1181 -2.773534059524536 +1182 -1.3901485204696655 +1183 -1.9971786737442017 +1184 -1.9971786737442017 +1185 -2.4861562252044678 +1186 -3.3414969444274902 +1187 -1.6698248386383057 +1188 -2.7782344818115234 +1189 -2.9028730392456055 +1190 -2.3904757499694824 +1191 -2.6098666191101074 +1192 -1.123551845550537 +1193 -3.0999867916107178 +1194 -2.41428279876709 +1195 -1.9838497638702393 +1196 -2.677511692047119 +1197 -1.7918286323547363 +1198 -1.4281723499298096 +1199 -2.901244878768921 diff --git a/example/python_pkg/Al_learn/DRAFFLE/DOutput/rlxd_structures_seed0.traj b/example/python_pkg/Al_learn/DRAFFLE/DOutput/rlxd_structures_seed0.traj new file mode 100644 index 00000000..e7029c0a Binary files /dev/null and b/example/python_pkg/Al_learn/DRAFFLE/DOutput/rlxd_structures_seed0.traj differ diff --git a/example/python_pkg/Al_learn/DRAFFLE/DOutput/unrlxd_structures_seed0.traj b/example/python_pkg/Al_learn/DRAFFLE/DOutput/unrlxd_structures_seed0.traj new file mode 100644 index 00000000..15727ca3 Binary files /dev/null and b/example/python_pkg/Al_learn/DRAFFLE/DOutput/unrlxd_structures_seed0.traj differ diff --git a/example/python_pkg/Al_learn/DRAFFLE/learn.py b/example/python_pkg/Al_learn/DRAFFLE/learn.py new file mode 100644 index 00000000..3e4c8e09 --- /dev/null +++ b/example/python_pkg/Al_learn/DRAFFLE/learn.py @@ -0,0 +1,255 @@ +from chgnet.model import CHGNetCalculator +from ase.calculators.singlepoint import SinglePointCalculator +from raffle.generator import raffle_generator +from ase import build, Atoms +from ase.optimize import FIRE +from ase.io import write +import numpy as np +import os +from copy import deepcopy +from joblib import Parallel, delayed + +import logging +logging.basicConfig(level=logging.DEBUG) + +# Function to relax a structure +def process_structure(i, atoms, num_structures_old, calc_params, optimise_structure, iteration): + # Check if the structure has already been processed + if i < num_structures_old: + return + + # calc = Vasp(**calc_params, label=f"struct{i}", directory=f"iteration{iteration}/struct{i}/", txt=f"stdout{i}.o") + inew = i - num_structures_old + atoms.calc = calc + + # Calculate and save the initial energy per atom + energy_unrlxd = atoms.get_potential_energy() / len(atoms) + print(f"Initial energy per atom: {energy_unrlxd}") + + # Optimise the structure if requested + if optimise_structure: + optimizer = FIRE(atoms, trajectory = f"traje{inew}.traj", logfile=f"optimisation{inew}.log") + try: + optimizer.run(fmax=0.05, steps=100) + except Exception as e: + print(f"Optimisation failed: {e}") + return None, None, None + + # Save the optimised structure and its energy per atom + energy_rlxd = atoms.get_potential_energy() / len(atoms) + + # Get the distance matrix + distances = atoms.get_all_distances(mic=True) + + # Set self-distances (diagonal entries) to infinity to ignore them + np.fill_diagonal(distances, np.inf) + + # Check if the minimum non-self distance is below 1.5 + if distances.min() < 1.0: + print(f"Distance too small: {atoms.get_all_distances(mic=True).min()}") + return None, None, None + + if abs(energy_rlxd - energy_unrlxd) > 10.0: + print(f"Energy difference too large: {energy_rlxd} vs {energy_unrlxd}") + return None, None, None + + return atoms, energy_unrlxd, energy_rlxd + + +if __name__ == "__main__": + + # set up the calculator + calc_params = {} + calc = CHGNetCalculator() + + # set up the hosts + crystal_structures = [ + 'orthorhombic', 'hcp', + ] + hosts = [] + for crystal_structure in crystal_structures: + print(f'Crystal structure: {crystal_structure}') + for a in np.linspace(3.1, 5.4, num=6): + b = a + c = a + atom = build.bulk( + name = 'Al', + crystalstructure = crystal_structure, + a = a, + b = b, + c = c, + ) + hosts.append(Atoms('Al', positions=[(0, 0, 0)], cell=atom.get_cell(), pbc=True, calculator=calc)) + print("number of hosts: ", len(hosts)) + + # set the parameters for the generator + optimise_structure = True + mass = 26.9815385 + density = 1.61 # u/A^3 + + # loop over random seeds + for seed in range(1): + print(f"Seed: {seed}") + energies_rlxd_filename = f"energies_rlxd_seed{seed}.txt" + energies_unrlxd_filename = f"energies_unrlxd_seed{seed}.txt" + generator = raffle_generator() + generator.distributions.set_element_energies( + { + 'Al': 0.0 + } + ) + # set energy scale + generator.distributions.set_kBT(0.4) + # set the distribution function widths (2-body, 3-body, 4-body) + generator.distributions.set_width([0.025, np.pi/200.0, np.pi/200.0]) + + # set the initial database + initial_database = [Atoms('Al', positions=[(0, 0, 0)], cell=[8, 8, 8], pbc=True)] + initial_database[0].calc = calc + generator.distributions.create(initial_database) + + # check if the energies file exists, if not create it + if os.path.exists(energies_rlxd_filename): + with open(energies_rlxd_filename, "w") as energy_file: + pass + else: + open(energies_rlxd_filename, "w").close() + + if os.path.exists(energies_unrlxd_filename): + with open(energies_unrlxd_filename, "w") as energy_file: + pass + else: + open(energies_unrlxd_filename, "w").close() + + # initialise the number of structures generated + num_structures_old = 0 + unrlxd_structures = [] + rlxd_structures = [] + iter2 = 0 + # start the iterations, loop over the hosts, then repeat the process X times + for iter in range(10): + for host in hosts: + generator.set_host(host) + volume = host.get_volume() + + # calculate the number of atoms in the host to achieve the desired density + num_atoms = round(density * volume / mass) - 1 + if(num_atoms < 1): + continue + iter2 += 1 + print(f"Volume: {volume}") + print(f"Number of atoms: {num_atoms}") + + # generate the structures + generator.generate( + num_structures = 5, + stoichiometry = { 'Al': num_atoms }, + seed = seed*1000+iter, + method_ratio = {"void": 0.5, "rand": 0.001, "walk": 0.5, "grow": 0.0, "min": 1.0}, + verbose = 0, + ) + + # print the number of structures generated + print("Total number of structures generated: ", generator.num_structures) + generated_structures = generator.get_structures(calc) + num_structures_new = len(generated_structures) + + # check if directory iteration[iter] exists, if not create it + iterdir = f"iteration{iter2}/" + if not os.path.exists(iterdir): + os.makedirs(iterdir) + generator.print_settings(iterdir+"generator_settings.txt") + + # set up list of energies + energy_unrlxd = np.zeros(num_structures_new - num_structures_old) + energy_rlxd = np.zeros(num_structures_new - num_structures_old) + for i in range(num_structures_new - num_structures_old): + write(iterdir+f"POSCAR_unrlxd_{i}", generated_structures[num_structures_old + i]) + print(f"Structure {i} energy per atom: {generated_structures[num_structures_old + i].get_potential_energy() / len(generated_structures[num_structures_old + i])}") + unrlxd_structures.append(generated_structures[num_structures_old + i].copy()) + unrlxd_structures[-1].calc = SinglePointCalculator( + generated_structures[num_structures_old + i], + energy=generated_structures[num_structures_old + i].get_potential_energy(), + forces=generated_structures[num_structures_old + i].get_forces() + ) + + # Start parallel execution + print("Starting parallel execution") + results = Parallel(n_jobs=5)( + delayed(process_structure)(i, generated_structures[i].copy(), num_structures_old, calc_params, optimise_structure, iteration=seed) + for i in range(num_structures_old, num_structures_new) + ) + + # Wait for all futures to complete + for j, result in enumerate(results): + generated_structures[num_structures_old + j], energy_unrlxd[j], energy_rlxd[j] = result + if generated_structures[num_structures_old + j] is None: + print("Structure failed the checks") + continue + rlxd_structures.append(generated_structures[num_structures_old + j].copy()) + rlxd_structures[-1].calc = SinglePointCalculator( + generated_structures[j+num_structures_old], + energy=generated_structures[num_structures_old + j].get_potential_energy(), + forces=generated_structures[num_structures_old + j].get_forces() + ) + print("All futures completed") + + # Remove structures that failed the checks + for j, atoms in reversed(list(enumerate(generated_structures))): + if atoms is None: + energy_unrlxd = np.delete(energy_unrlxd, j-num_structures_old) + energy_rlxd = np.delete(energy_rlxd, j-num_structures_old) + del generated_structures[j] + del unrlxd_structures[j] + del rlxd_structures[j] + generator.remove_structure(j) + num_structures_new = len(generated_structures) + + # write the structures to files + for i in range(num_structures_new - num_structures_old): + write(iterdir+f"POSCAR_{i}", generated_structures[num_structures_old + i]) + print(f"Structure {i} energy per atom: {energy_rlxd[i]}") + # append energy per atom to the 'energies_unrlxd_filename' file + with open(energies_unrlxd_filename, "a") as energy_file: + energy_file.write(f"{i+num_structures_old} {energy_unrlxd[i]}\n") + # append energy per atom to the 'energies_rlxd_filename' file + with open(energies_rlxd_filename, "a") as energy_file: + energy_file.write(f"{i+num_structures_old} {energy_rlxd[i]}\n") + + # update the distribution functions + print("Updating distributions") + generator.distributions.update(generated_structures[num_structures_old:], from_host=False, deallocate_systems=False) + + # print the new distribution functions to a file + print("Printing distributions") + generator.distributions.write_dfs(iterdir+"distributions.txt") + generator.distributions.write_2body(iterdir+"df2.txt") + generator.distributions.write_3body(iterdir+"df3.txt") + generator.distributions.write_4body(iterdir+"df4.txt") + generator.distributions.deallocate_systems() + + # update the number of structures generated + num_structures_old = num_structures_new + + # Write the final distribution functions to a file + generator.distributions.write_gdfs(f"gdfs_seed{seed}.txt") + + # Read energies from the file + with open(energies_rlxd_filename, "r") as energy_file: + energies = energy_file.readlines() + + # Parse and sort the energies + energies = [line.strip().split() for line in energies] + energies = sorted(energies, key=lambda x: float(x[1])) + + # Write the sorted energies back to the file + with open(f"sorted_{energies_rlxd_filename}", "w") as energy_file: + for entry in energies: + energy_file.write(f"{int(entry[0])} {float(entry[1])}\n") + + # Write the structures to files + write(f"unrlxd_structures_seed{seed}.traj", unrlxd_structures) + write(f"rlxd_structures_seed{seed}.traj", rlxd_structures) + print("All generated and relaxed structures written") + + print("Learning complete") \ No newline at end of file diff --git a/example/python_pkg/Al_learn/DRAFFLE/learn_placement.py b/example/python_pkg/Al_learn/DRAFFLE/learn_placement.py new file mode 100644 index 00000000..d18fda80 --- /dev/null +++ b/example/python_pkg/Al_learn/DRAFFLE/learn_placement.py @@ -0,0 +1,314 @@ +# from mace.calculators import mace_mp +# from ase.calculators.vasp import Vasp +from chgnet.model import CHGNetCalculator +from raffle.generator import raffle_generator +from ase import build, Atoms +from ase.optimize import BFGS, FIRE +from ase.io import write +from ase.visualize import view +import numpy as np +import os +from concurrent.futures import ProcessPoolExecutor, wait, as_completed +from multiprocessing import Process +from copy import deepcopy +from multiprocessing import Queue +from joblib import Parallel, delayed + +import logging +logging.basicConfig(level=logging.DEBUG) + +def runInParallel(*fns): + proc = [] + results = [] + for fn in fns: + p = Process(target=fn) + p.start() + proc.append(p) + for p in proc: + results.append(p.join()) + + print("All processes finished") + print(results) + + +def process_structure_with_queue(i, structure, num_old, calc_params, optimise_structure, iteration, queue): + # Perform the computation + result = process_structure(i, structure, num_old, calc_params, optimise_structure, iteration) + queue.put(result) # Report completion + +def process_structure(i, atoms, num_structures_old, calc_params, optimise_structure, iteration): + if i < num_structures_old: + return + + # calc = Vasp(**calc_params, label=f"struct{i}", directory=f"iteration{iteration}/struct{i}/", txt=f"stdout{i}.o") + inew = i - num_structures_old + atoms.calc = calc + # positions_initial = atoms.get_positions() + + # Calculate and save the initial energy per atom + energy_unrlxd = atoms.get_potential_energy() / len(atoms) + print(f"Initial energy per atom: {energy_unrlxd}") + + # Optimise the structure if requested + if optimise_structure: + optimizer = FIRE(atoms, trajectory = f"traje{inew}.traj", logfile=f"optimisation{inew}.log") + try: + optimizer.run(fmax=0.05, steps=100) + except Exception as e: + print(f"Optimisation failed: {e}") + return None, None, None + + # Save the optimised structure and its energy per atom + energy_rlxd = atoms.get_potential_energy() / len(atoms) + + # Get the distance matrix + distances = atoms.get_all_distances(mic=True) + + # Set self-distances (diagonal entries) to infinity to ignore them + np.fill_diagonal(distances, np.inf) + + # Check if the minimum non-self distance is below 1.5 + if distances.min() < 1.0: + print(f"Distance too small: {atoms.get_all_distances(mic=True).min()}") + return None, None, None + + if abs(energy_rlxd - energy_unrlxd) > 10.0: + print(f"Energy difference too large: {energy_rlxd} vs {energy_unrlxd}") + return None, None, None + + return atoms, energy_unrlxd, energy_rlxd + +# crystal_structures = [ +# 'sc', 'fcc', 'bcc', 'hcp', +# 'diamond', 'zincblende', 'rocksalt', 'cesiumchloride', +# 'fluorite', 'wurtzite', 'tetragonal', 'orthorhombic', +# 'bct', 'rhombohedral', 'mcl' +# ] + + + +if __name__ == "__main__": + + calc_params = {} + calc = CHGNetCalculator() + # calc_params = { + # "model": "large", + # "dispersion": False, + # "default_dtype": "float32", + # "device": 'cpu' + # } + # calc = mace_mp(**calc_params) + # calc_params = { + # "command": "$HOME/DVASP/vasp.6.4.3/bin/vasp_std", + # # "label": "iteration", + # # "txt": "stdout.o", + # "xc": 'pbe', + # "setups": {'C': ''}, + # "kpts": (3, 3, 3), + # "encut": 400, + # "istart": 0, + # "icharg": 0, + # } + # ## DON'T FORGET TO EXPORT THE VASP_PP_PATH + # calc = Vasp(**calc_params, label="tmp", directory="tmp", txt="stdout.o") + + #crystal_structures = [ + # 'orthorhombic', 'diamond', + # 'bct', 'sc', + # 'fcc', 'bcc', 'hcp', + #] + + """ + This needs to be changed to set the material cells that will be searched through. + The crystal_structures list contains the crystal structures that will be used to generate the hosts. + """ + crystal_structures = [ + 'orthorhombic', 'hcp', + ] + + """ + This needs to be changed to set the lattice constants that will be searched through. + The lattice_constants list contains the lattice constants that will be used to generate the hosts. + """ + lattice_constants = np.linspace(3.1, 5.4, num=6) + + """ + This needs to be changed to set the values of the method_ratio. + """ + #void_val; rand_val; walk_val; grow_val; min_val + ##############[ V, R, W, G, M] + method_val = [85.0, 15.0, 0.0, 0.0, 0.0] #change + + + + hosts = [] + for crystal_structure in crystal_structures: + print(f'Crystal structure: {crystal_structure}') + for a in lattice_constants: + b = a + c = a + atom = build.bulk( + name = 'Al', + crystalstructure = crystal_structure, + a = a, + b = b, + c = c, + ) + hosts.append(Atoms('Al', positions=[(0, 0, 0)], cell=atom.get_cell(), pbc=True, calculator=calc)) + # hosts[-1].set_pbc(True) + # hosts[-1].calc = calc + print(hosts[-1]) + + print("number of hosts: ", len(hosts)) + + optimise_structure = True + mass = 26.9815385 + density = 1.61 # u/A^3 + # num_atoms = 7 + + for seed in range(1): + print(f"Seed: {seed}") + energies_rlxd_filename = f"energies_rlxd_seed{seed}.txt" + energies_unrlxd_filename = f"energies_unrlxd_seed{seed}.txt" + generator = raffle_generator() + generator.distributions.set_element_energies( + { + 'Al': 0.0 + } + ) + # set energy scale + generator.distributions.set_kBT(0.4) + # set the distribution function widths (2-body, 3-body, 4-body) + generator.distributions.set_width([0.025, np.pi/200.0, np.pi/200.0]) + + initial_database = [Atoms('Al', positions=[(0, 0, 0)], cell=[8, 8, 8], pbc=True)] + initial_database[0].calc = calc + + generator.distributions.create(initial_database) + + if os.path.exists(energies_rlxd_filename): + with open(energies_rlxd_filename, "w") as energy_file: + pass + else: + open(energies_rlxd_filename, "w").close() + + if os.path.exists(energies_unrlxd_filename): + with open(energies_unrlxd_filename, "w") as energy_file: + pass + else: + open(energies_unrlxd_filename, "w").close() + + + num_structures_old = 0 + unrlxd_structures = [] + rlxd_structures = [] + iter2 = 0 + for iter in range(10): + for host in hosts: + generator.set_host(host) + volume = host.get_volume() + + num_atoms = round(density * volume / mass) - 1 + if(num_atoms < 1): + continue + iter2 += 1 + print(f"Volume: {volume}") + print(f"Number of atoms: {num_atoms}") + + generator.generate( + num_structures = 5, + stoichiometry = { 'Al': num_atoms }, + seed = seed*1000+iter, + method_ratio = {"void": method_val[0], "rand": method_val[1], "walk": method_val[2], "grow": method_val[3], "min": method_val[4]}, + verbose = 0, + ) + + # print the number of structures generated + print("Total number of structures generated: ", generator.num_structures) + generated_structures = generator.get_structures(calc) + num_structures_new = len(generated_structures) + + # check if directory iteration[iter] exists, if not create it + iterdir = f"iteration{iter2}/" + if not os.path.exists(iterdir): + os.makedirs(iterdir) + generator.print_settings(iterdir+"generator_settings.txt") + + # set up list of energies + energy_unrlxd = np.zeros(num_structures_new - num_structures_old) + energy_rlxd = np.zeros(num_structures_new - num_structures_old) + for i in range(num_structures_new - num_structures_old): + write(iterdir+f"POSCAR_unrlxd_{i}", generated_structures[num_structures_old + i]) + print(f"Structure {i} energy per atom: {generated_structures[num_structures_old + i].get_potential_energy() / len(generated_structures[num_structures_old + i])}") + unrlxd_structures.append(deepcopy(generated_structures[num_structures_old + i])) + + # Start parallel execution + print("Starting parallel execution") + results = Parallel(n_jobs=5)( + delayed(process_structure)(i, deepcopy(generated_structures[i]), num_structures_old, calc_params, optimise_structure, iteration=seed) + for i in range(num_structures_old, num_structures_new) + ) + + # Wait for all futures to complete + for j, result in enumerate(results): + generated_structures[j+num_structures_old], energy_unrlxd[j], energy_rlxd[j] = result + rlxd_structures.append(deepcopy(generated_structures[j+num_structures_old])) + print("All futures completed") + + # Remove structures that failed the checks + for j, atoms in reversed(list(enumerate(generated_structures))): + if atoms is None: + energy_unrlxd = np.delete(energy_unrlxd, j-num_structures_old) + energy_rlxd = np.delete(energy_rlxd, j-num_structures_old) + del generated_structures[j] + # del unrlxd_structures[j] + del rlxd_structures[j] + generator.remove_structure(j) + num_structures_new = len(generated_structures) + + # write the structures to files + for i in range(num_structures_new - num_structures_old): + write(iterdir+f"POSCAR_{i}", generated_structures[num_structures_old + i]) + print(f"Structure {i} energy per atom: {energy_rlxd[i]}") + # append energy per atom to the 'energies_unrlxd_filename' file + with open(energies_unrlxd_filename, "a") as energy_file: + energy_file.write(f"{i+num_structures_old} {energy_unrlxd[i]}\n") + # append energy per atom to the 'energies_rlxd_filename' file + with open(energies_rlxd_filename, "a") as energy_file: + energy_file.write(f"{i+num_structures_old} {energy_rlxd[i]}\n") + + # update the distribution functions + print("Updating distributions") + generator.distributions.update(generated_structures[num_structures_old:], from_host=False, deallocate_systems=False) + + # print the new distribution functions to a file + print("Printing distributions") + generator.distributions.write_dfs(iterdir+"distributions.txt") + generator.distributions.write_2body(iterdir+"df2.txt") + generator.distributions.write_3body(iterdir+"df3.txt") + generator.distributions.write_4body(iterdir+"df4.txt") + generator.distributions.deallocate_systems() + + # update the number of structures generated + num_structures_old = num_structures_new + + generator.distributions.write_gdfs(f"gdfs_seed{seed}.txt") + + # Read energies from the file + with open(energies_rlxd_filename, "r") as energy_file: + energies = energy_file.readlines() + + # Parse and sort the energies + energies = [line.strip().split() for line in energies] + energies = sorted(energies, key=lambda x: float(x[1])) + + # Write the sorted energies back to the file + with open(f"sorted_{energies_rlxd_filename}", "w") as energy_file: + for entry in energies: + energy_file.write(f"{int(entry[0])} {float(entry[1])}\n") + + write(f"unrlxd_structures_seed{seed}.traj", unrlxd_structures) + write(f"rlxd_structures_seed{seed}.traj", rlxd_structures) + print("All generated and relaxed structures written") + + print("Learning complete") \ No newline at end of file diff --git a/example/python_pkg/Al_learn/DRAFFLE/pca.ipynb b/example/python_pkg/Al_learn/DRAFFLE/pca.ipynb new file mode 100644 index 00000000..ead714fe --- /dev/null +++ b/example/python_pkg/Al_learn/DRAFFLE/pca.ipynb @@ -0,0 +1,425 @@ +{ + "cells": [ + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "import matplotlib.pyplot as plt\n", + "%matplotlib inline\n", + "\n", + "# matplotlib.use(\"Agg\")\n", + "\n", + "from ase.visualize import view\n", + "\n", + "from ase.io import read\n", + "from agox.databases import Database\n", + "from agox.environments import Environment\n", + "from agox.utils.graph_sorting import Analysis\n", + "\n", + "import glob\n", + "import numpy as np\n", + "from sklearn.decomposition import PCA\n", + "from matplotlib.ticker import (MultipleLocator, AutoMinorLocator)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set up the plotting environment\n", + "# matplotlib.rcParams.update(matplotlib.rcParamsDefault)\n", + "plt.rc('text', usetex=True)\n", + "plt.rc('font', family='cmr10', size=12)\n", + "plt.rcParams[\"axes.formatter.use_mathtext\"] = True" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set the plotting parameters\n", + "seed = 0\n", + "identifier = \"\"" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set the descriptors\n", + "from agox.models.descriptors import SOAP\n", + "local_descriptor = local_descriptor = SOAP.from_species([\"Al\"], r_cut=5.0)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set the calculators\n", + "from chgnet.model import CHGNetCalculator\n", + "from ase.calculators.singlepoint import SinglePointCalculator\n", + "calc = CHGNetCalculator()" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Load known structures\n", + "poscar_files = glob.glob(\"../known_phases/*.vasp\")\n", + "known_phases = []\n", + "opacity_list = []\n", + "known_phase_labels = []\n", + "for poscar_file in poscar_files:\n", + " phase = read(poscar_file)\n", + " opacity = None\n", + " if \"mp-134.vasp\" in poscar_file:\n", + " print(\"FCC\")\n", + " cell = phase.get_cell()\n", + " cell = [ vec * 4.02 / np.linalg.norm(vec) for vec in cell]\n", + " phase.set_cell(cell, scale_atoms=True)\n", + " opacity = 1.0\n", + " label = \"FCC (mp-134)\"\n", + " elif \"mp-2647008.vasp\" in poscar_file:\n", + " print(\"HCP\")\n", + " cell = phase.get_cell()\n", + " cell = [ vec * 3.56 / np.linalg.norm(vec) for vec in cell]\n", + " phase.set_cell(cell, scale_atoms=True)\n", + " opacity = 0.6\n", + " label = \"HCP (mp-2647008)\"\n", + " elif \"mp-998860.vasp\" in poscar_file:\n", + " print(\"BCC\")\n", + " cell = phase.get_cell()\n", + " cell = [ vec * 3.10 / np.linalg.norm(vec) for vec in cell]\n", + " phase.set_cell(cell, scale_atoms=True)\n", + " opacity = 0.4\n", + " label = \"BCC (mp-998860)\"\n", + " elif \"mp-1183144.vasp\" in poscar_file:\n", + " print(\"$\\\\alpha$\")\n", + " cell = phase.get_cell()\n", + " # cell[0] = [ vec * 4.94 / np.linalg.norm(vec) for vec in cell]\n", + " # cell[1] = [ vec * 4.94 / np.linalg.norm(vec) for vec in cell]\n", + " cell[2] = cell[2] * 9.88 / np.linalg.norm(cell[2])\n", + " phase.set_cell(cell, scale_atoms=True)\n", + " opacity = 0.7\n", + " label = \"$\\\\alpha$ (mp-1183144)\"\n", + " else:\n", + " print(\"Skipping \", poscar_file)\n", + " continue\n", + " opacity_list.append(opacity)\n", + " known_phase_labels.append(label)\n", + " phase.calc = calc\n", + " known_phases.append(phase)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Load the unrelaxed structures\n", + "unrlxd_structures = read(\"DOutput\"+identifier+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "for structure in unrlxd_structures:\n", + " structure.calc = calc" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Load the relaxed structures\n", + "rlxd_structures = read(\"DOutput\"+identifier+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "for structure in rlxd_structures:\n", + " structure.calc = calc" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Read energies from energies_unrlxd_seed0.txt and add to the respective structures using a SinglePointCalculator\n", + "## The file has the form \"index energy\"\n", + "## This is done because there seem to be issues with storing the energy in the ASE trajectory file for some setups\n", + "filename = \"DOutput\"+identifier+\"/energies_unrlxd_seed\"+str(seed)+\".txt\"\n", + "with open(filename) as f:\n", + " for line in f:\n", + " index, energy = line.split()\n", + " index = int(index)\n", + " energy = float(energy)\n", + " unrlxd_structures[index].calc = SinglePointCalculator(unrlxd_structures[index], energy=energy * len(unrlxd_structures[index]))\n", + "\n", + "\n", + "filename = \"DOutput\"+identifier+\"/energies_rlxd_seed\"+str(seed)+\".txt\"\n", + "with open(filename) as f:\n", + " for line in f:\n", + " index, energy = line.split()\n", + " index = int(index)\n", + " energy = float(energy)\n", + " rlxd_structures[index].calc = SinglePointCalculator(rlxd_structures[index], energy=energy * len(rlxd_structures[index]))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the minimum energy\n", + "min_energy = np.min([structure.get_potential_energy()/len(structure) for structure in rlxd_structures])" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Calculate energies per atom for each unrelaxed structure\n", + "energies_per_atom = [structure.get_potential_energy() / len(structure) for structure in unrlxd_structures]\n", + "unrlxd_delta_en_per_atom = np.array(energies_per_atom) - min_energy\n", + "print(\"Unrelaxed min energy: \", np.min(energies_per_atom))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Calculate energies per atom for each relaxed structure\n", + "energies_per_atom = [structure.get_potential_energy() / len(structure) for structure in rlxd_structures]\n", + "rlxd_delta_en_per_atom = np.array(energies_per_atom) - min_energy\n", + "print(\"Relaxed min energy: \", np.min(energies_per_atom))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set up the PCA\n", + "pca = PCA(n_components=2)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the 'super atom' descriptors for the unrelaxed structures\n", + "unrlxd_super_atoms = []\n", + "for structure in unrlxd_structures:\n", + " unrlxd_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the 'super atom' descriptors for the relaxed structures\n", + "rlxd_super_atoms = []\n", + "for structure in rlxd_structures:\n", + " rlxd_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the 'super atom' descriptors for the known structures\n", + "known_super_atoms = []\n", + "for structure in known_phases:\n", + " known_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Fit the PCA model to the unrelaxed or relaxed structures\n", + "rlxd_string = \"rlxd\"" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Save pca model\n", + "import pickle\n", + "if True:\n", + " pca.fit(np.squeeze([arr for arr in rlxd_super_atoms]))\n", + " with open(\"pca_model_all_rlxd_\"+str(seed)+\".pkl\", \"wb\") as f:\n", + " pickle.dump(pca, f)\n", + "\n", + "## Load pca model\n", + "with open(\"pca_model_all_\"+rlxd_string+\"_0.pkl\", \"rb\") as f:\n", + " pca = pickle.load(f)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Transform the unrelaxed and relaxed structures to the reduced space\n", + "unrlxd_X_reduced = pca.transform(np.squeeze([arr for arr in unrlxd_super_atoms]))\n", + "rlxd_X_reduced = pca.transform(np.squeeze([arr for arr in rlxd_super_atoms]))\n", + "known_X_reduced = pca.transform(np.squeeze([arr for arr in known_super_atoms]))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the index of the structure with the minimum energy\n", + "min_energy_index = np.argmin(rlxd_delta_en_per_atom)\n", + "print(min_energy_index)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Plot the PCA\n", + "fig, axes = plt.subplots(nrows=1, ncols=2, figsize=(8, 6))\n", + "\n", + "plt.subplots_adjust(wspace=0.05, hspace=0)\n", + "\n", + "## Get the maximum energy for the colourbar\n", + "max_en = min(3.0, max(np.max(unrlxd_delta_en_per_atom), np.max(rlxd_delta_en_per_atom)))\n", + "\n", + "## Plot the PCA\n", + "axes[0].scatter(unrlxd_X_reduced[:, 0], unrlxd_X_reduced[:, 1], c=unrlxd_delta_en_per_atom, cmap=\"viridis\", vmin = 0, vmax = max_en)\n", + "axes[1].scatter(rlxd_X_reduced[:, 0], rlxd_X_reduced[:, 1], c=rlxd_delta_en_per_atom, cmap=\"viridis\", vmin = 0, vmax = max_en)\n", + "\n", + "# Sort pairs of opacity and X_reduced by opacity value (highest to lowest)\n", + "sorted_pairs = sorted(zip(opacity_list, known_X_reduced, known_phase_labels), key=lambda x: x[0], reverse=False)\n", + "## Add the minimum energy structures to the plot\n", + "for ax in axes:\n", + " for i, X in enumerate(sorted_pairs):\n", + " ax.scatter(X[1][0], X[1][1], s=200, edgecolor=[1.0, 1.0-X[0], 1.0-X[0], X[0]], facecolor='none', linewidth=2, label=X[2])\n", + " if ax == axes[1]:\n", + " handles, labels = ax.get_legend_handles_labels()\n", + " ax.legend(handles[::-1], labels[::-1], facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, bbox_to_anchor=(1.041, 1.0), fontsize=20, handletextpad=0.2, borderpad=0.3, handlelength=1)\n", + " \n", + "## Add labels\n", + "fig.text(0.5, 0.0, 'Principal component 1', ha='center', fontsize=20)\n", + "axes[0].set_ylabel('Principal component 2', fontsize=20)\n", + "axes[0].set_title('Unrelaxed', fontsize=20)\n", + "axes[1].set_title('Relaxed', fontsize=20)\n", + "if rlxd_string == \"rlxd\":\n", + " xlims = [-30, 70]\n", + " ylims = [-5, 20]\n", + "else:\n", + " xlims = [-42, 55]\n", + " ylims = [-12, 30]\n", + "\n", + "for ax in axes:\n", + " ax.tick_params(axis='both', direction='in', length=6, labelsize=20)\n", + " # ax.yaxis.set_major_locator(MultipleLocator(3))\n", + " ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.xaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.tick_params(axis='both', which='minor', length=3, direction='in')\n", + " ax.set_xlim(xlims)\n", + " ax.set_ylim(ylims)\n", + "\n", + "## Unify tick labels\n", + "xticks = axes[0].get_xticks()\n", + "xticks = xticks[(xticks >= xlims[0]) & (xticks <= xlims[1])]\n", + "\n", + "axes[1].set_xticks(xticks)\n", + "axes[1].set_yticklabels([])\n", + "axes[0].tick_params(axis='x', labelbottom=True, top=True)\n", + "axes[1].tick_params(axis='x', labelbottom=True, top=True)\n", + "axes[0].tick_params(axis='y', labelbottom=True, right=True)\n", + "axes[1].tick_params(axis='y', labelbottom=True, right=True)\n", + "\n", + "## Make axes[0] and axes[1] the same width\n", + "axes[0].set_box_aspect(1.7)\n", + "axes[1].set_box_aspect(1.7)\n", + "\n", + "## Add colorbar next to the axes\n", + "cbar = fig.colorbar(axes[1].collections[0], ax=axes, orientation='vertical', fraction=0.085, pad=0.02)\n", + "cbar.ax.tick_params(labelsize=20)\n", + "cbar.ax.yaxis.set_major_locator(MultipleLocator(1))\n", + "cbar.ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + "cbar.set_label('Formation energy (eV/atom)', fontsize=20)\n", + "\n", + "## Save the figure\n", + "plt.savefig('Al_RAFFLE_pca_'+rlxd_string+'_fit_seed'+str(seed)+'.pdf', bbox_inches='tight', pad_inches=0, facecolor=fig.get_facecolor(), edgecolor='none')" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Identify the line of structures in the lower right corner\n", + "for i in range(len(rlxd_X_reduced)):\n", + " if rlxd_X_reduced[i, 0] > 40 and rlxd_X_reduced[i, 0] < 45 and rlxd_X_reduced[i, 1] > -5 and rlxd_X_reduced[i, 1] < 0:\n", + " print(i)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [] + } + ], + "metadata": { + "kernelspec": { + "display_name": "raffle_env", + "language": "python", + "name": "python3" + }, + "language_info": { + "codemirror_mode": { + "name": "ipython", + "version": 3 + }, + "file_extension": ".py", + "mimetype": "text/x-python", + "name": "python", + "nbconvert_exporter": "python", + "pygments_lexer": "ipython3", + "version": "3.12.8" + } + }, + "nbformat": 4, + "nbformat_minor": 2 +} diff --git a/example/python_pkg/Al_learn/DRAFFLE/pca_placement_boa.ipynb b/example/python_pkg/Al_learn/DRAFFLE/pca_placement_boa.ipynb new file mode 100644 index 00000000..f82c3bc6 --- /dev/null +++ b/example/python_pkg/Al_learn/DRAFFLE/pca_placement_boa.ipynb @@ -0,0 +1,603 @@ +{ + "cells": [ + { + "cell_type": "code", + "execution_count": 2, + "metadata": {}, + "outputs": [ + { + "name": "stderr", + "output_type": "stream", + "text": [ + "/home/ntt203/.conda/envs/raffle_env/lib/python3.12/site-packages/tqdm/auto.py:21: TqdmWarning: IProgress not found. Please update jupyter and ipywidgets. See https://ipywidgets.readthedocs.io/en/stable/user_install.html\n", + " from .autonotebook import tqdm as notebook_tqdm\n", + "2025-02-27 11:34:53,377\tINFO util.py:154 -- Missing packages: ['ipywidgets']. Run `pip install -U ipywidgets`, then restart the notebook server for rich notebook output.\n" + ] + } + ], + "source": [ + "import matplotlib.pyplot as plt\n", + "%matplotlib inline\n", + "\n", + "# matplotlib.use(\"Agg\")\n", + "\n", + "from ase.visualize import view\n", + "\n", + "from ase.io import read\n", + "from agox.databases import Database\n", + "from agox.environments import Environment\n", + "from agox.utils.graph_sorting import Analysis\n", + "\n", + "import glob\n", + "import numpy as np\n", + "from sklearn.decomposition import PCA\n", + "from matplotlib.ticker import (MultipleLocator, AutoMinorLocator)" + ] + }, + { + "cell_type": "code", + "execution_count": 3, + "metadata": {}, + "outputs": [], + "source": [ + "## Set up the plotting environment\n", + "# matplotlib.rcParams.update(matplotlib.rcParamsDefault)\n", + "plt.rc('text', usetex=True)\n", + "plt.rc('font', family='cmr10', size=12)\n", + "plt.rcParams[\"axes.formatter.use_mathtext\"] = True" + ] + }, + { + "cell_type": "code", + "execution_count": 4, + "metadata": {}, + "outputs": [], + "source": [ + "## Set the plotting parameters\n", + "seed = 0\n", + "identifier = \"\"\n", + "prefix = \"\"\n", + "method = \"2\"" + ] + }, + { + "cell_type": "code", + "execution_count": 5, + "metadata": {}, + "outputs": [], + "source": [ + "## Set the descriptors\n", + "from agox.models.descriptors import SOAP\n", + "local_descriptor = local_descriptor = SOAP.from_species([\"Al\"], r_cut=5.0)" + ] + }, + { + "cell_type": "code", + "execution_count": 6, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "CHGNet v0.3.0 initialized with 412,525 parameters\n", + "CHGNet will run on cuda\n" + ] + } + ], + "source": [ + "## Set the calculators\n", + "from chgnet.model import CHGNetCalculator\n", + "from ase.calculators.singlepoint import SinglePointCalculator\n", + "calc = CHGNetCalculator()" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "BCC\n", + "$\\alpha$\n", + "FCC\n", + "HCP\n" + ] + } + ], + "source": [ + "## Load known structures\n", + "poscar_files = glob.glob(\"../known_phases/*.vasp\")\n", + "known_phases = []\n", + "opacity_list = []\n", + "known_phase_labels = []\n", + "for poscar_file in poscar_files:\n", + " phase = read(poscar_file)\n", + " opacity = None\n", + " if \"mp-134.vasp\" in poscar_file:\n", + " print(\"FCC\")\n", + " cell = phase.get_cell()\n", + " cell = [ vec * 4.02 / np.linalg.norm(vec) for vec in cell]\n", + " phase.set_cell(cell, scale_atoms=True)\n", + " opacity = 1.0\n", + " label = \"FCC (mp-134)\"\n", + " elif \"mp-2647008.vasp\" in poscar_file:\n", + " print(\"HCP\")\n", + " cell = phase.get_cell()\n", + " cell = [ vec * 3.56 / np.linalg.norm(vec) for vec in cell]\n", + " phase.set_cell(cell, scale_atoms=True)\n", + " opacity = 0.6\n", + " label = \"HCP (mp-2647008)\"\n", + " elif \"mp-998860.vasp\" in poscar_file:\n", + " print(\"BCC\")\n", + " cell = phase.get_cell()\n", + " cell = [ vec * 3.10 / np.linalg.norm(vec) for vec in cell]\n", + " phase.set_cell(cell, scale_atoms=True)\n", + " opacity = 0.4\n", + " label = \"BCC (mp-998860)\"\n", + " elif \"mp-1183144.vasp\" in poscar_file:\n", + " print(\"$\\\\alpha$\")\n", + " cell = phase.get_cell()\n", + " # cell[0] = [ vec * 4.94 / np.linalg.norm(vec) for vec in cell]\n", + " # cell[1] = [ vec * 4.94 / np.linalg.norm(vec) for vec in cell]\n", + " cell[2] = cell[2] * 9.88 / np.linalg.norm(cell[2])\n", + " phase.set_cell(cell, scale_atoms=True)\n", + " opacity = 0.7\n", + " label = \"$\\\\alpha$ (mp-1183144)\"\n", + " else:\n", + " print(\"Skipping \", poscar_file)\n", + " continue\n", + " opacity_list.append(opacity)\n", + " known_phase_labels.append(label)\n", + " phase.calc = calc\n", + " known_phases.append(phase)" + ] + }, + { + "cell_type": "code", + "execution_count": 8, + "metadata": {}, + "outputs": [], + "source": [ + "## Load the unrelaxed structures\n", + "unrlxd_structures = read(prefix+\"DOutput\"+method+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "for structure in unrlxd_structures:\n", + " structure.calc = calc\n", + " " + ] + }, + { + "cell_type": "code", + "execution_count": 9, + "metadata": {}, + "outputs": [], + "source": [ + "## Load the relaxed structures\n", + "rlxd_structures = read(prefix+\"DOutput\"+method+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "for structure in rlxd_structures:\n", + " structure.calc = calc" + ] + }, + { + "cell_type": "code", + "execution_count": 10, + "metadata": {}, + "outputs": [], + "source": [ + "## Read energies from energies_unrlxd_seed0.txt and add to the respective structures using a SinglePointCalculator\n", + "## The file has the form \"index energy\"\n", + "## This is done because there seem to be issues with storing the energy in the ASE trajectory file for some setups\n", + "filename = prefix+\"DOutput\"+method+\"/energies_unrlxd_seed\"+str(seed)+\".txt\"\n", + "with open(filename) as f:\n", + " for line in f:\n", + " index, energy = line.split()\n", + " index = int(index)\n", + " energy = float(energy)\n", + " unrlxd_structures[index].calc = SinglePointCalculator(unrlxd_structures[index], energy=energy * len(unrlxd_structures[index]))\n", + "\n", + "\n", + "filename = prefix+\"DOutput\"+method+\"/energies_rlxd_seed\"+str(seed)+\".txt\"\n", + "with open(filename) as f:\n", + " for line in f:\n", + " index, energy = line.split()\n", + " index = int(index)\n", + " energy = float(energy)\n", + " rlxd_structures[index].calc = SinglePointCalculator(rlxd_structures[index], energy=energy * len(rlxd_structures[index]))" + ] + }, + { + "cell_type": "code", + "execution_count": 11, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the minimum energy\n", + "min_energy = np.min([structure.get_potential_energy()/len(structure) for structure in rlxd_structures])" + ] + }, + { + "cell_type": "code", + "execution_count": 12, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Unrelaxed min energy: -3.661088705062866\n" + ] + } + ], + "source": [ + "## Calculate energies per atom for each unrelaxed structure\n", + "energies_per_atom = [structure.get_potential_energy() / len(structure) for structure in unrlxd_structures]\n", + "unrlxd_delta_en_per_atom = np.array(energies_per_atom) - min_energy\n", + "print(\"Unrelaxed min energy: \", np.min(energies_per_atom))" + ] + }, + { + "cell_type": "code", + "execution_count": 13, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Relaxed min energy: -3.663501501083374\n" + ] + } + ], + "source": [ + "## Calculate energies per atom for each relaxed structure\n", + "energies_per_atom = [structure.get_potential_energy() / len(structure) for structure in rlxd_structures]\n", + "rlxd_delta_en_per_atom = np.array(energies_per_atom) - min_energy\n", + "print(\"Relaxed min energy: \", np.min(energies_per_atom))" + ] + }, + { + "cell_type": "code", + "execution_count": 14, + "metadata": {}, + "outputs": [], + "source": [ + "## Set up the PCA\n", + "pca = PCA(n_components=2)" + ] + }, + { + "cell_type": "code", + "execution_count": 15, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the 'super atom' descriptors for the unrelaxed structures\n", + "unrlxd_super_atoms = []\n", + "for structure in unrlxd_structures:\n", + " unrlxd_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" + ] + }, + { + "cell_type": "code", + "execution_count": 16, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the 'super atom' descriptors for the relaxed structures\n", + "rlxd_super_atoms = []\n", + "for structure in rlxd_structures:\n", + " rlxd_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" + ] + }, + { + "cell_type": "code", + "execution_count": 17, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the 'super atom' descriptors for the known structures\n", + "known_super_atoms = []\n", + "for structure in known_phases:\n", + " known_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" + ] + }, + { + "cell_type": "code", + "execution_count": 18, + "metadata": {}, + "outputs": [], + "source": [ + "## Fit the PCA model to the unrelaxed or relaxed structures\n", + "rlxd_string = \"rlxd\"" + ] + }, + { + "cell_type": "code", + "execution_count": 19, + "metadata": {}, + "outputs": [], + "source": [ + "## Save pca model\n", + "import pickle\n", + "if False:\n", + " pca.fit(np.squeeze([arr for arr in rlxd_super_atoms]))\n", + " with open(\"pca_model_all_rlxd_r_\"+str(seed)+\".pkl\", \"wb\") as f:\n", + " pickle.dump(pca, f)\n", + "\n", + "## Load pca model\n", + "with open(\"pca_model_all_\"+rlxd_string+\"_0.pkl\", \"rb\") as f:\n", + " pca = pickle.load(f)" + ] + }, + { + "cell_type": "code", + "execution_count": 20, + "metadata": {}, + "outputs": [], + "source": [ + "## Transform the unrelaxed and relaxed structures to the reduced space\n", + "unrlxd_X_reduced = pca.transform(np.squeeze([arr for arr in unrlxd_super_atoms]))\n", + "rlxd_X_reduced = pca.transform(np.squeeze([arr for arr in rlxd_super_atoms]))\n", + "known_X_reduced = pca.transform(np.squeeze([arr for arr in known_super_atoms]))" + ] + }, + { + "cell_type": "code", + "execution_count": 21, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "1031\n" + ] + } + ], + "source": [ + "## Get the index of the structure with the minimum energy\n", + "min_energy_index = np.argmin(rlxd_delta_en_per_atom)\n", + "print(min_energy_index)\n" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "26\n", + "[0, 1, 2, 3, 4, 60, 61, 62, 63, 64, 120, 121, 122, 123, 124, 180, 181, 182, 183, 184, 240, 241, 242, 243, 244, 300, 301, 302, 303, 304, 360, 361, 362, 363, 364, 420, 421, 422, 423, 424, 480, 481, 482, 483, 484, 540, 541, 542, 543, 544, 600, 601, 602, 603, 604, 660, 661, 662, 663, 664, 720, 721, 722, 723, 724, 780, 781, 782, 783, 784, 840, 841, 842, 843, 844, 900, 901, 902, 903, 904, 960, 961, 962, 963, 964, 1020, 1021, 1022, 1023, 1024, 1080, 1081, 1082, 1083, 1084, 1140, 1141, 1142, 1143, 1144]\n", + "[5, 6, 7, 8, 9, 65, 66, 67, 68, 69, 125, 126, 128, 129, 185, 187, 188, 189, 245, 246, 247, 248, 305, 306, 307, 365, 366, 367, 368, 369, 425, 426, 427, 429, 485, 488, 489, 545, 546, 548, 549, 605, 606, 608, 665, 666, 667, 668, 669, 725, 726, 728, 729, 785, 786, 787, 788, 845, 846, 847, 848, 849, 905, 906, 907, 908, 909, 965, 966, 968, 969, 1025, 1026, 1027, 1028, 1085, 1087, 1088, 1089, 1145, 1148, 1149]\n", + "[10, 11, 12, 13, 14, 70, 71, 72, 73, 74, 130, 132, 133, 134, 190, 191, 192, 193, 194, 251, 252, 254, 310, 312, 314, 370, 371, 372, 374, 431, 432, 433, 434, 490, 491, 492, 493, 494, 550, 551, 552, 553, 554, 610, 611, 612, 613, 614, 671, 672, 673, 674, 730, 731, 732, 733, 734, 790, 792, 793, 794, 850, 851, 852, 853, 854, 910, 911, 912, 913, 914, 970, 972, 973, 974, 1031, 1032, 1033, 1034, 1090, 1091, 1093, 1150, 1151, 1152, 1153]\n", + "[15, 16, 17, 18, 19, 75, 76, 77, 78, 135, 136, 137, 139, 195, 196, 197, 198, 255, 256, 257, 259, 315, 317, 318, 319, 376, 377, 378, 437, 438, 439, 495, 496, 497, 498, 499, 555, 557, 558, 615, 617, 618, 619, 675, 676, 677, 678, 679, 735, 736, 737, 738, 739, 795, 797, 798, 799, 855, 856, 857, 858, 859, 915, 916, 917, 918, 919, 975, 976, 977, 978, 1035, 1036, 1037, 1038, 1039, 1095, 1096, 1097, 1098, 1099, 1155, 1156, 1157, 1158, 1159]\n", + "[20, 21, 22, 23, 24, 80, 81, 82, 83, 84, 140, 141, 142, 143, 144, 200, 201, 202, 203, 204, 260, 261, 262, 263, 264, 320, 321, 322, 323, 324, 380, 381, 382, 383, 384, 440, 441, 442, 443, 500, 501, 502, 503, 504, 560, 561, 562, 563, 564, 620, 621, 622, 623, 624, 680, 681, 682, 683, 684, 740, 741, 742, 743, 744, 800, 801, 802, 803, 804, 860, 861, 862, 863, 864, 920, 921, 922, 923, 924, 980, 981, 982, 983, 984, 1040, 1041, 1042, 1043, 1044, 1100, 1101, 1102, 1103, 1104, 1160, 1161, 1162, 1164]\n", + "[25, 26, 27, 28, 29, 85, 86, 87, 88, 89, 146, 147, 148, 149, 205, 206, 207, 265, 266, 267, 268, 269, 326, 327, 328, 329, 385, 387, 445, 446, 448, 449, 505, 506, 507, 509, 565, 567, 568, 626, 627, 628, 629, 685, 686, 687, 688, 745, 746, 747, 749, 805, 806, 808, 865, 866, 867, 869, 925, 926, 927, 986, 987, 989, 1047, 1049, 1105, 1107, 1108, 1109, 1165, 1166, 1167, 1168, 1169]\n", + "[30, 31, 32, 33, 34, 90, 91, 92, 93, 94, 151, 152, 211, 212, 270, 271, 274, 330, 331, 391, 393, 450, 451, 453, 510, 511, 512, 513, 514, 571, 630, 631, 633, 634, 690, 691, 693, 751, 753, 811, 812, 870, 872, 873, 931, 932, 933, 1054, 1110, 1111, 1172, 1173]\n", + "[35, 36, 37, 38, 39, 95, 96, 156, 157, 158, 216, 218, 219, 275, 276, 277, 279, 335, 336, 396, 455, 456, 457, 515, 516, 518, 576, 577, 579, 635, 636, 638, 639, 695, 697, 698, 699, 758, 759, 816, 817, 819, 875, 876, 879, 936, 937, 939, 1059, 1115, 1116, 1117, 1118, 1119, 1177, 1178, 1179]\n", + "[40, 41, 43, 44, 100, 104, 160, 161, 162, 220, 221, 223, 280, 281, 283, 284, 340, 400, 403, 404, 460, 461, 462, 520, 523, 524, 580, 582, 583, 640, 642, 700, 702, 703, 704, 760, 763, 764, 820, 822, 823, 880, 884, 940, 941, 942, 1000, 1060, 1120, 1121, 1122, 1123, 1124, 1180, 1182]\n", + "[42, 101, 102, 163, 282, 342, 344, 401, 402, 464, 521, 641, 644, 701, 824, 881, 882, 943, 944, 1001, 1004, 1062, 1063, 1181, 1183, 1184]\n", + "[45, 46, 47, 48, 106, 107, 108, 109, 165, 166, 167, 168, 169, 225, 228, 229, 285, 287, 288, 289, 345, 346, 347, 349, 405, 406, 407, 408, 409, 465, 466, 467, 468, 469, 525, 526, 527, 528, 529, 585, 586, 587, 588, 589, 645, 646, 648, 649, 705, 706, 707, 765, 766, 767, 768, 769, 825, 826, 827, 829, 885, 886, 887, 888, 889, 946, 947, 948, 949, 1005, 1006, 1007, 1009, 1065, 1066, 1067, 1068, 1069, 1126, 1127, 1128, 1129, 1185, 1186, 1187, 1188, 1189]\n", + "[49, 105, 226, 227, 286, 348, 647, 708, 709, 828, 945, 1008, 1125]\n", + "[50, 51, 52, 53, 54, 55, 56, 58, 59, 110, 111, 112, 113, 114, 115, 116, 117, 118, 119, 170, 171, 172, 173, 174, 175, 176, 177, 178, 179, 230, 231, 232, 233, 234, 235, 236, 237, 238, 239, 290, 291, 292, 293, 294, 295, 296, 297, 298, 299, 350, 351, 352, 353, 354, 355, 356, 357, 358, 359, 410, 411, 412, 413, 414, 415, 416, 417, 418, 419, 470, 471, 472, 473, 474, 475, 476, 477, 478, 479, 530, 531, 532, 533, 534, 535, 536, 537, 538, 590, 591, 592, 593, 594, 595, 596, 598, 599, 650, 651, 652, 653, 654, 655, 656, 657, 658, 659, 710, 711, 712, 713, 715, 716, 717, 718, 719, 770, 771, 772, 773, 774, 775, 776, 777, 778, 779, 830, 831, 832, 833, 834, 835, 836, 837, 838, 839, 890, 891, 892, 893, 894, 895, 896, 897, 898, 899, 950, 951, 952, 953, 954, 955, 956, 957, 958, 1010, 1012, 1013, 1014, 1015, 1016, 1017, 1018, 1019, 1070, 1071, 1072, 1073, 1074, 1075, 1076, 1077, 1078, 1079, 1130, 1131, 1132, 1133, 1134, 1135, 1136, 1137, 1138, 1139, 1190, 1191, 1192, 1193, 1194, 1195, 1196, 1197, 1198, 1199]\n", + "[57, 597, 959]\n", + "[79, 138, 199, 258, 316, 375, 379, 435, 436, 556, 559, 616, 796, 979]\n", + "[97, 98, 99, 155, 159, 215, 217, 278, 337, 338, 339, 395, 397, 398, 399, 458, 459, 517, 519, 575, 578, 637, 696, 755, 756, 757, 815, 818, 877, 878, 935, 938, 995, 996, 997, 998, 999, 1055, 1056, 1057, 1058, 1175, 1176]\n", + "[103, 164, 222, 224, 341, 343, 463, 522, 581, 584, 643, 761, 762, 821, 883, 1002, 1003, 1061, 1064]\n", + "[127, 186, 249, 308, 309, 428, 486, 487, 547, 607, 609, 727, 789, 1146, 1147]\n", + "[131, 250, 253, 311, 313, 373, 430, 670, 791, 971, 1030, 1092, 1094, 1154]\n", + "[145, 208, 209, 325, 386, 388, 389, 447, 566, 569, 625, 689, 714, 748, 807, 809, 868, 928, 929, 985, 1045, 1048, 1106]\n", + "[150, 153, 154, 210, 213, 214, 272, 273, 332, 333, 334, 390, 392, 394, 452, 454, 570, 572, 573, 574, 632, 692, 694, 750, 752, 754, 810, 813, 814, 871, 874, 930, 934, 990, 991, 992, 993, 994, 1050, 1051, 1052, 1053, 1112, 1113, 1114, 1170, 1171, 1174]\n", + "[444, 1163]\n", + "[508, 988, 1046]\n", + "[539]\n", + "[967, 1029, 1086]\n", + "[1011]\n" + ] + } + ], + "source": [ + "tol_x = 3 # Adjust as needed\n", + "tol_y = 0.2\n", + "clusters = [] # will store the current \"center\" of each cluster (basin)\n", + "cluster_indices = [] # list of lists: each sublist stores indices belonging to that cluster\n", + "\n", + "for i, pt in enumerate(rlxd_X_reduced):\n", + " assigned = False\n", + " for j, center in enumerate(clusters):\n", + " if all( abs(pt - center) < [tol_x, tol_y] ):\n", + " # Add index to this cluster and update the cluster center (mean of points)\n", + " cluster_indices[j].append(i)\n", + " clusters[j] = np.mean(rlxd_X_reduced[cluster_indices[j]], axis=0)\n", + " assigned = True\n", + " break\n", + " if not assigned:\n", + " # Start a new cluster\n", + " clusters.append(pt.copy())\n", + " cluster_indices.append([i])\n", + "\n", + "print(len(cluster_indices))\n", + "for i in range(len(cluster_indices)):\n", + " print(cluster_indices[i])\n" + ] + }, + { + "cell_type": "code", + "execution_count": 23, + "metadata": {}, + "outputs": [ + { + "data": { + "image/png": "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", + "text/plain": [ + "
" + ] + }, + "metadata": {}, + "output_type": "display_data" + } + ], + "source": [ + "from matplotlib import cm\n", + "\n", + "n_clusters = len(clusters)\n", + "colors = cm.tab20(np.linspace(0, 1, n_clusters))\n", + "for idx, indices in enumerate(cluster_indices):\n", + " plt.scatter(unrlxd_X_reduced[indices, 0],unrlxd_X_reduced[indices, 1], color=colors[idx])" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "[1.0, 0.6, 0.6, 0.4]\n", + "[1.0, 0.4, 0.4, 0.6]\n", + "[1.0, 0.30000000000000004, 0.30000000000000004, 0.7]\n", + "[1.0, 0.0, 0.0, 1.0]\n", + "[1.0, 0.6, 0.6, 0.4]\n", + "[1.0, 0.4, 0.4, 0.6]\n", + "[1.0, 0.30000000000000004, 0.30000000000000004, 0.7]\n", + "[1.0, 0.0, 0.0, 1.0]\n" + ] + }, + { + "data": { + "image/png": "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", + "text/plain": [ + "
" + ] + }, + "metadata": {}, + "output_type": "display_data" + } + ], + "source": [ + "## Plot the PCA\n", + "fig, axes = plt.subplots(nrows=1, ncols=2, figsize=(8, 6))\n", + "\n", + "plt.subplots_adjust(wspace=0.05, hspace=0)\n", + "\n", + "## Get the maximum energy for the colourbar\n", + "#max_en = min(3.0, max(np.max(unrlxd_delta_en_per_atom), np.max(rlxd_delta_en_per_atom)))\n", + "\n", + "## Plot the PCA\n", + "colorlist = [\n", + " (0.4, 0.4, 0.8, 1.0),\n", + " (0.4, 0.8, 0.4, 1.0),\n", + " (1.0, 0.0, 0.0, 1.0),\n", + " (1.0, 0.6, 0.6, 1.0),\n", + " ]\n", + "i = -1\n", + "for idx, indices in reversed(list(enumerate(cluster_indices))):\n", + " if idx in [ 0, 2, 7, 12]: # [tol_x = 3, tol_y = 0.2]\n", + " i += 1\n", + " #plt.scatter(unrlxd_X_reduced[indices, 0],unrlxd_X_reduced[indices, 1], color=colors[idx])\n", + " axes[0].scatter(unrlxd_X_reduced[indices, 0], unrlxd_X_reduced[indices, 1], color=colorlist[i])\n", + " axes[1].scatter(rlxd_X_reduced[indices, 0], rlxd_X_reduced[indices, 1], color=colorlist[i])\n", + "\n", + "#axes[0].scatter(unrlxd_X_reduced[:, 0], unrlxd_X_reduced[:, 1], c=unrlxd_delta_en_per_atom, cmap=\"viridis\", vmin = 0, vmax = max_en)\n", + "#axes[1].scatter(rlxd_X_reduced[:, 0], rlxd_X_reduced[:, 1], c=rlxd_delta_en_per_atom, cmap=\"viridis\", vmin = 0, vmax = max_en)\n", + "\n", + "\n", + "# Sort pairs of opacity and X_reduced by opacity value (highest to lowest)\n", + "sorted_pairs = sorted(zip(opacity_list, known_X_reduced, known_phase_labels), key=lambda x: x[0], reverse=False)\n", + "## Add the minimum energy structures to the plot\n", + "for ax in axes:\n", + " for i, X in enumerate(sorted_pairs):\n", + " ax.scatter(X[1][0], X[1][1], s=200, edgecolor=[1.0, 1.0-X[0], 1.0-X[0], X[0]], facecolor='none', linewidth=2, label=X[2])\n", + " if ax == axes[1]:\n", + " handles, labels = ax.get_legend_handles_labels()\n", + " ax.legend(handles[::-1], labels[::-1], facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, bbox_to_anchor=(1.041, 1.0), fontsize=20, handletextpad=0.2, borderpad=0.3, handlelength=1)\n", + " \n", + "\n", + "\n", + "## Add labels\n", + "fig.text(0.5, 0.0, 'Principal component 1', ha='center', fontsize=20)\n", + "axes[0].set_ylabel('Principal component 2', fontsize=20)\n", + "axes[0].set_title('Unrelaxed', fontsize=20)\n", + "axes[1].set_title('Relaxed', fontsize=20)\n", + "if rlxd_string == \"rlxd\":\n", + " xlims = [-30, 65]\n", + " ylims = [-5, 20]\n", + "else:\n", + " xlims = [-42, 55]\n", + " ylims = [-12, 30]\n", + "\n", + "for ax in axes:\n", + " ax.tick_params(axis='both', direction='in', length=6, labelsize=20)\n", + " # ax.yaxis.set_major_locator(MultipleLocator(3))\n", + " ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.xaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.tick_params(axis='both', which='minor', length=3, direction='in')\n", + " ax.set_xlim(xlims)\n", + " ax.set_ylim(ylims)\n", + "\n", + "## Unify tick labels\n", + "xticks = axes[0].get_xticks()\n", + "xticks = xticks[(xticks >= xlims[0]) & (xticks <= xlims[1])]\n", + "\n", + "axes[1].set_xticks(xticks)\n", + "axes[1].set_yticklabels([])\n", + "axes[0].tick_params(axis='x', labelbottom=True, top=True)\n", + "axes[1].tick_params(axis='x', labelbottom=True, top=True)\n", + "axes[0].tick_params(axis='y', labelbottom=True, right=True)\n", + "axes[1].tick_params(axis='y', labelbottom=True, right=True)\n", + "\n", + "## Make axes[0] and axes[1] the same width\n", + "axes[0].set_box_aspect(1.7)\n", + "axes[1].set_box_aspect(1.7)\n", + "\n", + "## Add colorbar next to the axes\n", + "#cbar = fig.colorbar(axes[1].collections[0], ax=axes, orientation='vertical', fraction=0.085, pad=0.02)\n", + "#cbar.set_label('Formation energy (eV/atom)', fontsize=15)\n", + "\n", + "## Save the figure\n", + "plt.savefig('Al_RAFFLE_pca_'+rlxd_string+'_fit_seed'+str(seed)+'_boa_custom.pdf', bbox_inches='tight', pad_inches=0, facecolor=fig.get_facecolor(), edgecolor='none')\n" + ] + }, + { + "cell_type": "code", + "execution_count": 25, + "metadata": {}, + "outputs": [], + "source": [ + "## Identify the line of structures in the lower right corner\n", + "for i in range(len(rlxd_X_reduced)):\n", + " if rlxd_X_reduced[i, 0] > 40 and rlxd_X_reduced[i, 0] < 45 and rlxd_X_reduced[i, 1] > -5 and rlxd_X_reduced[i, 1] < 0:\n", + " print(i)" + ] + } + ], + "metadata": { + "kernelspec": { + "display_name": "Python 3", + "language": "python", + "name": "python3" + }, + "language_info": { + "codemirror_mode": { + "name": "ipython", + "version": 3 + }, + "file_extension": ".py", + "mimetype": "text/x-python", + "name": "python", + "nbconvert_exporter": "python", + "pygments_lexer": "ipython3", + "version": "3.12.2" + } + }, + "nbformat": 4, + "nbformat_minor": 2 +} diff --git a/example/python_pkg/Al_learn/DRAFFLE/pca_placement_boa_ratios.ipynb b/example/python_pkg/Al_learn/DRAFFLE/pca_placement_boa_ratios.ipynb new file mode 100644 index 00000000..7348db06 --- /dev/null +++ b/example/python_pkg/Al_learn/DRAFFLE/pca_placement_boa_ratios.ipynb @@ -0,0 +1,656 @@ +{ + "cells": [ + { + "cell_type": "code", + "execution_count": 33, + "metadata": {}, + "outputs": [], + "source": [ + "import matplotlib.pyplot as plt\n", + "%matplotlib inline\n", + "\n", + "# matplotlib.use(\"Agg\")\n", + "\n", + "from ase.visualize import view\n", + "\n", + "from ase.io import read\n", + "from agox.databases import Database\n", + "from agox.environments import Environment\n", + "from agox.utils.graph_sorting import Analysis\n", + "\n", + "import glob\n", + "import numpy as np\n", + "from sklearn.decomposition import PCA\n", + "from matplotlib.ticker import (MultipleLocator, AutoMinorLocator)" + ] + }, + { + "cell_type": "code", + "execution_count": 34, + "metadata": {}, + "outputs": [], + "source": [ + "## Set up the plotting environment\n", + "# matplotlib.rcParams.update(matplotlib.rcParamsDefault)\n", + "plt.rc('text', usetex=True)\n", + "plt.rc('font', family='cmr10', size=12)\n", + "plt.rcParams[\"axes.formatter.use_mathtext\"] = True" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set the plotting parameters\n", + "seed = 0\n", + "identifier = \"\"\n", + "prefix = \"DRatios/DALL_TMP/\"\n", + "method = \"_v1_r0_w0_g0_m0\"" + ] + }, + { + "cell_type": "code", + "execution_count": 36, + "metadata": {}, + "outputs": [], + "source": [ + "## Set the descriptors\n", + "from agox.models.descriptors import SOAP\n", + "local_descriptor = local_descriptor = SOAP.from_species([\"Al\"], r_cut=5.0)" + ] + }, + { + "cell_type": "code", + "execution_count": 37, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "CHGNet v0.3.0 initialized with 412,525 parameters\n", + "CHGNet will run on cuda\n" + ] + } + ], + "source": [ + "## Set the calculators\n", + "from chgnet.model import CHGNetCalculator\n", + "from ase.calculators.singlepoint import SinglePointCalculator\n", + "calc = CHGNetCalculator()" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "BCC\n", + "$\\alpha$\n", + "FCC\n", + "HCP\n" + ] + } + ], + "source": [ + "## Load known structures\n", + "poscar_files = glob.glob(\"../known_phases/*.vasp\")\n", + "known_phases = []\n", + "opacity_list = []\n", + "known_phase_labels = []\n", + "for poscar_file in poscar_files:\n", + " phase = read(poscar_file)\n", + " opacity = None\n", + " if \"mp-134.vasp\" in poscar_file:\n", + " print(\"FCC\")\n", + " cell = phase.get_cell()\n", + " cell = [ vec * 4.02 / np.linalg.norm(vec) for vec in cell]\n", + " phase.set_cell(cell, scale_atoms=True)\n", + " opacity = 1.0\n", + " label = \"FCC (mp-134)\"\n", + " elif \"mp-2647008.vasp\" in poscar_file:\n", + " print(\"HCP\")\n", + " cell = phase.get_cell()\n", + " cell = [ vec * 3.56 / np.linalg.norm(vec) for vec in cell]\n", + " phase.set_cell(cell, scale_atoms=True)\n", + " opacity = 0.6\n", + " label = \"HCP (mp-2647008)\"\n", + " elif \"mp-998860.vasp\" in poscar_file:\n", + " print(\"BCC\")\n", + " cell = phase.get_cell()\n", + " cell = [ vec * 3.10 / np.linalg.norm(vec) for vec in cell]\n", + " phase.set_cell(cell, scale_atoms=True)\n", + " opacity = 0.4\n", + " label = \"BCC (mp-998860)\"\n", + " elif \"mp-1183144.vasp\" in poscar_file:\n", + " print(\"$\\\\alpha$\")\n", + " cell = phase.get_cell()\n", + " # cell[0] = [ vec * 4.94 / np.linalg.norm(vec) for vec in cell]\n", + " # cell[1] = [ vec * 4.94 / np.linalg.norm(vec) for vec in cell]\n", + " cell[2] = cell[2] * 9.88 / np.linalg.norm(cell[2])\n", + " phase.set_cell(cell, scale_atoms=True)\n", + " opacity = 0.7\n", + " label = \"$\\\\alpha$ (mp-1183144)\"\n", + " else:\n", + " print(\"Skipping \", poscar_file)\n", + " continue\n", + " opacity_list.append(opacity)\n", + " known_phase_labels.append(label)\n", + " phase.calc = calc\n", + " known_phases.append(phase)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Load the unrelaxed structures\n", + "unrlxd_structures = read(prefix+\"DOutput\"+method+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "for structure in unrlxd_structures:\n", + " structure.calc = calc\n", + " " + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Load the relaxed structures\n", + "rlxd_structures = read(prefix+\"DOutput\"+method+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "for structure in rlxd_structures:\n", + " structure.calc = calc" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Read energies from energies_unrlxd_seed0.txt and add to the respective structures using a SinglePointCalculator\n", + "## The file has the form \"index energy\"\n", + "## This is done because there seem to be issues with storing the energy in the ASE trajectory file for some setups\n", + "filename = prefix+\"DOutput\"+method+\"/energies_unrlxd_seed\"+str(seed)+\".txt\"\n", + "with open(filename) as f:\n", + " for line in f:\n", + " index, energy = line.split()\n", + " index = int(index)\n", + " energy = float(energy)\n", + " unrlxd_structures[index].calc = SinglePointCalculator(unrlxd_structures[index], energy=energy * len(unrlxd_structures[index]))\n", + "\n", + "\n", + "filename = prefix+\"DOutput\"+method+\"/energies_rlxd_seed\"+str(seed)+\".txt\"\n", + "with open(filename) as f:\n", + " for line in f:\n", + " index, energy = line.split()\n", + " index = int(index)\n", + " energy = float(energy)\n", + " rlxd_structures[index].calc = SinglePointCalculator(rlxd_structures[index], energy=energy * len(rlxd_structures[index]))" + ] + }, + { + "cell_type": "code", + "execution_count": 42, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the minimum energy\n", + "min_energy = np.min([structure.get_potential_energy()/len(structure) for structure in rlxd_structures])" + ] + }, + { + "cell_type": "code", + "execution_count": 43, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Unrelaxed min energy: -3.661088705062866\n" + ] + } + ], + "source": [ + "## Calculate energies per atom for each unrelaxed structure\n", + "energies_per_atom = [structure.get_potential_energy() / len(structure) for structure in unrlxd_structures]\n", + "unrlxd_delta_en_per_atom = np.array(energies_per_atom) - min_energy\n", + "print(\"Unrelaxed min energy: \", np.min(energies_per_atom))" + ] + }, + { + "cell_type": "code", + "execution_count": 44, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Relaxed min energy: -3.663501501083374\n" + ] + } + ], + "source": [ + "## Calculate energies per atom for each relaxed structure\n", + "energies_per_atom = [structure.get_potential_energy() / len(structure) for structure in rlxd_structures]\n", + "rlxd_delta_en_per_atom = np.array(energies_per_atom) - min_energy\n", + "print(\"Relaxed min energy: \", np.min(energies_per_atom))" + ] + }, + { + "cell_type": "code", + "execution_count": 45, + "metadata": {}, + "outputs": [], + "source": [ + "## Set up the PCA\n", + "pca = PCA(n_components=2)" + ] + }, + { + "cell_type": "code", + "execution_count": 46, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the 'super atom' descriptors for the unrelaxed structures\n", + "unrlxd_super_atoms = []\n", + "for structure in unrlxd_structures:\n", + " unrlxd_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" + ] + }, + { + "cell_type": "code", + "execution_count": 47, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the 'super atom' descriptors for the relaxed structures\n", + "rlxd_super_atoms = []\n", + "for structure in rlxd_structures:\n", + " rlxd_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" + ] + }, + { + "cell_type": "code", + "execution_count": 48, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the 'super atom' descriptors for the known structures\n", + "known_super_atoms = []\n", + "for structure in known_phases:\n", + " known_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" + ] + }, + { + "cell_type": "code", + "execution_count": 49, + "metadata": {}, + "outputs": [], + "source": [ + "## Fit the PCA model to the unrelaxed or relaxed structures\n", + "rlxd_string = \"rlxd\"" + ] + }, + { + "cell_type": "code", + "execution_count": 50, + "metadata": {}, + "outputs": [], + "source": [ + "## Save pca model\n", + "import pickle\n", + "if False:\n", + " pca.fit(np.squeeze([arr for arr in rlxd_super_atoms]))\n", + " with open(\"pca_model_all_rlxd_r_\"+str(seed)+\".pkl\", \"wb\") as f:\n", + " pickle.dump(pca, f)\n", + "\n", + "## Load pca model\n", + "with open(\"pca_model_all_\"+rlxd_string+\"_0.pkl\", \"rb\") as f:\n", + " pca = pickle.load(f)" + ] + }, + { + "cell_type": "code", + "execution_count": 51, + "metadata": {}, + "outputs": [], + "source": [ + "## Transform the unrelaxed and relaxed structures to the reduced space\n", + "unrlxd_X_reduced = pca.transform(np.squeeze([arr for arr in unrlxd_super_atoms]))\n", + "rlxd_X_reduced = pca.transform(np.squeeze([arr for arr in rlxd_super_atoms]))\n", + "known_X_reduced = pca.transform(np.squeeze([arr for arr in known_super_atoms]))" + ] + }, + { + "cell_type": "code", + "execution_count": 87, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "1031\n" + ] + } + ], + "source": [ + "## Get the index of the structure with the minimum energy\n", + "min_energy_index = np.argmin(rlxd_delta_en_per_atom)\n", + "print(min_energy_index)\n" + ] + }, + { + "cell_type": "code", + "execution_count": 113, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "26\n", + "[0, 1, 2, 3, 4, 60, 61, 62, 63, 64, 120, 121, 122, 123, 124, 180, 181, 182, 183, 184, 240, 241, 242, 243, 244, 300, 301, 302, 303, 304, 360, 361, 362, 363, 364, 420, 421, 422, 423, 424, 480, 481, 482, 483, 484, 540, 541, 542, 543, 544, 600, 601, 602, 603, 604, 660, 661, 662, 663, 664, 720, 721, 722, 723, 724, 780, 781, 782, 783, 784, 840, 841, 842, 843, 844, 900, 901, 902, 903, 904, 960, 961, 962, 963, 964, 1020, 1021, 1022, 1023, 1024, 1080, 1081, 1082, 1083, 1084, 1140, 1141, 1142, 1143, 1144]\n", + "[5, 6, 7, 8, 9, 65, 66, 67, 68, 69, 125, 126, 128, 129, 185, 187, 188, 189, 245, 246, 247, 248, 305, 306, 307, 365, 366, 367, 368, 369, 425, 426, 427, 429, 485, 488, 489, 545, 546, 548, 549, 605, 606, 608, 665, 666, 667, 668, 669, 725, 726, 728, 729, 785, 786, 787, 788, 845, 846, 847, 848, 849, 905, 906, 907, 908, 909, 965, 966, 968, 969, 1025, 1026, 1027, 1028, 1085, 1087, 1088, 1089, 1145, 1148, 1149]\n", + "[10, 11, 12, 13, 14, 70, 71, 72, 73, 74, 130, 132, 133, 134, 190, 191, 192, 193, 194, 251, 252, 254, 310, 312, 314, 370, 371, 372, 374, 431, 432, 433, 434, 490, 491, 492, 493, 494, 550, 551, 552, 553, 554, 610, 611, 612, 613, 614, 671, 672, 673, 674, 730, 731, 732, 733, 734, 790, 792, 793, 794, 850, 851, 852, 853, 854, 910, 911, 912, 913, 914, 970, 972, 973, 974, 1031, 1032, 1033, 1034, 1090, 1091, 1093, 1150, 1151, 1152, 1153]\n", + "[15, 16, 17, 18, 19, 75, 76, 77, 78, 135, 136, 137, 139, 195, 196, 197, 198, 255, 256, 257, 259, 315, 317, 318, 319, 376, 377, 378, 437, 438, 439, 495, 496, 497, 498, 499, 555, 557, 558, 615, 617, 618, 619, 675, 676, 677, 678, 679, 735, 736, 737, 738, 739, 795, 797, 798, 799, 855, 856, 857, 858, 859, 915, 916, 917, 918, 919, 975, 976, 977, 978, 1035, 1036, 1037, 1038, 1039, 1095, 1096, 1097, 1098, 1099, 1155, 1156, 1157, 1158, 1159]\n", + "[20, 21, 22, 23, 24, 80, 81, 82, 83, 84, 140, 141, 142, 143, 144, 200, 201, 202, 203, 204, 260, 261, 262, 263, 264, 320, 321, 322, 323, 324, 380, 381, 382, 383, 384, 440, 441, 442, 443, 500, 501, 502, 503, 504, 560, 561, 562, 563, 564, 620, 621, 622, 623, 624, 680, 681, 682, 683, 684, 740, 741, 742, 743, 744, 800, 801, 802, 803, 804, 860, 861, 862, 863, 864, 920, 921, 922, 923, 924, 980, 981, 982, 983, 984, 1040, 1041, 1042, 1043, 1044, 1100, 1101, 1102, 1103, 1104, 1160, 1161, 1162, 1164]\n", + "[25, 26, 27, 28, 29, 85, 86, 87, 88, 89, 146, 147, 148, 149, 205, 206, 207, 265, 266, 267, 268, 269, 326, 327, 328, 329, 385, 387, 445, 446, 448, 449, 505, 506, 507, 509, 565, 567, 568, 626, 627, 628, 629, 685, 686, 687, 688, 745, 746, 747, 749, 805, 806, 808, 865, 866, 867, 869, 925, 926, 927, 986, 987, 989, 1047, 1049, 1105, 1107, 1108, 1109, 1165, 1166, 1167, 1168, 1169]\n", + "[30, 31, 32, 33, 34, 90, 91, 92, 93, 94, 151, 152, 211, 212, 270, 271, 274, 330, 331, 391, 393, 450, 451, 453, 510, 511, 512, 513, 514, 571, 630, 631, 633, 634, 690, 691, 693, 751, 753, 811, 812, 870, 872, 873, 931, 932, 933, 1054, 1110, 1111, 1172, 1173]\n", + "[35, 36, 37, 38, 39, 95, 96, 156, 157, 158, 216, 218, 219, 275, 276, 277, 279, 335, 336, 396, 455, 456, 457, 515, 516, 518, 576, 577, 579, 635, 636, 638, 639, 695, 697, 698, 699, 758, 759, 816, 817, 819, 875, 876, 879, 936, 937, 939, 1059, 1115, 1116, 1117, 1118, 1119, 1177, 1178, 1179]\n", + "[40, 41, 43, 44, 100, 104, 160, 161, 162, 220, 221, 223, 280, 281, 283, 284, 340, 400, 403, 404, 460, 461, 462, 520, 523, 524, 580, 582, 583, 640, 642, 700, 702, 703, 704, 760, 763, 764, 820, 822, 823, 880, 884, 940, 941, 942, 1000, 1060, 1120, 1121, 1122, 1123, 1124, 1180, 1182]\n", + "[42, 101, 102, 163, 282, 342, 344, 401, 402, 464, 521, 641, 644, 701, 824, 881, 882, 943, 944, 1001, 1004, 1062, 1063, 1181, 1183, 1184]\n", + "[45, 46, 47, 48, 106, 107, 108, 109, 165, 166, 167, 168, 169, 225, 228, 229, 285, 287, 288, 289, 345, 346, 347, 349, 405, 406, 407, 408, 409, 465, 466, 467, 468, 469, 525, 526, 527, 528, 529, 585, 586, 587, 588, 589, 645, 646, 648, 649, 705, 706, 707, 765, 766, 767, 768, 769, 825, 826, 827, 829, 885, 886, 887, 888, 889, 946, 947, 948, 949, 1005, 1006, 1007, 1009, 1065, 1066, 1067, 1068, 1069, 1126, 1127, 1128, 1129, 1185, 1186, 1187, 1188, 1189]\n", + "[49, 105, 226, 227, 286, 348, 647, 708, 709, 828, 945, 1008, 1125]\n", + "[50, 51, 52, 53, 54, 55, 56, 58, 59, 110, 111, 112, 113, 114, 115, 116, 117, 118, 119, 170, 171, 172, 173, 174, 175, 176, 177, 178, 179, 230, 231, 232, 233, 234, 235, 236, 237, 238, 239, 290, 291, 292, 293, 294, 295, 296, 297, 298, 299, 350, 351, 352, 353, 354, 355, 356, 357, 358, 359, 410, 411, 412, 413, 414, 415, 416, 417, 418, 419, 470, 471, 472, 473, 474, 475, 476, 477, 478, 479, 530, 531, 532, 533, 534, 535, 536, 537, 538, 590, 591, 592, 593, 594, 595, 596, 598, 599, 650, 651, 652, 653, 654, 655, 656, 657, 658, 659, 710, 711, 712, 713, 715, 716, 717, 718, 719, 770, 771, 772, 773, 774, 775, 776, 777, 778, 779, 830, 831, 832, 833, 834, 835, 836, 837, 838, 839, 890, 891, 892, 893, 894, 895, 896, 897, 898, 899, 950, 951, 952, 953, 954, 955, 956, 957, 958, 1010, 1012, 1013, 1014, 1015, 1016, 1017, 1018, 1019, 1070, 1071, 1072, 1073, 1074, 1075, 1076, 1077, 1078, 1079, 1130, 1131, 1132, 1133, 1134, 1135, 1136, 1137, 1138, 1139, 1190, 1191, 1192, 1193, 1194, 1195, 1196, 1197, 1198, 1199]\n", + "[57, 597, 959]\n", + "[79, 138, 199, 258, 316, 375, 379, 435, 436, 556, 559, 616, 796, 979]\n", + "[97, 98, 99, 155, 159, 215, 217, 278, 337, 338, 339, 395, 397, 398, 399, 458, 459, 517, 519, 575, 578, 637, 696, 755, 756, 757, 815, 818, 877, 878, 935, 938, 995, 996, 997, 998, 999, 1055, 1056, 1057, 1058, 1175, 1176]\n", + "[103, 164, 222, 224, 341, 343, 463, 522, 581, 584, 643, 761, 762, 821, 883, 1002, 1003, 1061, 1064]\n", + "[127, 186, 249, 308, 309, 428, 486, 487, 547, 607, 609, 727, 789, 1146, 1147]\n", + "[131, 250, 253, 311, 313, 373, 430, 670, 791, 971, 1030, 1092, 1094, 1154]\n", + "[145, 208, 209, 325, 386, 388, 389, 447, 566, 569, 625, 689, 714, 748, 807, 809, 868, 928, 929, 985, 1045, 1048, 1106]\n", + "[150, 153, 154, 210, 213, 214, 272, 273, 332, 333, 334, 390, 392, 394, 452, 454, 570, 572, 573, 574, 632, 692, 694, 750, 752, 754, 810, 813, 814, 871, 874, 930, 934, 990, 991, 992, 993, 994, 1050, 1051, 1052, 1053, 1112, 1113, 1114, 1170, 1171, 1174]\n", + "[444, 1163]\n", + "[508, 988, 1046]\n", + "[539]\n", + "[967, 1029, 1086]\n", + "[1011]\n" + ] + } + ], + "source": [ + "tol_x = 3 # Adjust as needed\n", + "tol_y = 0.2\n", + "clusters = [] # will store the current \"center\" of each cluster (basin)\n", + "cluster_indices = [] # list of lists: each sublist stores indices belonging to that cluster\n", + "\n", + "for i, pt in enumerate(rlxd_X_reduced):\n", + " assigned = False\n", + " for j, center in enumerate(clusters):\n", + " if all( abs(pt - center) < [tol_x, tol_y] ):\n", + " # Add index to this cluster and update the cluster center (mean of points)\n", + " cluster_indices[j].append(i)\n", + " clusters[j] = np.mean(rlxd_X_reduced[cluster_indices[j]], axis=0)\n", + " assigned = True\n", + " break\n", + " # if np.linalg.norm(pt - center) < tol:\n", + " # # Add index to this cluster and update the cluster center (mean of points)\n", + " # cluster_indices[j].append(i)\n", + " # clusters[j] = np.mean(rlxd_X_reduced[cluster_indices[j]], axis=0)\n", + " # assigned = True\n", + " # break\n", + " if not assigned:\n", + " # Start a new cluster\n", + " clusters.append(pt.copy())\n", + " cluster_indices.append([i])\n", + "\n", + "print(len(cluster_indices))\n", + "for i in range(len(cluster_indices)):\n", + " print(cluster_indices[i])\n" + ] + }, + { + "cell_type": "code", + "execution_count": 114, + "metadata": {}, + "outputs": [ + { + "data": { + "image/png": "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", + "text/plain": [ + "
" + ] + }, + "metadata": {}, + "output_type": "display_data" + } + ], + "source": [ + "from matplotlib import cm\n", + "\n", + "n_clusters = len(clusters)\n", + "colors = cm.tab20(np.linspace(0, 1, n_clusters))\n", + "for idx, indices in enumerate(cluster_indices):\n", + " plt.scatter(unrlxd_X_reduced[indices, 0],unrlxd_X_reduced[indices, 1], color=colors[idx])" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "[1.0, 0.6, 0.6, 0.4]\n", + "[1.0, 0.4, 0.4, 0.6]\n", + "[1.0, 0.30000000000000004, 0.30000000000000004, 0.7]\n", + "[1.0, 0.0, 0.0, 1.0]\n", + "[1.0, 0.6, 0.6, 0.4]\n", + "[1.0, 0.4, 0.4, 0.6]\n", + "[1.0, 0.30000000000000004, 0.30000000000000004, 0.7]\n", + "[1.0, 0.0, 0.0, 1.0]\n" + ] + }, + { + "data": { + "image/png": "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", + "text/plain": [ + "
" + ] + }, + "metadata": {}, + "output_type": "display_data" + } + ], + "source": [ + "## Plot the PCA\n", + "fig, axes = plt.subplots(nrows=1, ncols=2, figsize=(8, 6))\n", + "\n", + "plt.subplots_adjust(wspace=0.05, hspace=0)\n", + "\n", + "## Get the maximum energy for the colourbar\n", + "#max_en = min(3.0, max(np.max(unrlxd_delta_en_per_atom), np.max(rlxd_delta_en_per_atom)))\n", + "\n", + "## Plot the PCA\n", + "colorlist = [\n", + " (0.4, 0.4, 0.8, 1.0),\n", + " (0.4, 0.8, 0.4, 1.0),\n", + " (1.0, 0.0, 0.0, 1.0),\n", + " (1.0, 0.6, 0.6, 1.0),\n", + " ]\n", + "i = -1\n", + "for idx, indices in reversed(list(enumerate(cluster_indices))):\n", + " # if idx in [ 0, 2, 4, 6]:\n", + " # if idx in [ 0, 1, 4, 6]:\n", + " if idx in [ 0, 2, 7, 12]: # [tol_x = 3, tol_y = 0.2]\n", + " i += 1\n", + " #plt.scatter(unrlxd_X_reduced[indices, 0],unrlxd_X_reduced[indices, 1], color=colors[idx])\n", + " axes[0].scatter(unrlxd_X_reduced[indices, 0], unrlxd_X_reduced[indices, 1], color=colorlist[i])\n", + " axes[1].scatter(rlxd_X_reduced[indices, 0], rlxd_X_reduced[indices, 1], color=colorlist[i])\n", + "\n", + "#axes[0].scatter(unrlxd_X_reduced[:, 0], unrlxd_X_reduced[:, 1], c=unrlxd_delta_en_per_atom, cmap=\"viridis\", vmin = 0, vmax = max_en)\n", + "#axes[1].scatter(rlxd_X_reduced[:, 0], rlxd_X_reduced[:, 1], c=rlxd_delta_en_per_atom, cmap=\"viridis\", vmin = 0, vmax = max_en)\n", + "\n", + "\n", + "# Sort pairs of opacity and X_reduced by opacity value (highest to lowest)\n", + "sorted_pairs = sorted(zip(opacity_list, known_X_reduced, known_phase_labels), key=lambda x: x[0], reverse=False)\n", + "## Add the minimum energy structures to the plot\n", + "for ax in axes:\n", + " for i, X in enumerate(sorted_pairs):\n", + " print([1.0, 1.0-X[0], 1.0-X[0], X[0]])\n", + " ax.scatter(X[1][0], X[1][1], s=200, edgecolor=[1.0, 1.0-X[0], 1.0-X[0], X[0]], facecolor='none', linewidth=2, label=X[2])\n", + " if ax == axes[1]:\n", + " handles, labels = ax.get_legend_handles_labels()\n", + " ax.legend(handles[::-1], labels[::-1], facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, bbox_to_anchor=(1.041, 1.0), fontsize=20, handletextpad=0.2, borderpad=0.3, handlelength=1)\n", + " \n", + "\n", + "\n", + "## Add labels\n", + "fig.text(0.5, 0.0, 'Principal component 1', ha='center', fontsize=20)\n", + "axes[0].set_ylabel('Principal component 2', fontsize=20)\n", + "axes[0].set_title('Unrelaxed', fontsize=20)\n", + "axes[1].set_title('Relaxed', fontsize=20)\n", + "if rlxd_string == \"rlxd\":\n", + " xlims = [-30, 65]\n", + " ylims = [-5, 20]\n", + "else:\n", + " xlims = [-42, 55]\n", + " ylims = [-12, 30]\n", + "\n", + "for ax in axes:\n", + " ax.tick_params(axis='both', direction='in', length=6, labelsize=20)\n", + " # ax.yaxis.set_major_locator(MultipleLocator(3))\n", + " ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.xaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.tick_params(axis='both', which='minor', length=3, direction='in')\n", + " ax.set_xlim(xlims)\n", + " ax.set_ylim(ylims)\n", + "\n", + "## Unify tick labels\n", + "xticks = axes[0].get_xticks()\n", + "xticks = xticks[(xticks >= xlims[0]) & (xticks <= xlims[1])]\n", + "\n", + "axes[1].set_xticks(xticks)\n", + "axes[1].set_yticklabels([])\n", + "axes[0].tick_params(axis='x', labelbottom=True, top=True)\n", + "axes[1].tick_params(axis='x', labelbottom=True, top=True)\n", + "axes[0].tick_params(axis='y', labelbottom=True, right=True)\n", + "axes[1].tick_params(axis='y', labelbottom=True, right=True)\n", + "\n", + "## Make axes[0] and axes[1] the same width\n", + "axes[0].set_box_aspect(1.7)\n", + "axes[1].set_box_aspect(1.7)\n", + "\n", + "## Add colorbar next to the axes\n", + "#cbar = fig.colorbar(axes[1].collections[0], ax=axes, orientation='vertical', fraction=0.085, pad=0.02)\n", + "#cbar.set_label('Formation energy (eV/atom)', fontsize=15)\n", + "\n", + "## Save the figure\n", + "plt.savefig('Al_RAFFLE_pca_'+rlxd_string+'_fit_seed'+str(seed)+'_boa'+method+'.pdf', bbox_inches='tight', pad_inches=0, facecolor=fig.get_facecolor(), edgecolor='none')\n" + ] + }, + { + "cell_type": "code", + "execution_count": 58, + "metadata": {}, + "outputs": [], + "source": [ + "## Identify the line of structures in the lower right corner\n", + "for i in range(len(rlxd_X_reduced)):\n", + " if rlxd_X_reduced[i, 0] > 40 and rlxd_X_reduced[i, 0] < 45 and rlxd_X_reduced[i, 1] > -5 and rlxd_X_reduced[i, 1] < 0:\n", + " print(i)" + ] + }, + { + "cell_type": "code", + "execution_count": 60, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "[-5.29144493 2.06021608]\n" + ] + } + ], + "source": [ + "view(rlxd_structures[138])\n", + "print(rlxd_X_reduced[138])" + ] + }, + { + "cell_type": "code", + "execution_count": 68, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "[46.21698951 -0.52926592]\n" + ] + } + ], + "source": [ + "view(rlxd_structures[30])\n", + "print(rlxd_X_reduced[30])" + ] + }, + { + "cell_type": "code", + "execution_count": 67, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "[48.50032929 2.03884429]\n" + ] + } + ], + "source": [ + "view(unrlxd_structures[1174])\n", + "print(unrlxd_X_reduced[1174])" + ] + } + ], + "metadata": { + "kernelspec": { + "display_name": "Python 3", + "language": "python", + "name": "python3" + }, + "language_info": { + "codemirror_mode": { + "name": "ipython", + "version": 3 + }, + "file_extension": ".py", + "mimetype": "text/x-python", + "name": "python", + "nbconvert_exporter": "python", + "pygments_lexer": "ipython3", + "version": "3.12.2" + } + }, + "nbformat": 4, + "nbformat_minor": 2 +} diff --git a/example/python_pkg/Al_learn/DRAFFLE/pca_placement_order_ratios.ipynb b/example/python_pkg/Al_learn/DRAFFLE/pca_placement_order_ratios.ipynb new file mode 100644 index 00000000..ff58f01d --- /dev/null +++ b/example/python_pkg/Al_learn/DRAFFLE/pca_placement_order_ratios.ipynb @@ -0,0 +1,434 @@ +{ + "cells": [ + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "import matplotlib.pyplot as plt\n", + "%matplotlib inline\n", + "\n", + "# matplotlib.use(\"Agg\")\n", + "\n", + "from ase.visualize import view\n", + "\n", + "from ase.io import read\n", + "from agox.databases import Database\n", + "from agox.environments import Environment\n", + "from agox.utils.graph_sorting import Analysis\n", + "\n", + "import glob\n", + "import numpy as np\n", + "from sklearn.decomposition import PCA\n", + "from matplotlib.ticker import (MultipleLocator, AutoMinorLocator)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set up the plotting environment\n", + "# matplotlib.rcParams.update(matplotlib.rcParamsDefault)\n", + "plt.rc('text', usetex=True)\n", + "plt.rc('font', family='cmr10', size=12)\n", + "plt.rcParams[\"axes.formatter.use_mathtext\"] = True" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set the plotting parameters\n", + "seed = 0\n", + "identifier = \"\"\n", + "prefix = \"DRatios/DALL_TMP/\"\n", + "method = \"v1_r0_w0_g0_m0\"\n", + "no_colourbar = True" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set the descriptors\n", + "from agox.models.descriptors import SOAP\n", + "local_descriptor = local_descriptor = SOAP.from_species([\"Al\"], r_cut=5.0)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set the calculators\n", + "from chgnet.model import CHGNetCalculator\n", + "from ase.calculators.singlepoint import SinglePointCalculator\n", + "calc = CHGNetCalculator()" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Load known structures\n", + "poscar_files = glob.glob(\"../known_phases/*.vasp\")\n", + "known_phases = []\n", + "opacity_list = []\n", + "known_phase_labels = []\n", + "for poscar_file in poscar_files:\n", + " phase = read(poscar_file)\n", + " opacity = None\n", + " if \"mp-134.vasp\" in poscar_file:\n", + " print(\"FCC\")\n", + " cell = phase.get_cell()\n", + " cell = [ vec * 4.02 / np.linalg.norm(vec) for vec in cell]\n", + " phase.set_cell(cell, scale_atoms=True)\n", + " opacity = 1.0\n", + " label = \"FCC (mp-134)\"\n", + " elif \"mp-2647008.vasp\" in poscar_file:\n", + " print(\"HCP\")\n", + " cell = phase.get_cell()\n", + " cell = [ vec * 3.56 / np.linalg.norm(vec) for vec in cell]\n", + " phase.set_cell(cell, scale_atoms=True)\n", + " opacity = 0.6\n", + " label = \"HCP (mp-2647008)\"\n", + " elif \"mp-998860.vasp\" in poscar_file:\n", + " print(\"BCC\")\n", + " cell = phase.get_cell()\n", + " cell = [ vec * 3.10 / np.linalg.norm(vec) for vec in cell]\n", + " phase.set_cell(cell, scale_atoms=True)\n", + " opacity = 0.4\n", + " label = \"BCC (mp-998860)\"\n", + " elif \"mp-1183144.vasp\" in poscar_file:\n", + " print(\"$\\\\alpha$\")\n", + " cell = phase.get_cell()\n", + " # cell[0] = [ vec * 4.94 / np.linalg.norm(vec) for vec in cell]\n", + " # cell[1] = [ vec * 4.94 / np.linalg.norm(vec) for vec in cell]\n", + " cell[2] = cell[2] * 9.88 / np.linalg.norm(cell[2])\n", + " phase.set_cell(cell, scale_atoms=True)\n", + " opacity = 0.7\n", + " label = \"$\\\\alpha$ (mp-1183144)\"\n", + " else:\n", + " print(\"Skipping \", poscar_file)\n", + " continue\n", + " opacity_list.append(opacity)\n", + " known_phase_labels.append(label)\n", + " phase.calc = calc\n", + " known_phases.append(phase)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Load the unrelaxed structures\n", + "unrlxd_structures = read(prefix+\"DOutput_\"+method+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "for structure in unrlxd_structures:\n", + " structure.calc = calc\n", + " " + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Load the relaxed structures\n", + "rlxd_structures = read(prefix+\"DOutput_\"+method+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "for structure in rlxd_structures:\n", + " structure.calc = calc" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Read energies from energies_unrlxd_seed0.txt and add to the respective structures using a SinglePointCalculator\n", + "## The file has the form \"index energy\"\n", + "## This is done because there seem to be issues with storing the energy in the ASE trajectory file for some setups\n", + "filename = prefix+\"DOutput_\"+method+\"/energies_unrlxd_seed\"+str(seed)+\".txt\"\n", + "with open(filename) as f:\n", + " for line in f:\n", + " index, energy = line.split()\n", + " index = int(index)\n", + " energy = float(energy)\n", + " unrlxd_structures[index].calc = SinglePointCalculator(unrlxd_structures[index], energy=energy * len(unrlxd_structures[index]))\n", + "\n", + "\n", + "filename = prefix+\"DOutput_\"+method+\"/energies_rlxd_seed\"+str(seed)+\".txt\"\n", + "with open(filename) as f:\n", + " for line in f:\n", + " index, energy = line.split()\n", + " index = int(index)\n", + " energy = float(energy)\n", + " rlxd_structures[index].calc = SinglePointCalculator(rlxd_structures[index], energy=energy * len(rlxd_structures[index]))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the minimum energy\n", + "min_energy = np.min([structure.get_potential_energy()/len(structure) for structure in rlxd_structures])" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Calculate energies per atom for each unrelaxed structure\n", + "energies_per_atom = [structure.get_potential_energy() / len(structure) for structure in unrlxd_structures]\n", + "unrlxd_delta_en_per_atom = np.array(energies_per_atom) - min_energy\n", + "print(\"Unrelaxed min energy: \", np.min(energies_per_atom))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Calculate energies per atom for each relaxed structure\n", + "energies_per_atom = [structure.get_potential_energy() / len(structure) for structure in rlxd_structures]\n", + "rlxd_delta_en_per_atom = np.array(energies_per_atom) - min_energy\n", + "print(\"Relaxed min energy: \", np.min(energies_per_atom))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set up the PCA\n", + "pca = PCA(n_components=2)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the 'super atom' descriptors for the unrelaxed structures\n", + "unrlxd_super_atoms = []\n", + "for structure in unrlxd_structures:\n", + " unrlxd_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the 'super atom' descriptors for the relaxed structures\n", + "rlxd_super_atoms = []\n", + "for structure in rlxd_structures:\n", + " rlxd_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the 'super atom' descriptors for the known structures\n", + "known_super_atoms = []\n", + "for structure in known_phases:\n", + " known_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Fit the PCA model to the unrelaxed or relaxed structures\n", + "rlxd_string = \"rlxd\"" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Save pca model\n", + "import pickle\n", + "if False:\n", + " pca.fit(np.squeeze([arr for arr in rlxd_super_atoms]))\n", + " with open(\"pca_model_all_rlxd_r_\"+str(seed)+\".pkl\", \"wb\") as f:\n", + " pickle.dump(pca, f)\n", + "\n", + "## Load pca model\n", + "with open(\"pca_model_all_\"+rlxd_string+\"_0.pkl\", \"rb\") as f:\n", + " pca = pickle.load(f)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Transform the unrelaxed and relaxed structures to the reduced space\n", + "unrlxd_X_reduced = pca.transform(np.squeeze([arr for arr in unrlxd_super_atoms]))\n", + "rlxd_X_reduced = pca.transform(np.squeeze([arr for arr in rlxd_super_atoms]))\n", + "known_X_reduced = pca.transform(np.squeeze([arr for arr in known_super_atoms]))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the index of the structure with the minimum energy\n", + "min_energy_index = np.argmin(rlxd_delta_en_per_atom)\n", + "print(min_energy_index)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Plot the PCA\n", + "fig, axes = plt.subplots(nrows=1, ncols=2, figsize=(8, 6))\n", + "\n", + "plt.subplots_adjust(wspace=0.05, hspace=0)\n", + "\n", + "## Get the maximum energy for the colourbar\n", + "vmax = len(rlxd_structures)/5\n", + "\n", + "## Plot the PCA\n", + "axes[0].scatter(unrlxd_X_reduced[:, 0], unrlxd_X_reduced[:, 1], c=[i/5 for i in range(len(rlxd_structures))], cmap=\"cividis\", vmax=vmax)\n", + "axes[1].scatter(rlxd_X_reduced[:, 0], rlxd_X_reduced[:, 1], c=[i/5 for i in range(len(rlxd_structures))], cmap=\"cividis\", vmax=vmax)\n", + "\n", + "# Sort pairs of opacity and X_reduced by opacity value (highest to lowest)\n", + "sorted_pairs = sorted(zip(opacity_list, known_X_reduced, known_phase_labels), key=lambda x: x[0], reverse=False)\n", + "## Add the minimum energy structures to the plot\n", + "for ax in axes:\n", + " for i, X in enumerate(sorted_pairs):\n", + " ax.scatter(X[1][0], X[1][1], s=200, edgecolor=[1.0, 1.0-X[0], 1.0-X[0], X[0]], facecolor='none', linewidth=2, label=X[2])\n", + " if ax == axes[1]:\n", + " handles, labels = ax.get_legend_handles_labels()\n", + " ax.legend(handles[::-1], labels[::-1], facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, bbox_to_anchor=(1.041, 1.0), fontsize=20, handletextpad=0.2, borderpad=0.3, handlelength=1)\n", + " \n", + "\n", + "## Add labels\n", + "fig.text(0.5, 0.0, 'Principal component 1', ha='center', fontsize=20)\n", + "axes[0].set_ylabel('Principal component 2', fontsize=20)\n", + "axes[0].set_title('Unrelaxed', fontsize=20)\n", + "axes[1].set_title('Relaxed', fontsize=20)\n", + "if rlxd_string == \"rlxd\":\n", + " xlims = [-30, 70]\n", + " ylims = [-5, 20]\n", + "else:\n", + " xlims = [-42, 55]\n", + " ylims = [-12, 30]\n", + "\n", + "for ax in axes:\n", + " ax.tick_params(axis='both', direction='in', length=6, labelsize=20)\n", + " # ax.yaxis.set_major_locator(MultipleLocator(3))\n", + " ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.xaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.tick_params(axis='both', which='minor', length=3, direction='in')\n", + " ax.set_xlim(xlims)\n", + " ax.set_ylim(ylims)\n", + "\n", + "## Unify tick labels\n", + "xticks = axes[0].get_xticks()\n", + "xticks = xticks[(xticks >= xlims[0]) & (xticks <= xlims[1])]\n", + "\n", + "axes[1].set_xticks(xticks)\n", + "axes[1].set_yticklabels([])\n", + "axes[0].tick_params(axis='x', labelbottom=True, top=True)\n", + "axes[1].tick_params(axis='x', labelbottom=True, top=True)\n", + "axes[0].tick_params(axis='y', labelbottom=True, right=True)\n", + "axes[1].tick_params(axis='y', labelbottom=True, right=True)\n", + "\n", + "## Make axes[0] and axes[1] the same width\n", + "axes[0].set_box_aspect(1.7)\n", + "axes[1].set_box_aspect(1.7)\n", + "\n", + "## Add colorbar next to the axes\n", + "if not no_colourbar:\n", + " cbar = fig.colorbar(axes[1].collections[0], ax=axes, orientation='vertical', fraction=0.085, pad=0.02)\n", + " cbar.ax.tick_params(labelsize=20)\n", + " # cbar.ax.yaxis.set_major_locator(MultipleLocator(1))\n", + " # cbar.ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + " cbar.set_label('Generation order', fontsize=20)\n", + "\n", + "## Save the figure\n", + "if no_colourbar:\n", + " plt.savefig('Al_RAFFLE_pca_'+rlxd_string+'_fit_seed'+str(seed)+'_order_'+method+'_nocbar.pdf', bbox_inches='tight', pad_inches=0, facecolor=fig.get_facecolor(), edgecolor='none')\n", + "else:\n", + " plt.savefig('Al_RAFFLE_pca_'+rlxd_string+'_fit_seed'+str(seed)+'_order_'+method+'.pdf', bbox_inches='tight', pad_inches=0, facecolor=fig.get_facecolor(), edgecolor='none')\n" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Identify the line of structures in the lower right corner\n", + "for i in range(len(rlxd_X_reduced)):\n", + " if rlxd_X_reduced[i, 0] > 40 and rlxd_X_reduced[i, 0] < 45 and rlxd_X_reduced[i, 1] > -5 and rlxd_X_reduced[i, 1] < 0:\n", + " print(i)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [] + } + ], + "metadata": { + "kernelspec": { + "display_name": "raffle_env", + "language": "python", + "name": "python3" + }, + "language_info": { + "codemirror_mode": { + "name": "ipython", + "version": 3 + }, + "file_extension": ".py", + "mimetype": "text/x-python", + "name": "python", + "nbconvert_exporter": "python", + "pygments_lexer": "ipython3", + "version": "3.12.8" + } + }, + "nbformat": 4, + "nbformat_minor": 2 +} diff --git a/example/python_pkg/Al_learn/DRSS/DOutput/rlxd_structures_seed0.traj b/example/python_pkg/Al_learn/DRSS/DOutput/rlxd_structures_seed0.traj new file mode 100644 index 00000000..9d0fd6c0 Binary files /dev/null and b/example/python_pkg/Al_learn/DRSS/DOutput/rlxd_structures_seed0.traj differ diff --git a/example/python_pkg/Al_learn/DRSS/DOutput/unrlxd_structures_seed0.traj b/example/python_pkg/Al_learn/DRSS/DOutput/unrlxd_structures_seed0.traj new file mode 100644 index 00000000..add33942 Binary files /dev/null and b/example/python_pkg/Al_learn/DRSS/DOutput/unrlxd_structures_seed0.traj differ diff --git a/example/python_pkg/Al_learn/DRSS/pca.ipynb b/example/python_pkg/Al_learn/DRSS/pca.ipynb new file mode 100644 index 00000000..2cfb0355 --- /dev/null +++ b/example/python_pkg/Al_learn/DRSS/pca.ipynb @@ -0,0 +1,417 @@ +{ + "cells": [ + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "import matplotlib.pyplot as plt\n", + "%matplotlib inline\n", + "\n", + "# matplotlib.use(\"Agg\")\n", + "\n", + "from ase.visualize import view\n", + "\n", + "from ase.io import read\n", + "from agox.databases import Database\n", + "from agox.environments import Environment\n", + "from agox.utils.graph_sorting import Analysis\n", + "\n", + "import glob\n", + "import numpy as np\n", + "from sklearn.decomposition import PCA\n", + "from matplotlib.ticker import (MultipleLocator, AutoMinorLocator)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set up the plotting environment\n", + "# matplotlib.rcParams.update(matplotlib.rcParamsDefault)\n", + "plt.rc('text', usetex=True)\n", + "plt.rc('font', family='cmr10', size=12)\n", + "plt.rcParams[\"axes.formatter.use_mathtext\"] = True" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set the plotting parameters\n", + "seed = 0\n", + "identifier = \"\"" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set the descriptors\n", + "from agox.models.descriptors import SOAP\n", + "local_descriptor = local_descriptor = SOAP.from_species([\"Al\"], r_cut=5.0)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set the calculators\n", + "from chgnet.model import CHGNetCalculator\n", + "from ase.calculators.singlepoint import SinglePointCalculator\n", + "calc = CHGNetCalculator()" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Load known structures\n", + "poscar_files = glob.glob(\"../known_phases/*.vasp\")\n", + "known_phases = []\n", + "opacity_list = []\n", + "known_phase_labels = []\n", + "for poscar_file in poscar_files:\n", + " phase = read(poscar_file)\n", + " opacity = None\n", + " if \"mp-134.vasp\" in poscar_file:\n", + " print(\"FCC\")\n", + " cell = phase.get_cell()\n", + " cell = [ vec * 4.02 / np.linalg.norm(vec) for vec in cell]\n", + " phase.set_cell(cell, scale_atoms=True)\n", + " opacity = 1.0\n", + " label = \"FCC (mp-134)\"\n", + " elif \"mp-2647008.vasp\" in poscar_file:\n", + " print(\"HCP\")\n", + " cell = phase.get_cell()\n", + " cell = [ vec * 3.56 / np.linalg.norm(vec) for vec in cell]\n", + " phase.set_cell(cell, scale_atoms=True)\n", + " opacity = 0.6\n", + " label = \"HCP (mp-2647008)\"\n", + " elif \"mp-998860.vasp\" in poscar_file:\n", + " print(\"BCC\")\n", + " cell = phase.get_cell()\n", + " cell = [ vec * 3.10 / np.linalg.norm(vec) for vec in cell]\n", + " phase.set_cell(cell, scale_atoms=True)\n", + " opacity = 0.4\n", + " label = \"BCC (mp-998860)\"\n", + " elif \"mp-1183144.vasp\" in poscar_file:\n", + " print(\"$\\\\alpha$\")\n", + " cell = phase.get_cell()\n", + " # cell[0] = [ vec * 4.94 / np.linalg.norm(vec) for vec in cell]\n", + " # cell[1] = [ vec * 4.94 / np.linalg.norm(vec) for vec in cell]\n", + " cell[2] = cell[2] * 9.88 / np.linalg.norm(cell[2])\n", + " phase.set_cell(cell, scale_atoms=True)\n", + " opacity = 0.7\n", + " label = \"$\\\\alpha$ (mp-1183144)\"\n", + " else:\n", + " print(\"Skipping \", poscar_file)\n", + " continue\n", + " opacity_list.append(opacity)\n", + " known_phase_labels.append(label)\n", + " phase.calc = calc\n", + " known_phases.append(phase)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Load the unrelaxed structures\n", + "unrlxd_structures = read(\"DOutput\"+identifier+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "for structure in unrlxd_structures:\n", + " structure.calc = calc" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Load the relaxed structures\n", + "rlxd_structures = read(\"DOutput\"+identifier+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "for structure in rlxd_structures:\n", + " structure.calc = calc" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "# ## Read energies from energies_unrlxd_seed0.txt and add to the respective structures using a SinglePointCalculator\n", + "# ## The file has the form \"index energy\"\n", + "# ## This is done because there seem to be issues with storing the energy in the ASE trajectory file for some setups\n", + "# filename = \"DOutput\"+identifier+\"/energies_unrlxd_seed\"+str(seed)+\".txt\"\n", + "# with open(filename) as f:\n", + "# for line in f:\n", + "# index, energy = line.split()\n", + "# index = int(index)\n", + "# energy = float(energy)\n", + "# unrlxd_structures[index].calc = SinglePointCalculator(unrlxd_structures[index], energy=energy * len(unrlxd_structures[index]))\n", + "\n", + "\n", + "# filename = \"DOutput\"+identifier+\"/energies_rlxd_seed\"+str(seed)+\".txt\"\n", + "# with open(filename) as f:\n", + "# for line in f:\n", + "# index, energy = line.split()\n", + "# index = int(index)\n", + "# energy = float(energy)\n", + "# rlxd_structures[index].calc = SinglePointCalculator(rlxd_structures[index], energy=energy * len(rlxd_structures[index]))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the minimum energy\n", + "min_energy = np.min([structure.get_potential_energy()/len(structure) for structure in rlxd_structures])" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Calculate energies per atom for each unrelaxed structure\n", + "energies_per_atom = [structure.get_potential_energy() / len(structure) for structure in unrlxd_structures]\n", + "unrlxd_delta_en_per_atom = np.array(energies_per_atom) - min_energy\n", + "print(\"Unrelaxed min energy: \", np.min(energies_per_atom))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Calculate energies per atom for each relaxed structure\n", + "energies_per_atom = [structure.get_potential_energy() / len(structure) for structure in rlxd_structures]\n", + "rlxd_delta_en_per_atom = np.array(energies_per_atom) - min_energy\n", + "print(\"Relaxed min energy: \", np.min(energies_per_atom))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set up the PCA\n", + "pca = PCA(n_components=2)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the 'super atom' descriptors for the unrelaxed structures\n", + "unrlxd_super_atoms = []\n", + "for structure in unrlxd_structures:\n", + " unrlxd_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the 'super atom' descriptors for the relaxed structures\n", + "rlxd_super_atoms = []\n", + "for structure in rlxd_structures:\n", + " rlxd_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the 'super atom' descriptors for the known structures\n", + "known_super_atoms = []\n", + "for structure in known_phases:\n", + " known_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Fit the PCA model to the unrelaxed or relaxed structures\n", + "rlxd_string = \"rlxd\"" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Save pca model\n", + "import pickle\n", + "if False:\n", + " pca.fit(np.squeeze([arr for arr in rlxd_super_atoms]))\n", + " with open(\"pca_model_all_rlxd_\"+str(seed)+\".pkl\", \"wb\") as f:\n", + " pickle.dump(pca, f)\n", + "\n", + "## Load pca model\n", + "with open(\"../DRAFFLE/pca_model_all_\"+rlxd_string+\"_0.pkl\", \"rb\") as f:\n", + " pca = pickle.load(f)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Transform the unrelaxed and relaxed structures to the reduced space\n", + "unrlxd_X_reduced = pca.transform(np.squeeze([arr for arr in unrlxd_super_atoms]))\n", + "rlxd_X_reduced = pca.transform(np.squeeze([arr for arr in rlxd_super_atoms]))\n", + "known_X_reduced = pca.transform(np.squeeze([arr for arr in known_super_atoms]))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the index of the structure with the minimum energy\n", + "min_energy_index = np.argmin(rlxd_delta_en_per_atom)\n", + "print(min_energy_index)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Plot the PCA\n", + "fig, axes = plt.subplots(nrows=1, ncols=2, figsize=(8, 6))\n", + "\n", + "plt.subplots_adjust(wspace=0.05, hspace=0)\n", + "\n", + "## Get the maximum energy for the colourbar\n", + "max_en = min(3.0, max(np.max(unrlxd_delta_en_per_atom), np.max(rlxd_delta_en_per_atom)))\n", + "\n", + "## Plot the PCA\n", + "axes[0].scatter(unrlxd_X_reduced[:, 0], unrlxd_X_reduced[:, 1], c=unrlxd_delta_en_per_atom, cmap=\"viridis\", vmin = 0, vmax = max_en)\n", + "axes[1].scatter(rlxd_X_reduced[:, 0], rlxd_X_reduced[:, 1], c=rlxd_delta_en_per_atom, cmap=\"viridis\", vmin = 0, vmax = max_en)\n", + "\n", + "# Sort pairs of opacity and X_reduced by opacity value (highest to lowest)\n", + "sorted_pairs = sorted(zip(opacity_list, known_X_reduced, known_phase_labels), key=lambda x: x[0], reverse=False)\n", + "## Add the minimum energy structures to the plot\n", + "for ax in axes:\n", + " for i, X in enumerate(sorted_pairs):\n", + " ax.scatter(X[1][0], X[1][1], s=200, edgecolor=[1.0, 1.0-X[0], 1.0-X[0], X[0]], facecolor='none', linewidth=2, label=X[2])\n", + " if ax == axes[1]:\n", + " handles, labels = ax.get_legend_handles_labels()\n", + " ax.legend(handles[::-1], labels[::-1], facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, bbox_to_anchor=(1.041, 1.0), fontsize=20, handletextpad=0.2, borderpad=0.3, handlelength=1)\n", + " \n", + "## Add labels\n", + "fig.text(0.5, 0.0, 'Principal component 1', ha='center', fontsize=20)\n", + "axes[0].set_ylabel('Principal component 2', fontsize=20)\n", + "axes[0].set_title('Unrelaxed', fontsize=20)\n", + "axes[1].set_title('Relaxed', fontsize=20)\n", + "if rlxd_string == \"rlxd\":\n", + " xlims = [-30, 70]\n", + " ylims = [-5, 20]\n", + "else:\n", + " xlims = [-42, 55]\n", + " ylims = [-12, 30]\n", + "\n", + "for ax in axes:\n", + " ax.tick_params(axis='both', direction='in', length=6, labelsize=20)\n", + " # ax.yaxis.set_major_locator(MultipleLocator(3))\n", + " ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.xaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.tick_params(axis='both', which='minor', length=3, direction='in')\n", + " ax.set_xlim(xlims)\n", + " ax.set_ylim(ylims)\n", + "\n", + "## Unify tick labels\n", + "xticks = axes[0].get_xticks()\n", + "xticks = xticks[(xticks >= xlims[0]) & (xticks <= xlims[1])]\n", + "\n", + "axes[1].set_xticks(xticks)\n", + "axes[1].set_yticklabels([])\n", + "axes[0].tick_params(axis='x', labelbottom=True, top=True)\n", + "axes[1].tick_params(axis='x', labelbottom=True, top=True)\n", + "axes[0].tick_params(axis='y', labelbottom=True, right=True)\n", + "axes[1].tick_params(axis='y', labelbottom=True, right=True)\n", + "## Make axes[0] and axes[1] the same width\n", + "axes[0].set_box_aspect(1.7)\n", + "axes[1].set_box_aspect(1.7)\n", + "\n", + "## Add colorbar next to the axes\n", + "cbar = fig.colorbar(axes[1].collections[0], ax=axes, orientation='vertical', fraction=0.085, pad=0.02)\n", + "cbar.ax.tick_params(labelsize=20)\n", + "cbar.ax.yaxis.set_major_locator(MultipleLocator(1))\n", + "cbar.ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + "cbar.set_label('Formation energy (eV/atom)', fontsize=20)\n", + "\n", + "## Save the figure\n", + "plt.savefig('Al_RSS_pca_'+rlxd_string+'_fit_seed'+str(seed)+'.pdf', bbox_inches='tight', pad_inches=0, facecolor=fig.get_facecolor(), edgecolor='none')" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Identify the line of structures in the lower right corner\n", + "for i in range(len(rlxd_X_reduced)):\n", + " if rlxd_X_reduced[i, 0] > 40 and rlxd_X_reduced[i, 0] < 45 and rlxd_X_reduced[i, 1] > -5 and rlxd_X_reduced[i, 1] < 0:\n", + " print(i)" + ] + } + ], + "metadata": { + "kernelspec": { + "display_name": "raffle_env", + "language": "python", + "name": "python3" + }, + "language_info": { + "codemirror_mode": { + "name": "ipython", + "version": 3 + }, + "file_extension": ".py", + "mimetype": "text/x-python", + "name": "python", + "nbconvert_exporter": "python", + "pygments_lexer": "ipython3", + "version": "3.12.8" + } + }, + "nbformat": 4, + "nbformat_minor": 2 +} diff --git a/example/python_pkg/Al_learn/DRSS/rss.py b/example/python_pkg/Al_learn/DRSS/rss.py new file mode 100644 index 00000000..18240ce2 --- /dev/null +++ b/example/python_pkg/Al_learn/DRSS/rss.py @@ -0,0 +1,156 @@ +# https://agox.gitlab.io/agox/command_line_tools/command_line.html + +import matplotlib + +matplotlib.use("Agg") + + +import numpy as np +from ase import Atoms +from ase.io import write + +from agox import AGOX +from agox.databases import Database +from agox.environments import Environment +from agox.evaluators import LocalOptimizationEvaluator +from agox.generators import RandomGenerator +from agox.postprocessors import MinimumDistPostProcess + + +iteration_directory = "iteration" + +############################################################################## +# Calculator +############################################################################## + +# from mace.calculators import mace_mp +from chgnet.model import CHGNetCalculator +from ase.build import bulk +import os + +# calc = mace_mp() +calc = CHGNetCalculator() + +############################################################################## +# System & general settings: +############################################################################## + + +# diamond = bulk("Al", "diamond", a=3.567) # Lattice constant for diamond cubic carbon +# diamond.write("diamond.traj") +# post1 = MinimumDistPostProcess(order=1.5, c1=0.75) +# post2 = MinimumDistPostProcess(order=2.5, c1=0.75) + +# # Make an empty template with a cubic cell of size 6x6x6 with periodic boundary conditions +# # in all directions +# a = 3.567 +# iteration = 0 +# template = Atoms("", cell=np.eye(3) * a, pbc=True) + + +crystal_structures = [ + 'orthorhombic', 'hcp', +] +hosts = [] +for crystal_structure in crystal_structures: + print(f'Crystal structure: {crystal_structure}') + for a in np.linspace(3.1, 5.4, num=6): + b = a + c = a + atom = bulk( + name = 'Al', + crystalstructure = crystal_structure, + a = a, + b = b, + c = c, + ) + hosts.append(Atoms('Al', positions=[(0, 0, 0)], cell=atom.get_cell(), pbc=True, calculator=calc)) +print("number of hosts: ", len(hosts)) + +iteration = 0 +mass = 26.9815385 +density = 1.61 # u/A^3 +unrlxd_structures = [] +rlxd_structures = [] +database_index = -1 +for template in hosts: + database_index += 1 + volume = template.get_volume() + + # calculate the number of atoms in the host to achieve the desired density + num_atoms = round(density * volume / mass) - 1 + if(num_atoms < 1): + continue + print(f"Volume: {volume}") + print(f"Number of atoms: {num_atoms}") + + # Confinement cell matches the template cell in all dimensions and is placed at + # the origin of the template cell. + confinement_cell = template.cell.copy() + confinement_corner = np.array([0, 0, 0]) + + environment = Environment( + template=template, + symbols=f"Al{num_atoms-1}", + confinement_cell=confinement_cell, + confinement_corner=confinement_corner, + box_constraint_pbc=[True, True, True], # Confinement is periodic in all directions. + ) + + # Database + db_directory = iteration_directory+"{}".format(iteration)+"/" + if not os.path.exists(db_directory): + os.makedirs(db_directory) + db_path = db_directory+"db{}.db".format(database_index) # From input argument! + + for seed in range(1): + database = Database(filename=db_path, order=3, initialize=True) + + ############################################################################## + # Search Settings: + ############################################################################## + + random_generator = RandomGenerator(**environment.get_confinement(), environment=environment, order=1) + + # Wont relax fully with steps:5 - more realistic setting would be 100+. + evaluator = LocalOptimizationEvaluator( + calc, + gets={"get_key": "candidates"}, + optimizer_run_kwargs={"fmax": 0.05, "steps": 100}, + store_trajectory=True, + order=2, + constraints=environment.get_constraints(), + ) + + ############################################################################## + # Let get the show running! + ############################################################################## + + agox = AGOX(random_generator, database, evaluator, seed=seed) + + agox.run(N_iterations=50) + + structure_data = database.get_all_structures_data() + # check iteration number has changed + iteration_check = -1 + for idx, structure in enumerate(structure_data): + if structure["iteration"] != iteration_check: + iteration_check = structure["iteration"] + unrlxd_structures.append(database.db_to_atoms(structure)) + if idx != 0: + rlxd_structures.append(database.db_to_atoms(structure_data[idx-1])) + if len(rlxd_structures) != len(unrlxd_structures): + rlxd_structures.append(database.db_to_atoms(structure_data[-1])) + + +for structure in unrlxd_structures: + structure.calc = None +for structure in rlxd_structures: + structure.calc = None +print("Unrelaxed structures", len(unrlxd_structures)) +print("Relaxed structures", len(rlxd_structures)) +write(f"unrlxd_structures_seed{seed}.traj", unrlxd_structures) +write(f"rlxd_structures_seed{seed}.traj", rlxd_structures) + +# database.restore_to_memory() +# structures = database.get_all_candidates() # this is an Atoms object with some more stuff diff --git a/example/python_pkg/Al_learn/learn.py b/example/python_pkg/Al_learn/learn.py index 88d35cfa..cc793de5 100644 --- a/example/python_pkg/Al_learn/learn.py +++ b/example/python_pkg/Al_learn/learn.py @@ -63,9 +63,7 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct # set up the hosts crystal_structures = [ - 'orthorhombic', 'diamond', - 'bct', 'sc', - 'fcc', 'bcc', 'hcp', + 'orthorhombic', 'hcp', ] hosts = [] for crystal_structure in crystal_structures: @@ -146,7 +144,7 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct num_structures = 5, stoichiometry = { 'Al': num_atoms }, seed = seed*1000+iter, - method_probab = {"void": 0.5, "rand": 0.001, "walk": 0.5, "grow": 0.0, "min": 1.0}, + method_ratio = {"void": 0.5, "rand": 0.001, "walk": 0.5, "grow": 0.0, "min": 1.0}, verbose = 0, ) diff --git a/example/python_pkg/Al_learn/pca.ipynb b/example/python_pkg/Al_learn/pca.ipynb deleted file mode 100644 index a2a5e0cf..00000000 --- a/example/python_pkg/Al_learn/pca.ipynb +++ /dev/null @@ -1,484 +0,0 @@ -{ - "cells": [ - { - "cell_type": "code", - "execution_count": 1, - "metadata": {}, - "outputs": [ - { - "name": "stderr", - "output_type": "stream", - "text": [ - "/home/ntt203/.conda/envs/raffle_env/lib/python3.12/site-packages/tqdm/auto.py:21: TqdmWarning: IProgress not found. Please update jupyter and ipywidgets. See https://ipywidgets.readthedocs.io/en/stable/user_install.html\n", - " from .autonotebook import tqdm as notebook_tqdm\n", - "2025-02-14 13:21:52,267\tINFO util.py:154 -- Missing packages: ['ipywidgets']. Run `pip install -U ipywidgets`, then restart the notebook server for rich notebook output.\n" - ] - } - ], - "source": [ - "import matplotlib.pyplot as plt\n", - "%matplotlib inline\n", - "\n", - "# matplotlib.use(\"Agg\")\n", - "\n", - "from ase.visualize import view\n", - "\n", - "from ase.io import read\n", - "from agox.databases import Database\n", - "from agox.environments import Environment\n", - "from agox.utils.graph_sorting import Analysis\n", - "\n", - "import glob\n", - "import numpy as np\n", - "from sklearn.decomposition import PCA" - ] - }, - { - "cell_type": "code", - "execution_count": 2, - "metadata": {}, - "outputs": [], - "source": [ - "## Set up the plotting environment\n", - "# matplotlib.rcParams.update(matplotlib.rcParamsDefault)\n", - "plt.rc('text', usetex=True)\n", - "plt.rc('font', family='cmr10', size=12)\n", - "plt.rcParams[\"axes.formatter.use_mathtext\"] = True" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "## Set the plotting parameters\n", - "seed = 0\n", - "identifier = \"\"" - ] - }, - { - "cell_type": "code", - "execution_count": 4, - "metadata": {}, - "outputs": [], - "source": [ - "## Set the descriptors\n", - "from agox.models.descriptors import SOAP\n", - "local_descriptor = local_descriptor = SOAP.from_species([\"Al\"], r_cut=5.0)" - ] - }, - { - "cell_type": "code", - "execution_count": 5, - "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "CHGNet v0.3.0 initialized with 412,525 parameters\n", - "CHGNet will run on cuda\n" - ] - } - ], - "source": [ - "## Set the calculators\n", - "from chgnet.model import CHGNetCalculator\n", - "from ase.calculators.singlepoint import SinglePointCalculator\n", - "calc = CHGNetCalculator()" - ] - }, - { - "cell_type": "code", - "execution_count": 6, - "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "BCC\n", - "$\\alpha$\n", - "FCC\n", - "HCP\n" - ] - } - ], - "source": [ - "## Load known structures\n", - "poscar_files = glob.glob(\"known_phases/*.vasp\")\n", - "known_phases = []\n", - "opacity_list = []\n", - "known_phase_labels = []\n", - "for poscar_file in poscar_files:\n", - " phase = read(poscar_file)\n", - " opacity = None\n", - " if \"mp-134.vasp\" in poscar_file:\n", - " print(\"FCC\")\n", - " cell = phase.get_cell()\n", - " cell = [ vec * 4.02 / np.linalg.norm(vec) for vec in cell]\n", - " phase.set_cell(cell, scale_atoms=True)\n", - " opacity = 1.0\n", - " label = \"FCC (mp-134)\"\n", - " elif \"mp-2647008.vasp\" in poscar_file:\n", - " print(\"HCP\")\n", - " cell = phase.get_cell()\n", - " cell = [ vec * 3.56 / np.linalg.norm(vec) for vec in cell]\n", - " phase.set_cell(cell, scale_atoms=True)\n", - " opacity = 0.6\n", - " label = \"HCP (mp-2647008)\"\n", - " elif \"mp-998860.vasp\" in poscar_file:\n", - " print(\"BCC\")\n", - " cell = phase.get_cell()\n", - " cell = [ vec * 3.10 / np.linalg.norm(vec) for vec in cell]\n", - " phase.set_cell(cell, scale_atoms=True)\n", - " opacity = 0.4\n", - " label = \"BCC (mp-998860)\"\n", - " elif \"mp-1183144.vasp\" in poscar_file:\n", - " print(\"$\\\\alpha$\")\n", - " cell = phase.get_cell()\n", - " # cell[0] = [ vec * 4.94 / np.linalg.norm(vec) for vec in cell]\n", - " # cell[1] = [ vec * 4.94 / np.linalg.norm(vec) for vec in cell]\n", - " cell[2] = cell[2] * 9.88 / np.linalg.norm(cell[2])\n", - " phase.set_cell(cell, scale_atoms=True)\n", - " opacity = 0.7\n", - " label = \"$\\\\alpha$ (mp-1183144)\"\n", - " else:\n", - " print(\"Skipping \", poscar_file)\n", - " continue\n", - " opacity_list.append(opacity)\n", - " known_phase_labels.append(label)\n", - " phase.calc = calc\n", - " known_phases.append(phase)" - ] - }, - { - "cell_type": "code", - "execution_count": 7, - "metadata": {}, - "outputs": [], - "source": [ - "## Load the unrelaxed structures\n", - "unrlxd_structures = read(\"DTMP\"+identifier+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", - "for structure in unrlxd_structures:\n", - " structure.calc = calc" - ] - }, - { - "cell_type": "code", - "execution_count": 8, - "metadata": {}, - "outputs": [], - "source": [ - "## Load the relaxed structures\n", - "rlxd_structures = read(\"DTMP\"+identifier+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", - "for structure in rlxd_structures:\n", - " structure.calc = calc" - ] - }, - { - "cell_type": "code", - "execution_count": 9, - "metadata": {}, - "outputs": [], - "source": [ - "## Read energies from energies_unrlxd_seed0.txt and add to the respective structures using a SinglePointCalculator\n", - "## The file has the form \"index energy\"\n", - "## This is done because there seem to be issues with storing the energy in the ASE trajectory file for some setups\n", - "filename = \"DTMP\"+identifier+\"/energies_unrlxd_seed\"+str(seed)+\".txt\"\n", - "with open(filename) as f:\n", - " for line in f:\n", - " index, energy = line.split()\n", - " index = int(index)\n", - " energy = float(energy)\n", - " unrlxd_structures[index].calc = SinglePointCalculator(unrlxd_structures[index], energy=energy * len(unrlxd_structures[index]))\n", - "\n", - "\n", - "filename = \"DTMP\"+identifier+\"/energies_rlxd_seed\"+str(seed)+\".txt\"\n", - "with open(filename) as f:\n", - " for line in f:\n", - " index, energy = line.split()\n", - " index = int(index)\n", - " energy = float(energy)\n", - " rlxd_structures[index].calc = SinglePointCalculator(rlxd_structures[index], energy=energy * len(rlxd_structures[index]))" - ] - }, - { - "cell_type": "code", - "execution_count": 10, - "metadata": {}, - "outputs": [], - "source": [ - "## Get the minimum energy\n", - "min_energy = np.min([structure.get_potential_energy()/len(structure) for structure in rlxd_structures])" - ] - }, - { - "cell_type": "code", - "execution_count": 11, - "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "Unrelaxed min energy: -3.661088705062866\n" - ] - } - ], - "source": [ - "## Calculate energies per atom for each unrelaxed structure\n", - "energies_per_atom = [structure.get_potential_energy() / len(structure) for structure in unrlxd_structures]\n", - "unrlxd_delta_en_per_atom = np.array(energies_per_atom) - min_energy\n", - "print(\"Unrelaxed min energy: \", np.min(energies_per_atom))" - ] - }, - { - "cell_type": "code", - "execution_count": 12, - "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "Relaxed min energy: -3.663501501083374\n" - ] - } - ], - "source": [ - "## Calculate energies per atom for each relaxed structure\n", - "energies_per_atom = [structure.get_potential_energy() / len(structure) for structure in rlxd_structures]\n", - "rlxd_delta_en_per_atom = np.array(energies_per_atom) - min_energy\n", - "print(\"Relaxed min energy: \", np.min(energies_per_atom))" - ] - }, - { - "cell_type": "code", - "execution_count": 13, - "metadata": {}, - "outputs": [], - "source": [ - "## Set up the PCA\n", - "pca = PCA(n_components=2)" - ] - }, - { - "cell_type": "code", - "execution_count": 14, - "metadata": {}, - "outputs": [], - "source": [ - "## Get the 'super atom' descriptors for the unrelaxed structures\n", - "unrlxd_super_atoms = []\n", - "for structure in unrlxd_structures:\n", - " unrlxd_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" - ] - }, - { - "cell_type": "code", - "execution_count": 15, - "metadata": {}, - "outputs": [], - "source": [ - "## Get the 'super atom' descriptors for the relaxed structures\n", - "rlxd_super_atoms = []\n", - "for structure in rlxd_structures:\n", - " rlxd_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" - ] - }, - { - "cell_type": "code", - "execution_count": 16, - "metadata": {}, - "outputs": [], - "source": [ - "## Get the 'super atom' descriptors for the known structures\n", - "known_super_atoms = []\n", - "for structure in known_phases:\n", - " known_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" - ] - }, - { - "cell_type": "code", - "execution_count": 17, - "metadata": {}, - "outputs": [], - "source": [ - "## Fit the PCA model to the unrelaxed or relaxed structures\n", - "rlxd_string = \"rlxd\"" - ] - }, - { - "cell_type": "code", - "execution_count": 18, - "metadata": {}, - "outputs": [], - "source": [ - "## Save pca model\n", - "import pickle\n", - "if True:\n", - " pca.fit(np.squeeze([arr for arr in rlxd_super_atoms]))\n", - " with open(\"pca_model_all_rlxd_\"+str(seed)+\".pkl\", \"wb\") as f:\n", - " pickle.dump(pca, f)\n", - "\n", - "## Load pca model\n", - "with open(\"pca_model_all_\"+rlxd_string+\"_0.pkl\", \"rb\") as f:\n", - " pca = pickle.load(f)" - ] - }, - { - "cell_type": "code", - "execution_count": 19, - "metadata": {}, - "outputs": [], - "source": [ - "## Transform the unrelaxed and relaxed structures to the reduced space\n", - "unrlxd_X_reduced = pca.transform(np.squeeze([arr for arr in unrlxd_super_atoms]))\n", - "rlxd_X_reduced = pca.transform(np.squeeze([arr for arr in rlxd_super_atoms]))\n", - "known_X_reduced = pca.transform(np.squeeze([arr for arr in known_super_atoms]))" - ] - }, - { - "cell_type": "code", - "execution_count": 20, - "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "1031\n" - ] - } - ], - "source": [ - "## Get the index of the structure with the minimum energy\n", - "min_energy_index = np.argmin(rlxd_delta_en_per_atom)\n", - "print(min_energy_index)" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [ - { - "data": { - "image/png": "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", - "text/plain": [ - "
" - ] - }, - "metadata": {}, - "output_type": "display_data" - } - ], - "source": [ - "## Plot the PCA\n", - "fig, axes = plt.subplots(nrows=1, ncols=2, figsize=(8, 6))\n", - "\n", - "plt.subplots_adjust(wspace=0.05, hspace=0)\n", - "\n", - "## Get the maximum energy for the colourbar\n", - "max_en = min(3.0, max(np.max(unrlxd_delta_en_per_atom), np.max(rlxd_delta_en_per_atom)))\n", - "\n", - "## Plot the PCA\n", - "axes[0].scatter(unrlxd_X_reduced[:, 0], unrlxd_X_reduced[:, 1], c=unrlxd_delta_en_per_atom, cmap=\"viridis\", vmin = 0, vmax = max_en)\n", - "axes[1].scatter(rlxd_X_reduced[:, 0], rlxd_X_reduced[:, 1], c=rlxd_delta_en_per_atom, cmap=\"viridis\", vmin = 0, vmax = max_en)\n", - "\n", - "# Sort pairs of opacity and X_reduced by opacity value (highest to lowest)\n", - "sorted_pairs = sorted(zip(opacity_list, known_X_reduced, known_phase_labels), key=lambda x: x[0], reverse=False)\n", - "## Add the minimum energy structures to the plot\n", - "for ax in axes:\n", - " for i, X in enumerate(sorted_pairs):\n", - " ax.scatter(X[1][0], X[1][1], s=200, edgecolor=[1.0, 1.0-X[0], 1.0-X[0], X[0]], facecolor='none', linewidth=2, label=X[2])\n", - " if ax == axes[1]:\n", - " ax.legend(fontsize=10)\n", - " handles, labels = ax.get_legend_handles_labels()\n", - " ax.legend(handles[::-1], labels[::-1], facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, loc='upper right')\n", - " \n", - " \n", - "## Add labels\n", - "fig.text(0.5, 0.04, 'Principal Component 1', ha='center', fontsize=15)\n", - "axes[0].set_ylabel('Principal Component 2', fontsize=15)\n", - "axes[0].set_title('Unrelaxed')\n", - "axes[1].set_title('Relaxed')\n", - "if rlxd_string == \"rlxd\":\n", - " xlims = [-30, 70]\n", - " ylims = [-5, 20]\n", - "else:\n", - " xlims = [-42, 55]\n", - " ylims = [-12, 30]\n", - "\n", - "for ax in axes:\n", - " ax.tick_params(axis='both', direction='in')\n", - " ax.set_xlim(xlims)\n", - " ax.set_ylim(ylims)\n", - "\n", - "## Unify tick labels\n", - "xticks = axes[0].get_xticks()\n", - "xticks = xticks[(xticks >= xlims[0]) & (xticks <= xlims[1])]\n", - "\n", - "axes[1].set_xticks(xticks)\n", - "axes[1].set_yticklabels([])\n", - "axes[0].tick_params(axis='x', labelbottom=True, top=True)\n", - "axes[1].tick_params(axis='x', labelbottom=True, top=True)\n", - "axes[0].tick_params(axis='y', labelbottom=True, right=True)\n", - "axes[1].tick_params(axis='y', labelbottom=True, right=True)\n", - "\n", - "## Make axes[0] and axes[1] the same width\n", - "axes[0].set_box_aspect(1.7)\n", - "axes[1].set_box_aspect(1.7)\n", - "\n", - "## Add colorbar next to the axes\n", - "cbar = fig.colorbar(axes[1].collections[0], ax=axes, orientation='vertical', fraction=0.085, pad=0.02)\n", - "cbar.set_label('Formation energy (eV/atom)', fontsize=15)\n", - "\n", - "## Save the figure\n", - "plt.savefig('Al_RAFFLE_pca_'+rlxd_string+'_fit_seed'+str(seed)+'.pdf', bbox_inches='tight', pad_inches=0, facecolor=fig.get_facecolor(), edgecolor='none')" - ] - }, - { - "cell_type": "code", - "execution_count": 22, - "metadata": {}, - "outputs": [], - "source": [ - "## Identify the line of structures in the lower right corner\n", - "for i in range(len(rlxd_X_reduced)):\n", - " if rlxd_X_reduced[i, 0] > 40 and rlxd_X_reduced[i, 0] < 45 and rlxd_X_reduced[i, 1] > -5 and rlxd_X_reduced[i, 1] < 0:\n", - " print(i)" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [] - } - ], - "metadata": { - "kernelspec": { - "display_name": "Python 3", - "language": "python", - "name": "python3" - }, - "language_info": { - "codemirror_mode": { - "name": "ipython", - "version": 3 - }, - "file_extension": ".py", - "mimetype": "text/x-python", - "name": "python", - "nbconvert_exporter": "python", - "pygments_lexer": "ipython3", - "version": "3.12.2" - } - }, - "nbformat": 4, - "nbformat_minor": 2 -} diff --git a/example/python_pkg/BaTiO3/run.py b/example/python_pkg/BaTiO3/run.py index a947d970..56eddf57 100644 --- a/example/python_pkg/BaTiO3/run.py +++ b/example/python_pkg/BaTiO3/run.py @@ -141,7 +141,7 @@ print(f"Iteration {iter}") print("Generating...") # this is the main function to generate structures - generator.generate(num_structures=1, stoichiometry=stoich_dict, seed=0+iter, verbose=1, method_probab={"void":0.001, "walk":0.0, "min":1.0}) + generator.generate(num_structures=1, stoichiometry=stoich_dict, seed=0+iter, verbose=1, method_ratio={"void":0.001, "walk":0.0, "min":1.0}) print("Generated") print("Getting structures") diff --git a/example/python_pkg/C-MgO/run.py b/example/python_pkg/C-MgO/run.py index fa4385c4..75d6cc3e 100644 --- a/example/python_pkg/C-MgO/run.py +++ b/example/python_pkg/C-MgO/run.py @@ -104,7 +104,7 @@ print(f"Iteration {iter}") print("Generating...") # this is the main function to generate structures - generator.generate(num_structures=10, stoichiometry=stoich_dict, seed=0+iter, verbose=0, method_probab={"void":1.0, "walk":1.0, "min":1.0}) + generator.generate(num_structures=10, stoichiometry=stoich_dict, seed=0+iter, verbose=0, method_ratio={"void":1.0, "walk":1.0, "min":1.0}) print("Generated") print("Getting structures") diff --git a/example/python_pkg/C-MgO_learn/learn.py b/example/python_pkg/C-MgO_learn/learn.py index 292f50fd..37aa7cf3 100644 --- a/example/python_pkg/C-MgO_learn/learn.py +++ b/example/python_pkg/C-MgO_learn/learn.py @@ -1,4 +1,5 @@ from chgnet.model import CHGNetCalculator +from ase.calculators.singlepoint import SinglePointCalculator from raffle.generator import raffle_generator from ase import build, Atoms from ase.optimize import FIRE @@ -228,7 +229,7 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct num_structures = 5, stoichiometry = { 'Mg': num_atoms_Mg, 'O': num_atoms_O }, seed = seed*1000+iter, - method_probab = {"void": 1.0, "rand": 0.001, "walk": 1.0, "grow": 0.0, "min": 1.0}, + method_ratio = {"void": 1.0, "rand": 0.001, "walk": 1.0, "grow": 0.0, "min": 1.0}, verbose = 0, ) @@ -250,6 +251,10 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct write(iterdir+f"POSCAR_unrlxd_{i}", generated_structures[num_structures_old + i]) print(f"Structure {i} energy per atom: {generated_structures[num_structures_old + i].get_potential_energy() / len(generated_structures[num_structures_old + i])}") unrlxd_structures.append(generated_structures[num_structures_old + i].copy()) + unrlxd_structures[-1].calc = SinglePointCalculator( + generated_structures[num_structures_old + i], + energy=generated_structures[num_structures_old + i].get_potential_energy(), + forces=generated_structures[num_structures_old + i].get_forces() # Start parallel execution print("Starting parallel execution") @@ -260,11 +265,16 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct # Wait for all futures to complete for j, result in enumerate(results): - generated_structures[j+num_structures_old], energy_unrlxd[j], energy_rlxd[j] = result - if generated_structures[j+num_structures_old] is None: + generated_structures[num_structures_old + j], energy_unrlxd[j], energy_rlxd[j] = result + if generated_structures[num_structures_old + j] is None: print("Structure failed the checks") continue - rlxd_structures.append(generated_structures[j+num_structures_old].copy()) + rlxd_structures.append(generated_structures[num_structures_old + j].copy()) + rlxd_structures[-1].calc = SinglePointCalculator( + generated_structures[j+num_structures_old], + energy=generated_structures[num_structures_old + j].get_potential_energy(), + forces=generated_structures[num_structures_old + j].get_forces() + ) print("All futures completed") # Remove structures that failed the checks diff --git a/example/python_pkg/C-MgO_learn/pca.ipynb b/example/python_pkg/C-MgO_learn/pca.ipynb index 4e403cb6..0ac9cf37 100644 --- a/example/python_pkg/C-MgO_learn/pca.ipynb +++ b/example/python_pkg/C-MgO_learn/pca.ipynb @@ -131,7 +131,7 @@ "outputs": [], "source": [ "## Load the unrelaxed structures\n", - "unrlxd_structures = read(\"DTMP\"+identifier+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "unrlxd_structures = read(\"DOutput\"+identifier+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", "for structure in unrlxd_structures:\n", " structure.calc = calc" ] @@ -143,7 +143,7 @@ "outputs": [], "source": [ "## Load the relaxed structures\n", - "rlxd_structures = read(\"DTMP\"+identifier+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "rlxd_structures = read(\"DOutput\"+identifier+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", "for structure in rlxd_structures:\n", " structure.calc = calc\n", "# min_energy = min([structure.get_potential_energy()/len(structure) for structure in rlxd_structures])" @@ -316,8 +316,8 @@ " ax.scatter(rlxd_X_reduced[min_energy_index, 0], rlxd_X_reduced[min_energy_index, 1], s=200, edgecolor='red', facecolor='none', linewidth=2)\n", "\n", "## Add labels\n", - "fig.text(0.5, 0.04, 'Principal Component 1', ha='center', fontsize=15)\n", - "axes[0].set_ylabel('Principal Component 2', fontsize=15)\n", + "fig.text(0.5, 0.04, 'Principal component 1', ha='center', fontsize=15)\n", + "axes[0].set_ylabel('Principal component 2', fontsize=15)\n", "axes[0].set_title('Unrelaxed')\n", "axes[1].set_title('Relaxed')\n", "if identifier == \"_VASP\":\n", diff --git a/example/python_pkg/C_learn/DRAFFLE/DOutput/energies_rlxd_seed0.txt b/example/python_pkg/C_learn/DRAFFLE/DOutput/energies_rlxd_seed0.txt new file mode 100644 index 00000000..ba2b7a8d --- /dev/null +++ b/example/python_pkg/C_learn/DRAFFLE/DOutput/energies_rlxd_seed0.txt @@ -0,0 +1,1000 @@ +0 -7.46671724319458 +1 -7.761768817901611 +2 -7.559265613555908 +3 -7.499917507171631 +4 -9.064054489135742 +5 -9.064081192016602 +6 -8.059991836547852 +7 -7.529697418212891 +8 -9.064064025878906 +9 -8.06004524230957 +10 -7.6497578620910645 +11 -7.6132330894470215 +12 -7.804856300354004 +13 -9.063827514648438 +14 -9.064050674438477 +15 -9.064031600952148 +16 -7.864800930023193 +17 -7.5356950759887695 +18 -7.468886375427246 +19 -9.064067840576172 +20 -7.564468860626221 +21 -7.901965141296387 +22 -7.837897300720215 +23 -7.613235950469971 +24 -9.0640869140625 +25 -9.064088821411133 +26 -7.85193395614624 +27 -9.064069747924805 +28 -7.655058860778809 +29 -9.064046859741211 +30 -7.9021992683410645 +31 -9.064044952392578 +32 -7.288197994232178 +33 -9.064077377319336 +34 -9.064050674438477 +35 -7.738381862640381 +36 -7.6897664070129395 +37 -9.064085006713867 +38 -9.064079284667969 +39 -7.502946853637695 +40 -7.798646926879883 +41 -7.646306037902832 +42 -9.064085006713867 +43 -9.064071655273438 +44 -9.06406021118164 +45 -8.060050010681152 +46 -9.064085006713867 +47 -9.06408405303955 +48 -9.064023971557617 +49 -9.064085960388184 +50 -7.779990196228027 +51 -9.06406307220459 +52 -9.064082145690918 +53 -9.064082145690918 +54 -9.064083099365234 +55 -7.738173484802246 +56 -7.983728408813477 +57 -8.113298416137695 +58 -9.064067840576172 +59 -7.837855339050293 +60 -7.890251159667969 +61 -9.064079284667969 +62 -8.113286972045898 +63 -7.998491287231445 +64 -7.798721790313721 +65 -8.00741958618164 +66 -9.0640869140625 +67 -9.06407642364502 +68 -7.5701584815979 +69 -7.779989242553711 +70 -9.0640869140625 +71 -7.804872989654541 +72 -7.502915382385254 +73 -7.565874099731445 +74 -7.717765808105469 +75 -9.06408405303955 +76 -9.06406021118164 +77 -9.064079284667969 +78 -7.602352142333984 +79 -9.064058303833008 +80 -9.063992500305176 +81 -7.798725605010986 +82 -7.9022297859191895 +83 -7.569190979003906 +84 -7.83790397644043 +85 -7.6021552085876465 +86 -7.588003158569336 +87 -7.403774738311768 +88 -9.064066886901855 +89 -7.804843425750732 +90 -7.837827682495117 +91 -9.064081192016602 +92 -7.4927520751953125 +93 -7.837902069091797 +94 -9.064067840576172 +95 -9.0640869140625 +96 -7.657420635223389 +97 -9.064075469970703 +98 -9.064083099365234 +99 -9.06406021118164 +100 -9.064078330993652 +101 -9.06363296508789 +102 -9.064080238342285 +103 -9.06408405303955 +104 -7.837897777557373 +105 -9.064072608947754 +106 -9.064064979553223 +107 -8.060050010681152 +108 -7.623502731323242 +109 -9.064085960388184 +110 -9.064077377319336 +111 -8.060062408447266 +112 -7.779994010925293 +113 -7.56129264831543 +114 -7.395891189575195 +115 -7.658965110778809 +116 -9.064069747924805 +117 -7.738155841827393 +118 -9.064078330993652 +119 -9.06405258178711 +120 -9.064050674438477 +121 -7.613247871398926 +122 -8.06005859375 +123 -9.064050674438477 +124 -7.8378586769104 +125 -9.064079284667969 +126 -7.8640971183776855 +127 -7.739743232727051 +128 -7.606507301330566 +129 -9.064078330993652 +130 -9.064072608947754 +131 -7.711942195892334 +132 -7.741828441619873 +133 -9.064068794250488 +134 -9.064044952392578 +135 -9.06401252746582 +136 -9.064064025878906 +137 -7.779992580413818 +138 -9.064075469970703 +139 -7.902349472045898 +140 -7.988633155822754 +141 -7.804869651794434 +142 -9.06406307220459 +143 -9.064065933227539 +144 -7.915647506713867 +145 -9.064079284667969 +146 -7.606497287750244 +147 -7.774993896484375 +148 -9.064078330993652 +149 -7.636028289794922 +150 -7.630472183227539 +151 -7.915622711181641 +152 -9.064059257507324 +153 -9.064079284667969 +154 -9.064068794250488 +155 -9.064077377319336 +156 -7.8378448486328125 +157 -9.064053535461426 +158 -8.060066223144531 +159 -7.625127792358398 +160 -9.064074516296387 +161 -7.990740776062012 +162 -7.38029670715332 +163 -9.064082145690918 +164 -7.898954391479492 +165 -9.064082145690918 +166 -7.473813533782959 +167 -7.915649890899658 +168 -7.904606819152832 +169 -9.064079284667969 +170 -7.706534385681152 +171 -7.698086738586426 +172 -7.890316009521484 +173 -9.064065933227539 +174 -9.064071655273438 +175 -9.06407356262207 +176 -7.569275856018066 +177 -7.779983997344971 +178 -7.7616658210754395 +179 -9.064077377319336 +180 -9.064057350158691 +181 -7.897143363952637 +182 -7.798725128173828 +183 -7.645262718200684 +184 -7.4915690422058105 +185 -7.435067653656006 +186 -7.804866313934326 +187 -9.064004898071289 +188 -9.06407642364502 +189 -7.6671857833862305 +190 -9.064088821411133 +191 -7.568464279174805 +192 -7.707293510437012 +193 -7.772226810455322 +194 -9.064069747924805 +195 -7.837851047515869 +196 -7.804872512817383 +197 -7.606508255004883 +198 -9.064080238342285 +199 -7.899049758911133 +200 -7.606472969055176 +201 -7.344770431518555 +202 -9.064083099365234 +203 -7.36248779296875 +204 -7.864793300628662 +205 -7.864794731140137 +206 -8.060060501098633 +207 -7.673759937286377 +208 -7.73276424407959 +209 -7.44532585144043 +210 -7.655864238739014 +211 -7.795297622680664 +212 -9.064042091369629 +213 -7.626308441162109 +214 -7.288258075714111 +215 -7.802527904510498 +216 -7.668293476104736 +217 -9.064085006713867 +218 -9.064083099365234 +219 -7.587989807128906 +220 -9.06404972076416 +221 -9.064068794250488 +222 -9.06408405303955 +223 -9.064046859741211 +224 -8.11329460144043 +225 -9.064058303833008 +226 -7.606457233428955 +227 -9.064085006713867 +228 -7.732751846313477 +229 -9.064090728759766 +230 -7.649750232696533 +231 -9.064053535461426 +232 -8.111794471740723 +233 -9.064048767089844 +234 -7.864806175231934 +235 -7.779973983764648 +236 -9.06408405303955 +237 -7.800027847290039 +238 -9.064085960388184 +239 -7.898444175720215 +240 -9.064078330993652 +241 -9.0640869140625 +242 -9.06404972076416 +243 -7.987721920013428 +244 -9.064080238342285 +245 -9.064087867736816 +246 -9.064081192016602 +247 -7.138001918792725 +248 -8.113300323486328 +249 -7.802548408508301 +250 -9.064083099365234 +251 -7.905372142791748 +252 -9.064074516296387 +253 -9.06408405303955 +254 -9.064081192016602 +255 -9.064087867736816 +256 -9.064046859741211 +257 -7.611690521240234 +258 -7.899073600769043 +259 -7.8439483642578125 +260 -9.064085006713867 +261 -7.947166919708252 +262 -9.064083099365234 +263 -7.417083740234375 +264 -7.7987470626831055 +265 -7.779743194580078 +266 -9.064085006713867 +267 -7.796970367431641 +268 -9.064078330993652 +269 -9.064082145690918 +270 -9.064077377319336 +271 -7.897177219390869 +272 -9.064081192016602 +273 -7.725342750549316 +274 -9.06408405303955 +275 -9.064069747924805 +276 -9.064077377319336 +277 -9.06407642364502 +278 -7.780007362365723 +279 -9.064067840576172 +280 -7.837876319885254 +281 -9.064075469970703 +282 -7.565878391265869 +283 -7.915637969970703 +284 -7.566555976867676 +285 -7.6537628173828125 +286 -8.11328411102295 +287 -9.064074516296387 +288 -9.06406021118164 +289 -9.064071655273438 +290 -7.798730850219727 +291 -7.803275108337402 +292 -7.779998302459717 +293 -7.9045796394348145 +294 -9.06406021118164 +295 -9.064059257507324 +296 -7.903016090393066 +297 -9.064082145690918 +298 -7.761683464050293 +299 -9.064079284667969 +300 -9.06408405303955 +301 -9.064059257507324 +302 -9.064085006713867 +303 -7.583813667297363 +304 -7.779999256134033 +305 -9.064051628112793 +306 -7.624391555786133 +307 -9.064088821411133 +308 -9.064069747924805 +309 -7.6064629554748535 +310 -9.06408405303955 +311 -7.6023149490356445 +312 -9.064070701599121 +313 -9.064078330993652 +314 -7.738170623779297 +315 -9.064082145690918 +316 -7.473801612854004 +317 -7.837764739990234 +318 -7.494704246520996 +319 -9.064082145690918 +320 -9.064065933227539 +321 -7.976980209350586 +322 -7.528559684753418 +323 -7.802660942077637 +324 -7.947198867797852 +325 -7.738163948059082 +326 -7.739193439483643 +327 -9.064085006713867 +328 -9.064044952392578 +329 -7.739745140075684 +330 -9.064085006713867 +331 -9.06405258178711 +332 -8.060042381286621 +333 -9.064081192016602 +334 -9.06404972076416 +335 -9.06408977508545 +336 -8.060053825378418 +337 -9.064065933227539 +338 -9.06407356262207 +339 -9.064071655273438 +340 -7.688249588012695 +341 -7.79873514175415 +342 -9.064061164855957 +343 -9.064066886901855 +344 -7.535689353942871 +345 -7.734156608581543 +346 -7.798733711242676 +347 -7.779984474182129 +348 -7.738185405731201 +349 -7.804867267608643 +350 -9.06407356262207 +351 -7.864785194396973 +352 -7.6234025955200195 +353 -7.253953456878662 +354 -7.363303184509277 +355 -9.064072608947754 +356 -9.064070701599121 +357 -8.0079984664917 +358 -7.837860584259033 +359 -7.27909517288208 +360 -9.064074516296387 +361 -7.565864562988281 +362 -7.708899974822998 +363 -7.602447032928467 +364 -7.798737525939941 +365 -7.915651321411133 +366 -9.064082145690918 +367 -7.779983043670654 +368 -7.864797592163086 +369 -8.060050010681152 +370 -7.798726558685303 +371 -9.064061164855957 +372 -9.064065933227539 +373 -7.67374324798584 +374 -7.5658369064331055 +375 -9.064064025878906 +376 -7.94716739654541 +377 -9.063043594360352 +378 -9.06407642364502 +379 -9.06406307220459 +380 -7.898951530456543 +381 -7.661760330200195 +382 -9.064080238342285 +383 -9.064075469970703 +384 -9.064043998718262 +385 -9.064080238342285 +386 -9.064081192016602 +387 -9.064047813415527 +388 -7.652034282684326 +389 -9.064074516296387 +390 -7.717774391174316 +391 -7.610191822052002 +392 -9.064081192016602 +393 -7.673899173736572 +394 -9.064074516296387 +395 -7.864804267883301 +396 -7.901947021484375 +397 -9.064085006713867 +398 -7.732760429382324 +399 -9.064083099365234 +400 -7.782713413238525 +401 -7.902407646179199 +402 -7.720774173736572 +403 -9.064047813415527 +404 -8.007081985473633 +405 -7.645172119140625 +406 -9.064046859741211 +407 -9.064085006713867 +408 -7.773974418640137 +409 -9.064079284667969 +410 -7.676827907562256 +411 -7.78001070022583 +412 -7.798735618591309 +413 -7.634696960449219 +414 -9.064064025878906 +415 -9.06408405303955 +416 -7.837890625 +417 -7.50295352935791 +418 -9.064082145690918 +419 -7.632152557373047 +420 -7.864402770996094 +421 -9.064085006713867 +422 -7.675619125366211 +423 -7.947174072265625 +424 -9.063624382019043 +425 -9.064078330993652 +426 -7.709378242492676 +427 -9.0640869140625 +428 -9.064041137695312 +429 -7.90302038192749 +430 -7.602426528930664 +431 -7.864781379699707 +432 -9.064048767089844 +433 -9.064032554626465 +434 -7.904069900512695 +435 -7.779973030090332 +436 -9.064051628112793 +437 -9.064079284667969 +438 -9.064080238342285 +439 -7.371070861816406 +440 -9.064043045043945 +441 -9.05327033996582 +442 -9.06407642364502 +443 -7.905429363250732 +444 -7.475221157073975 +445 -7.73819637298584 +446 -9.064078330993652 +447 -9.064062118530273 +448 -7.915644645690918 +449 -7.619472026824951 +450 -9.064087867736816 +451 -7.804863452911377 +452 -9.064078330993652 +453 -9.064080238342285 +454 -7.475222587585449 +455 -7.544063568115234 +456 -8.113295555114746 +457 -7.5599260330200195 +458 -7.570390224456787 +459 -8.06005573272705 +460 -7.798740386962891 +461 -9.064054489135742 +462 -9.064077377319336 +463 -7.8379034996032715 +464 -9.06408405303955 +465 -7.672008514404297 +466 -8.007983207702637 +467 -7.741840839385986 +468 -7.837903022766113 +469 -9.064066886901855 +470 -9.064082145690918 +471 -7.796937465667725 +472 -9.064068794250488 +473 -7.655862331390381 +474 -7.998490333557129 +475 -9.064057350158691 +476 -9.064064979553223 +477 -9.064044952392578 +478 -7.796937465667725 +479 -9.064083099365234 +480 -7.864804744720459 +481 -9.064048767089844 +482 -7.779987812042236 +483 -8.060041427612305 +484 -9.064066886901855 +485 -9.043476104736328 +486 -9.063860893249512 +487 -9.064037322998047 +488 -7.511075019836426 +489 -7.483211040496826 +490 -7.6571044921875 +491 -7.7145843505859375 +492 -7.717782974243164 +493 -7.864797592163086 +494 -9.064088821411133 +495 -9.064070701599121 +496 -7.494700908660889 +497 -7.8990936279296875 +498 -9.064068794250488 +499 -9.064081192016602 +500 -8.109705924987793 +501 -7.798731803894043 +502 -9.06408405303955 +503 -9.064069747924805 +504 -7.405154705047607 +505 -9.064072608947754 +506 -7.864806175231934 +507 -7.54088830947876 +508 -9.064087867736816 +509 -8.356389999389648 +510 -7.602081775665283 +511 -9.064074516296387 +512 -7.80485200881958 +513 -9.064042091369629 +514 -9.064083099365234 +515 -9.06403923034668 +516 -8.060052871704102 +517 -9.064087867736816 +518 -9.064068794250488 +519 -9.064087867736816 +520 -9.06407356262207 +521 -9.06408405303955 +522 -7.590173721313477 +523 -9.064075469970703 +524 -7.390007972717285 +525 -7.605257511138916 +526 -7.83790397644043 +527 -7.90241813659668 +528 -7.796936511993408 +529 -7.892817497253418 +530 -7.904615879058838 +531 -9.064056396484375 +532 -7.8989434242248535 +533 -9.06406021118164 +534 -9.064056396484375 +535 -7.659409523010254 +536 -7.677009582519531 +537 -7.837886810302734 +538 -7.804863929748535 +539 -9.064066886901855 +540 -7.802492141723633 +541 -8.06005859375 +542 -9.064081192016602 +543 -9.064066886901855 +544 -9.064088821411133 +545 -7.624398708343506 +546 -9.064066886901855 +547 -9.064078330993652 +548 -9.06407356262207 +549 -7.734374523162842 +550 -7.864797115325928 +551 -7.837801456451416 +552 -9.064069747924805 +553 -9.064085006713867 +554 -8.060046195983887 +555 -7.940216064453125 +556 -7.837845802307129 +557 -7.522243499755859 +558 -9.064081192016602 +559 -7.837891578674316 +560 -9.06405258178711 +561 -7.905403137207031 +562 -7.779987335205078 +563 -9.064069747924805 +564 -8.057414054870605 +565 -9.064077377319336 +566 -7.529624938964844 +567 -9.064079284667969 +568 -9.06408405303955 +569 -7.804875373840332 +570 -9.064066886901855 +571 -9.064058303833008 +572 -7.587987422943115 +573 -9.06407356262207 +574 -9.064082145690918 +575 -7.902284622192383 +576 -9.064055442810059 +577 -9.06408405303955 +578 -7.998416423797607 +579 -7.8048624992370605 +580 -9.064075469970703 +581 -9.06393051147461 +582 -7.904630184173584 +583 -7.3504743576049805 +584 -7.46893835067749 +585 -7.6755523681640625 +586 -9.064085006713867 +587 -9.064062118530273 +588 -9.06407356262207 +589 -7.8000335693359375 +590 -7.469902515411377 +591 -7.802530288696289 +592 -9.064064025878906 +593 -9.064081192016602 +594 -7.864789009094238 +595 -9.064085006713867 +596 -9.064078330993652 +597 -9.064082145690918 +598 -7.74077033996582 +599 -9.064078330993652 +600 -7.8647990226745605 +601 -9.064051628112793 +602 -9.064057350158691 +603 -9.064078330993652 +604 -9.064085006713867 +605 -9.064071655273438 +606 -9.064077377319336 +607 -9.064043045043945 +608 -9.063928604125977 +609 -9.06408405303955 +610 -7.837926864624023 +611 -7.606504440307617 +612 -7.606471061706543 +613 -7.864795207977295 +614 -9.064065933227539 +615 -9.06407356262207 +616 -8.008001327514648 +617 -9.064079284667969 +618 -7.606450080871582 +619 -9.064080238342285 +620 -7.4752302169799805 +621 -7.254012107849121 +622 -9.06408405303955 +623 -7.843924522399902 +624 -9.064074516296387 +625 -7.898743152618408 +626 -8.060051918029785 +627 -7.3626708984375 +628 -9.064087867736816 +629 -9.064083099365234 +630 -9.064083099365234 +631 -9.064085006713867 +632 -8.060065269470215 +633 -8.060050010681152 +634 -9.064079284667969 +635 -9.06407356262207 +636 -7.336514949798584 +637 -7.7616777420043945 +638 -7.798741817474365 +639 -7.535693645477295 +640 -9.064079284667969 +641 -9.064068794250488 +642 -9.064077377319336 +643 -7.899106502532959 +644 -7.904569149017334 +645 -7.864783763885498 +646 -9.064077377319336 +647 -7.613246917724609 +648 -7.555421829223633 +649 -9.064085006713867 +650 -7.588455677032471 +651 -8.113287925720215 +652 -9.064041137695312 +653 -7.837861061096191 +654 -7.563817024230957 +655 -7.864792346954346 +656 -7.837904930114746 +657 -9.06406307220459 +658 -9.064071655273438 +659 -9.064085006713867 +660 -9.064067840576172 +661 -7.738183975219727 +662 -8.060049057006836 +663 -7.893726348876953 +664 -9.06407356262207 +665 -9.064081192016602 +666 -8.113300323486328 +667 -8.11111831665039 +668 -7.994819641113281 +669 -9.064083099365234 +670 -7.796937465667725 +671 -9.064081192016602 +672 -9.064074516296387 +673 -7.725529670715332 +674 -9.06405258178711 +675 -7.904577732086182 +676 -7.837897300720215 +677 -7.585260391235352 +678 -8.060060501098633 +679 -7.390578746795654 +680 -9.06407356262207 +681 -9.064081192016602 +682 -8.113288879394531 +683 -9.064054489135742 +684 -9.06403636932373 +685 -7.782845497131348 +686 -7.802609443664551 +687 -7.740581035614014 +688 -7.599094390869141 +689 -7.741826057434082 +690 -7.903578281402588 +691 -9.064078330993652 +692 -7.675619602203369 +693 -9.064081192016602 +694 -8.007994651794434 +695 -9.064069747924805 +696 -7.843918800354004 +697 -9.064072608947754 +698 -7.67678689956665 +699 -9.064079284667969 +700 -7.802524089813232 +701 -9.06407642364502 +702 -9.064074516296387 +703 -9.064071655273438 +704 -9.064070701599121 +705 -9.064074516296387 +706 -8.008005142211914 +707 -9.064067840576172 +708 -7.899104118347168 +709 -9.064082145690918 +710 -7.665282726287842 +711 -9.064079284667969 +712 -7.804867267608643 +713 -7.657419204711914 +714 -8.9979248046875 +715 -9.064085960388184 +716 -9.064079284667969 +717 -7.650778293609619 +718 -9.064045906066895 +719 -7.7482829093933105 +720 -9.064082145690918 +721 -8.060033798217773 +722 -9.064064025878906 +723 -9.064067840576172 +724 -9.064080238342285 +725 -9.064079284667969 +726 -9.064078330993652 +727 -9.064085960388184 +728 -9.064056396484375 +729 -9.064083099365234 +730 -7.804873943328857 +731 -7.721997261047363 +732 -9.064080238342285 +733 -9.064050674438477 +734 -7.804879188537598 +735 -9.064067840576172 +736 -9.064078330993652 +737 -7.8647918701171875 +738 -8.060051918029785 +739 -7.8378424644470215 +740 -7.417080402374268 +741 -7.739774703979492 +742 -7.717779636383057 +743 -9.064070701599121 +744 -9.064077377319336 +745 -9.064069747924805 +746 -7.657485485076904 +747 -7.717776298522949 +748 -7.9851179122924805 +749 -9.06405258178711 +750 -9.064057350158691 +751 -7.837754726409912 +752 -7.837735652923584 +753 -8.11309814453125 +754 -7.798735618591309 +755 -9.064079284667969 +756 -9.064085006713867 +757 -9.064067840576172 +758 -9.06406307220459 +759 -9.064068794250488 +760 -7.864805698394775 +761 -8.060029983520508 +762 -9.064064979553223 +763 -9.06407642364502 +764 -7.738644123077393 +765 -7.804874420166016 +766 -9.06408977508545 +767 -7.8647847175598145 +768 -9.064069747924805 +769 -9.064079284667969 +770 -7.646307945251465 +771 -8.060022354125977 +772 -9.064083099365234 +773 -9.0640869140625 +774 -9.064081192016602 +775 -9.064072608947754 +776 -9.064085006713867 +777 -9.063654899597168 +778 -9.064057350158691 +779 -7.2075395584106445 +780 -9.064055442810059 +781 -9.064061164855957 +782 -7.902319431304932 +783 -7.864798069000244 +784 -7.671499252319336 +785 -9.064077377319336 +786 -9.0640869140625 +787 -7.837841510772705 +788 -9.064078330993652 +789 -8.113297462463379 +790 -7.7799859046936035 +791 -9.064081192016602 +792 -9.064046859741211 +793 -9.064077377319336 +794 -7.5703840255737305 +795 -7.798733711242676 +796 -9.064064025878906 +797 -9.064077377319336 +798 -7.424100399017334 +799 -9.064069747924805 +800 -7.748257637023926 +801 -9.064081192016602 +802 -9.064075469970703 +803 -7.690703868865967 +804 -9.064083099365234 +805 -7.798736095428467 +806 -8.060050964355469 +807 -7.338460445404053 +808 -9.064085960388184 +809 -9.064074516296387 +810 -7.796931266784668 +811 -7.714536666870117 +812 -9.064071655273438 +813 -9.064064025878906 +814 -9.06405258178711 +815 -7.779972553253174 +816 -7.837893009185791 +817 -7.704198837280273 +818 -9.064075469970703 +819 -9.064079284667969 +820 -7.624390602111816 +821 -7.7968902587890625 +822 -9.064082145690918 +823 -9.06406021118164 +824 -7.793280124664307 +825 -7.899047374725342 +826 -9.064053535461426 +827 -9.064072608947754 +828 -7.39923620223999 +829 -8.060068130493164 +830 -9.064072608947754 +831 -7.802519798278809 +832 -9.064083099365234 +833 -7.493803024291992 +834 -9.06406307220459 +835 -7.580492973327637 +836 -7.60649299621582 +837 -9.064085960388184 +838 -9.064069747924805 +839 -7.335829734802246 +840 -9.06407642364502 +841 -7.469902992248535 +842 -7.655557632446289 +843 -9.064050674438477 +844 -9.064072608947754 +845 -9.064057350158691 +846 -8.058680534362793 +847 -9.064085960388184 +848 -8.060064315795898 +849 -9.064081192016602 +850 -7.8378987312316895 +851 -7.998493671417236 +852 -9.06406021118164 +853 -9.024826049804688 +854 -8.060053825378418 +855 -7.7103657722473145 +856 -8.059996604919434 +857 -7.6692681312561035 +858 -9.064064025878906 +859 -8.113289833068848 +860 -7.392307281494141 +861 -9.064059257507324 +862 -9.064074516296387 +863 -9.064080238342285 +864 -7.707300186157227 +865 -7.902402877807617 +866 -9.064044952392578 +867 -7.798740863800049 +868 -9.064071655273438 +869 -7.761703968048096 +870 -9.064081192016602 +871 -7.675617694854736 +872 -9.064075469970703 +873 -9.064064979553223 +874 -7.606488227844238 +875 -9.064055442810059 +876 -7.535707473754883 +877 -7.623307704925537 +878 -7.9401960372924805 +879 -9.064082145690918 +880 -7.904559135437012 +881 -7.8378729820251465 +882 -9.064067840576172 +883 -9.064068794250488 +884 -9.064064025878906 +885 -7.804877758026123 +886 -9.0640869140625 +887 -9.064074516296387 +888 -8.060030937194824 +889 -9.063010215759277 +890 -7.633208751678467 +891 -9.064083099365234 +892 -9.064085006713867 +893 -7.676571846008301 +894 -9.064077377319336 +895 -7.947165489196777 +896 -7.963821887969971 +897 -9.064077377319336 +898 -7.6064958572387695 +899 -9.064043998718262 +900 -7.804862022399902 +901 -7.8048601150512695 +902 -8.060052871704102 +903 -9.0640869140625 +904 -9.064062118530273 +905 -9.064053535461426 +906 -9.064058303833008 +907 -7.685595512390137 +908 -9.064079284667969 +909 -7.475053787231445 +910 -7.804872512817383 +911 -9.064075469970703 +912 -9.064045906066895 +913 -9.064079284667969 +914 -9.064055442810059 +915 -9.064075469970703 +916 -7.738189697265625 +917 -9.06406021118164 +918 -7.3944525718688965 +919 -9.064085960388184 +920 -9.064064979553223 +921 -7.779999732971191 +922 -7.636761665344238 +923 -7.843841552734375 +924 -7.779980182647705 +925 -7.991211891174316 +926 -9.064072608947754 +927 -7.432979583740234 +928 -7.587963581085205 +929 -9.064085006713867 +930 -9.064057350158691 +931 -7.804861068725586 +932 -7.502937316894531 +933 -8.060056686401367 +934 -9.064087867736816 +935 -9.064058303833008 +936 -7.94716739654541 +937 -7.904460906982422 +938 -7.905415058135986 +939 -7.837821960449219 +940 -7.80487060546875 +941 -7.837841510772705 +942 -7.843934535980225 +943 -7.738173484802246 +944 -9.064068794250488 +945 -9.064082145690918 +946 -7.535703182220459 +947 -7.473826885223389 +948 -9.064081192016602 +949 -7.904612064361572 +950 -7.864774703979492 +951 -9.064044952392578 +952 -7.402742862701416 +953 -7.864800453186035 +954 -7.514472961425781 +955 -7.6653242111206055 +956 -9.064079284667969 +957 -9.06408977508545 +958 -7.837856292724609 +959 -7.649531364440918 +960 -7.8037109375 +961 -9.064082145690918 +962 -9.064082145690918 +963 -8.113287925720215 +964 -9.06408405303955 +965 -7.655835151672363 +966 -9.064047813415527 +967 -9.064080238342285 +968 -7.685607433319092 +969 -7.780002593994141 +970 -9.06408405303955 +971 -9.064062118530273 +972 -7.417113780975342 +973 -9.063929557800293 +974 -9.064078330993652 +975 -7.7177815437316895 +976 -9.06406307220459 +977 -7.535696983337402 +978 -7.837862968444824 +979 -7.837899208068848 +980 -9.0640869140625 +981 -8.058277130126953 +982 -7.864331245422363 +983 -9.064067840576172 +984 -7.864314079284668 +985 -9.064045906066895 +986 -9.064085006713867 +987 -9.064065933227539 +988 -7.796901702880859 +989 -7.864800453186035 +990 -7.779967784881592 +991 -7.6064772605896 +992 -9.064085006713867 +993 -7.905362129211426 +994 -8.059954643249512 +995 -7.940493583679199 +996 -9.06403923034668 +997 -7.779995918273926 +998 -7.864802837371826 +999 -9.06407356262207 diff --git a/example/python_pkg/C_learn/DRAFFLE/DOutput/energies_unrlxd_seed0.txt b/example/python_pkg/C_learn/DRAFFLE/DOutput/energies_unrlxd_seed0.txt new file mode 100644 index 00000000..bc5da1d5 --- /dev/null +++ b/example/python_pkg/C_learn/DRAFFLE/DOutput/energies_unrlxd_seed0.txt @@ -0,0 +1,1000 @@ +0 -5.625258445739746 +1 -5.54370641708374 +2 -5.506875038146973 +3 -5.625923156738281 +4 -6.034417152404785 +5 -6.180569648742676 +6 -6.222733020782471 +7 -5.737820625305176 +8 -8.448609352111816 +9 -5.79707145690918 +10 -6.5035505294799805 +11 -5.908145904541016 +12 -6.437061309814453 +13 -5.699845314025879 +14 -6.465216636657715 +15 -6.219339370727539 +16 -6.511139392852783 +17 -6.203361988067627 +18 -6.161733627319336 +19 -7.083890914916992 +20 -6.064803123474121 +21 -6.00860595703125 +22 -6.227874755859375 +23 -5.816102027893066 +24 -6.306500434875488 +25 -6.583066940307617 +26 -6.138380527496338 +27 -7.418243408203125 +28 -5.979685306549072 +29 -7.306440353393555 +30 -5.964258193969727 +31 -8.53251838684082 +32 -6.222347259521484 +33 -6.017777919769287 +34 -5.777582168579102 +35 -6.309724807739258 +36 -5.860268592834473 +37 -6.541164875030518 +38 -6.253314971923828 +39 -5.830376625061035 +40 -5.568923473358154 +41 -6.353241920471191 +42 -7.125243186950684 +43 -5.81344747543335 +44 -6.706960201263428 +45 -6.275940418243408 +46 -6.8769354820251465 +47 -6.172989845275879 +48 -6.3487958908081055 +49 -5.952094078063965 +50 -5.683538436889648 +51 -8.573521614074707 +52 -5.833309173583984 +53 -6.26357889175415 +54 -6.875478744506836 +55 -5.849799156188965 +56 -6.464990615844727 +57 -6.507535934448242 +58 -7.541873931884766 +59 -5.766350746154785 +60 -6.210514545440674 +61 -5.845498561859131 +62 -6.706912517547607 +63 -5.885786533355713 +64 -6.118422031402588 +65 -5.998577117919922 +66 -6.8005146980285645 +67 -5.737294673919678 +68 -5.845566749572754 +69 -6.011412143707275 +70 -5.749746322631836 +71 -6.931706428527832 +72 -5.703165054321289 +73 -6.259182453155518 +74 -5.433825492858887 +75 -7.372961521148682 +76 -6.20775032043457 +77 -6.110994338989258 +78 -6.273366451263428 +79 -8.034229278564453 +80 -5.9706010818481445 +81 -5.636708736419678 +82 -5.875096321105957 +83 -5.867452621459961 +84 -6.71538782119751 +85 -6.028715133666992 +86 -5.811283588409424 +87 -5.777836799621582 +88 -6.58015251159668 +89 -6.623195171356201 +90 -6.3985276222229 +91 -6.094529151916504 +92 -6.2889018058776855 +93 -6.778980255126953 +94 -6.546700954437256 +95 -8.559852600097656 +96 -5.728944778442383 +97 -8.931962966918945 +98 -6.951544761657715 +99 -6.903443336486816 +100 -6.614019393920898 +101 -6.15463924407959 +102 -6.288923263549805 +103 -6.576052188873291 +104 -5.531921863555908 +105 -7.014852523803711 +106 -6.081881523132324 +107 -5.890716552734375 +108 -6.408995151519775 +109 -5.948583602905273 +110 -7.335312843322754 +111 -6.053921222686768 +112 -5.636848449707031 +113 -5.957300662994385 +114 -5.85793924331665 +115 -5.374678611755371 +116 -6.300693988800049 +117 -6.318826675415039 +118 -7.496017932891846 +119 -6.5885467529296875 +120 -6.827249050140381 +121 -5.713998794555664 +122 -6.290520668029785 +123 -6.584198951721191 +124 -5.806170463562012 +125 -6.1244354248046875 +126 -5.951214790344238 +127 -5.766374588012695 +128 -5.711113452911377 +129 -6.654621601104736 +130 -7.000788688659668 +131 -6.043679714202881 +132 -6.269127368927002 +133 -8.948888778686523 +134 -5.87860631942749 +135 -6.486729621887207 +136 -6.506778717041016 +137 -6.106212615966797 +138 -6.148618698120117 +139 -5.573973655700684 +140 -5.619133949279785 +141 -6.928820610046387 +142 -5.84007453918457 +143 -6.883596420288086 +144 -5.622611999511719 +145 -6.966097354888916 +146 -6.226434707641602 +147 -5.719452381134033 +148 -5.746899604797363 +149 -5.706743240356445 +150 -6.109408378601074 +151 -5.751640319824219 +152 -6.162962913513184 +153 -5.937086582183838 +154 -6.250260829925537 +155 -5.639177322387695 +156 -6.008530616760254 +157 -5.88198184967041 +158 -5.9306182861328125 +159 -5.894412994384766 +160 -6.729594707489014 +161 -5.875377178192139 +162 -5.86617374420166 +163 -7.4024810791015625 +164 -5.979375839233398 +165 -6.184109687805176 +166 -5.0887908935546875 +167 -6.187101364135742 +168 -5.819021701812744 +169 -7.3570051193237305 +170 -6.482846260070801 +171 -5.852309703826904 +172 -5.41455078125 +173 -6.155811309814453 +174 -6.196176528930664 +175 -7.602703094482422 +176 -5.637753486633301 +177 -5.860238075256348 +178 -5.672201156616211 +179 -6.695729732513428 +180 -8.963038444519043 +181 -5.9278459548950195 +182 -6.407260894775391 +183 -5.778528690338135 +184 -6.520796775817871 +185 -5.642932891845703 +186 -6.376558780670166 +187 -5.737453460693359 +188 -6.378030776977539 +189 -5.668063640594482 +190 -9.050735473632812 +191 -6.2520599365234375 +192 -5.769150733947754 +193 -5.819587707519531 +194 -6.080240249633789 +195 -5.662180423736572 +196 -6.58329439163208 +197 -6.081718921661377 +198 -6.8168816566467285 +199 -5.753853797912598 +200 -5.7975006103515625 +201 -5.655069351196289 +202 -7.139856338500977 +203 -6.021464824676514 +204 -5.645769119262695 +205 -6.313482284545898 +206 -5.793389797210693 +207 -6.001546859741211 +208 -5.798325061798096 +209 -5.7817840576171875 +210 -6.405166149139404 +211 -6.421175956726074 +212 -6.899491310119629 +213 -6.019468784332275 +214 -5.766125202178955 +215 -6.535529613494873 +216 -5.711154937744141 +217 -5.969555854797363 +218 -6.304862022399902 +219 -5.804429054260254 +220 -7.610747814178467 +221 -7.637850761413574 +222 -8.987985610961914 +223 -7.327510356903076 +224 -5.733061790466309 +225 -6.128152847290039 +226 -5.945845603942871 +227 -7.4068098068237305 +228 -5.5342183113098145 +229 -5.824772834777832 +230 -5.92591667175293 +231 -6.586916923522949 +232 -5.709383964538574 +233 -7.449156761169434 +234 -6.157779216766357 +235 -6.085198879241943 +236 -6.542386531829834 +237 -5.685559272766113 +238 -7.209693908691406 +239 -5.695235252380371 +240 -6.287254333496094 +241 -6.272797584533691 +242 -6.629539489746094 +243 -5.767636775970459 +244 -6.136187553405762 +245 -9.050735473632812 +246 -7.1028828620910645 +247 -6.145686149597168 +248 -6.487083435058594 +249 -6.918762683868408 +250 -8.81816291809082 +251 -6.186945915222168 +252 -6.194036483764648 +253 -6.543398380279541 +254 -6.072504997253418 +255 -6.4146318435668945 +256 -6.30171012878418 +257 -5.882248401641846 +258 -5.065625190734863 +259 -5.78890323638916 +260 -6.574092864990234 +261 -5.670848846435547 +262 -6.782797813415527 +263 -6.178454399108887 +264 -5.870675563812256 +265 -5.705730438232422 +266 -7.135876655578613 +267 -6.521923065185547 +268 -7.51512336730957 +269 -7.124627113342285 +270 -7.816612243652344 +271 -5.712604999542236 +272 -6.438637733459473 +273 -6.443897247314453 +274 -6.251984596252441 +275 -8.532449722290039 +276 -8.705018043518066 +277 -9.008456230163574 +278 -6.208083629608154 +279 -6.765484809875488 +280 -6.4741058349609375 +281 -5.922882080078125 +282 -6.073613166809082 +283 -6.070947647094727 +284 -5.781082630157471 +285 -6.104592323303223 +286 -6.199921607971191 +287 -6.313396453857422 +288 -8.950899124145508 +289 -5.950301170349121 +290 -6.449919700622559 +291 -6.466614246368408 +292 -5.758705139160156 +293 -5.553998947143555 +294 -6.455525875091553 +295 -6.401394367218018 +296 -6.504973411560059 +297 -6.307416915893555 +298 -6.114121437072754 +299 -6.150482654571533 +300 -8.885735511779785 +301 -6.627658843994141 +302 -6.864001750946045 +303 -6.2408552169799805 +304 -6.436013221740723 +305 -5.863783836364746 +306 -6.156900405883789 +307 -7.150396347045898 +308 -6.792147636413574 +309 -6.226151943206787 +310 -6.393101692199707 +311 -6.343409061431885 +312 -6.0498552322387695 +313 -5.678066253662109 +314 -5.771461486816406 +315 -6.717714786529541 +316 -6.310296058654785 +317 -5.749441146850586 +318 -6.040179252624512 +319 -6.371785640716553 +320 -6.260903835296631 +321 -5.583294868469238 +322 -6.262316703796387 +323 -5.899998664855957 +324 -5.561620235443115 +325 -5.467794418334961 +326 -5.795025825500488 +327 -7.609809875488281 +328 -6.51627254486084 +329 -6.246192455291748 +330 -6.805715084075928 +331 -6.7032036781311035 +332 -6.06033182144165 +333 -6.621670246124268 +334 -7.069849491119385 +335 -7.0513200759887695 +336 -5.794835090637207 +337 -8.934073448181152 +338 -6.535745620727539 +339 -6.035209655761719 +340 -6.164533615112305 +341 -6.868404865264893 +342 -7.689846515655518 +343 -6.5362420082092285 +344 -6.081188678741455 +345 -5.693109512329102 +346 -6.228372573852539 +347 -5.765520095825195 +348 -6.21735954284668 +349 -6.396574020385742 +350 -5.898601531982422 +351 -6.3542585372924805 +352 -6.395130157470703 +353 -5.651226043701172 +354 -5.925042152404785 +355 -7.545780658721924 +356 -6.251797676086426 +357 -6.4693450927734375 +358 -6.303279399871826 +359 -5.8799638748168945 +360 -6.006555557250977 +361 -5.806490421295166 +362 -5.564859390258789 +363 -7.013643264770508 +364 -6.601746082305908 +365 -5.9324541091918945 +366 -6.112591743469238 +367 -5.900864601135254 +368 -6.877999305725098 +369 -6.166744232177734 +370 -6.046445369720459 +371 -7.341767311096191 +372 -6.844782829284668 +373 -5.726247787475586 +374 -5.9779157638549805 +375 -5.311508655548096 +376 -5.670848846435547 +377 -5.804991722106934 +378 -6.28523063659668 +379 -6.561999320983887 +380 -5.842855453491211 +381 -6.09095573425293 +382 -6.505275726318359 +383 -6.582812309265137 +384 -6.685980796813965 +385 -8.967819213867188 +386 -6.121598243713379 +387 -7.450665473937988 +388 -5.9873433113098145 +389 -6.641507625579834 +390 -5.840574741363525 +391 -6.040524005889893 +392 -6.758048057556152 +393 -5.808074951171875 +394 -5.866438388824463 +395 -6.426656723022461 +396 -5.745184421539307 +397 -8.396958351135254 +398 -5.986380577087402 +399 -6.09887170791626 +400 -5.765338897705078 +401 -6.076348304748535 +402 -6.663179874420166 +403 -6.101449489593506 +404 -5.647885799407959 +405 -5.88641881942749 +406 -7.327509880065918 +407 -5.967791557312012 +408 -6.43614387512207 +409 -6.53305721282959 +410 -5.9732160568237305 +411 -6.011238098144531 +412 -6.061323165893555 +413 -5.760869979858398 +414 -8.66810131072998 +415 -6.720785140991211 +416 -6.384693145751953 +417 -6.111566543579102 +418 -5.94540548324585 +419 -5.831274032592773 +420 -6.138628005981445 +421 -7.183223724365234 +422 -6.282772064208984 +423 -5.935297966003418 +424 -5.941021919250488 +425 -6.231409549713135 +426 -6.01513671875 +427 -5.857850551605225 +428 -5.991311073303223 +429 -5.745452404022217 +430 -6.593457221984863 +431 -6.191692352294922 +432 -6.590087890625 +433 -5.953146457672119 +434 -6.0055437088012695 +435 -6.4543681144714355 +436 -6.829550266265869 +437 -6.0634050369262695 +438 -5.7538275718688965 +439 -5.879923343658447 +440 -6.317349433898926 +441 -6.0188117027282715 +442 -6.185413360595703 +443 -6.199267387390137 +444 -6.005063056945801 +445 -5.879277229309082 +446 -5.950657844543457 +447 -6.384634494781494 +448 -5.99052095413208 +449 -5.714311122894287 +450 -6.875188827514648 +451 -6.641371250152588 +452 -6.423637390136719 +453 -6.578392505645752 +454 -6.005063056945801 +455 -5.813251972198486 +456 -5.759304046630859 +457 -6.3449506759643555 +458 -5.5762038230896 +459 -5.721346378326416 +460 -5.862799644470215 +461 -6.720072269439697 +462 -9.00845718383789 +463 -5.762905120849609 +464 -6.439462661743164 +465 -5.886170864105225 +466 -6.1372857093811035 +467 -5.760171890258789 +468 -6.0960693359375 +469 -6.1089372634887695 +470 -8.202828407287598 +471 -6.082918167114258 +472 -6.886911392211914 +473 -5.774627685546875 +474 -5.885787010192871 +475 -6.204636573791504 +476 -7.3383307456970215 +477 -6.194353103637695 +478 -6.082918167114258 +479 -7.5326714515686035 +480 -6.281431198120117 +481 -6.346641540527344 +482 -6.409841537475586 +483 -5.740712642669678 +484 -6.960446357727051 +485 -5.914647102355957 +486 -6.627464771270752 +487 -6.542416572570801 +488 -6.283136367797852 +489 -5.9365081787109375 +490 -6.706348419189453 +491 -5.610869407653809 +492 -5.694388389587402 +493 -5.587920188903809 +494 -9.050735473632812 +495 -6.525986671447754 +496 -5.828036308288574 +497 -6.411458969116211 +498 -6.54382848739624 +499 -7.680239677429199 +500 -6.540629863739014 +501 -5.893093109130859 +502 -6.298898220062256 +503 -6.102260589599609 +504 -5.752753257751465 +505 -7.433257102966309 +506 -6.537933349609375 +507 -5.754422664642334 +508 -6.5206618309021 +509 -6.545675277709961 +510 -6.293200969696045 +511 -5.946765899658203 +512 -6.323009014129639 +513 -6.171902656555176 +514 -8.623857498168945 +515 -6.498884201049805 +516 -5.521573543548584 +517 -6.851832389831543 +518 -8.322074890136719 +519 -6.216789245605469 +520 -6.997589588165283 +521 -8.924962997436523 +522 -6.183781147003174 +523 -6.318470001220703 +524 -5.923692226409912 +525 -6.443979263305664 +526 -6.0960693359375 +527 -6.1618194580078125 +528 -6.082919120788574 +529 -6.108731269836426 +530 -5.845404624938965 +531 -6.445098876953125 +532 -5.979375839233398 +533 -5.809296607971191 +534 -6.3647942543029785 +535 -6.199468612670898 +536 -5.7772979736328125 +537 -5.899194717407227 +538 -6.641371726989746 +539 -6.1362385749816895 +540 -6.0739898681640625 +541 -6.593090057373047 +542 -6.203608512878418 +543 -6.656407833099365 +544 -6.934448719024658 +545 -5.757739067077637 +546 -8.305217742919922 +547 -8.870388984680176 +548 -6.677595138549805 +549 -5.743724822998047 +550 -6.131414890289307 +551 -6.501823425292969 +552 -9.018701553344727 +553 -6.358669281005859 +554 -5.471986293792725 +555 -6.012734413146973 +556 -6.269867897033691 +557 -5.951064586639404 +558 -6.112592697143555 +559 -6.325624465942383 +560 -6.014603137969971 +561 -6.945378303527832 +562 -6.288824558258057 +563 -5.496447563171387 +564 -5.909440040588379 +565 -7.534494876861572 +566 -6.068049430847168 +567 -7.11583137512207 +568 -6.382993698120117 +569 -6.135202407836914 +570 -6.221905708312988 +571 -8.35110092163086 +572 -5.452610015869141 +573 -6.226111888885498 +574 -6.386175632476807 +575 -5.994019508361816 +576 -6.002331733703613 +577 -6.5912652015686035 +578 -5.688867568969727 +579 -7.077563285827637 +580 -5.865667343139648 +581 -5.829936504364014 +582 -5.697108268737793 +583 -5.677310943603516 +584 -5.948738098144531 +585 -5.8670244216918945 +586 -8.950543403625488 +587 -6.985742092132568 +588 -6.381265640258789 +589 -6.102216720581055 +590 -5.9912567138671875 +591 -6.55414342880249 +592 -8.254939079284668 +593 -6.388506889343262 +594 -5.873917579650879 +595 -7.0899858474731445 +596 -6.201246738433838 +597 -6.895969390869141 +598 -5.568007469177246 +599 -6.892893314361572 +600 -6.375534534454346 +601 -6.96082878112793 +602 -5.769836902618408 +603 -8.465218544006348 +604 -6.413577556610107 +605 -9.002161979675293 +606 -6.308368682861328 +607 -6.559668064117432 +608 -5.8299360275268555 +609 -6.38946008682251 +610 -6.217807769775391 +611 -5.684643268585205 +612 -6.120643615722656 +613 -6.487399101257324 +614 -7.158870697021484 +615 -6.125647068023682 +616 -5.776715278625488 +617 -6.588736057281494 +618 -6.50176477432251 +619 -6.572261810302734 +620 -6.030294418334961 +621 -6.1602983474731445 +622 -7.025943756103516 +623 -5.750759601593018 +624 -6.430287837982178 +625 -6.555822372436523 +626 -5.9940185546875 +627 -6.114010810852051 +628 -6.595184326171875 +629 -6.185595512390137 +630 -6.010686874389648 +631 -6.228641033172607 +632 -6.299027919769287 +633 -6.224544525146484 +634 -6.60872220993042 +635 -6.158705711364746 +636 -6.137353897094727 +637 -5.903401851654053 +638 -6.578736305236816 +639 -5.973752975463867 +640 -6.513108730316162 +641 -6.079357147216797 +642 -6.301565170288086 +643 -6.092560291290283 +644 -6.0768632888793945 +645 -5.897031784057617 +646 -5.997508525848389 +647 -6.8762617111206055 +648 -6.653698921203613 +649 -6.111976623535156 +650 -6.304327964782715 +651 -6.1195478439331055 +652 -5.535238265991211 +653 -5.723516464233398 +654 -5.450411796569824 +655 -6.175771713256836 +656 -5.945003986358643 +657 -6.9034423828125 +658 -7.552550315856934 +659 -7.042308330535889 +660 -6.980930328369141 +661 -5.993536949157715 +662 -6.422492980957031 +663 -5.760951995849609 +664 -6.271821975708008 +665 -8.861909866333008 +666 -5.715144157409668 +667 -6.834677696228027 +668 -6.174781799316406 +669 -7.848386287689209 +670 -6.082919120788574 +671 -7.634238243103027 +672 -6.051810264587402 +673 -6.041529178619385 +674 -6.305295944213867 +675 -5.90633487701416 +676 -6.412741661071777 +677 -5.882315635681152 +678 -6.241926670074463 +679 -5.67778205871582 +680 -6.920296669006348 +681 -6.577727317810059 +682 -6.192865371704102 +683 -6.671334743499756 +684 -6.768184661865234 +685 -5.822035789489746 +686 -5.782768249511719 +687 -6.254261016845703 +688 -5.699968338012695 +689 -6.211568355560303 +690 -5.771151542663574 +691 -6.474553108215332 +692 -6.678554058074951 +693 -6.4699273109436035 +694 -6.326586723327637 +695 -7.331451416015625 +696 -6.223031044006348 +697 -6.495985984802246 +698 -6.2951250076293945 +699 -5.967083930969238 +700 -5.722494125366211 +701 -5.676231384277344 +702 -5.847560405731201 +703 -5.812419891357422 +704 -5.664209842681885 +705 -6.997591018676758 +706 -5.486222743988037 +707 -6.453377723693848 +708 -5.934382438659668 +709 -7.140514850616455 +710 -5.850358009338379 +711 -5.765175819396973 +712 -6.001755714416504 +713 -5.728944301605225 +714 -5.849210739135742 +715 -6.476551055908203 +716 -7.573486804962158 +717 -5.837264537811279 +718 -5.873879432678223 +719 -6.363165855407715 +720 -6.382688045501709 +721 -6.089352130889893 +722 -6.346688270568848 +723 -6.886911869049072 +724 -6.095605373382568 +725 -8.838692665100098 +726 -6.545417785644531 +727 -8.98538589477539 +728 -6.4626922607421875 +729 -7.310587406158447 +730 -6.761629581451416 +731 -6.311594009399414 +732 -8.603961944580078 +733 -6.308243751525879 +734 -5.821474552154541 +735 -6.453410625457764 +736 -8.222550392150879 +737 -6.170874118804932 +738 -6.126735687255859 +739 -6.289032936096191 +740 -6.24286413192749 +741 -6.1954731941223145 +742 -6.293363571166992 +743 -6.366123676300049 +744 -6.231409072875977 +745 -6.132113456726074 +746 -5.81991720199585 +747 -6.070521354675293 +748 -5.601280212402344 +749 -6.852383136749268 +750 -6.408202171325684 +751 -6.206845283508301 +752 -6.328245162963867 +753 -5.924075126647949 +754 -5.921818733215332 +755 -6.298253059387207 +756 -5.971883773803711 +757 -8.922310829162598 +758 -6.270387649536133 +759 -9.018701553344727 +760 -5.812974452972412 +761 -6.130641460418701 +762 -6.974058628082275 +763 -6.5948805809021 +764 -6.43129825592041 +765 -6.502565860748291 +766 -7.028055191040039 +767 -5.897031307220459 +768 -6.558971405029297 +769 -7.868524074554443 +770 -5.953925132751465 +771 -6.1638054847717285 +772 -7.470683574676514 +773 -6.09358024597168 +774 -5.822464466094971 +775 -5.574365615844727 +776 -7.345703601837158 +777 -6.051626682281494 +778 -6.235677242279053 +779 -6.053827285766602 +780 -5.864211082458496 +781 -6.204524993896484 +782 -6.380260944366455 +783 -6.0997724533081055 +784 -5.644716739654541 +785 -6.7989501953125 +786 -6.841445446014404 +787 -6.289032936096191 +788 -6.711008071899414 +789 -6.116814613342285 +790 -5.845738410949707 +791 -7.029945373535156 +792 -7.492811679840088 +793 -9.051900863647461 +794 -6.022797584533691 +795 -6.055707931518555 +796 -6.380989074707031 +797 -6.684103012084961 +798 -7.325785160064697 +799 -6.791959762573242 +800 -5.885241508483887 +801 -6.735965728759766 +802 -5.832648277282715 +803 -5.863130569458008 +804 -5.828059196472168 +805 -6.773612976074219 +806 -6.255561828613281 +807 -6.246756076812744 +808 -8.047590255737305 +809 -6.2555832862854 +810 -7.295813083648682 +811 -6.341983795166016 +812 -6.013909339904785 +813 -6.233728408813477 +814 -6.040297508239746 +815 -5.862359046936035 +816 -6.069845676422119 +817 -5.725578784942627 +818 -8.950509071350098 +819 -7.164671897888184 +820 -6.678109169006348 +821 -5.655113220214844 +822 -7.494091510772705 +823 -6.457180500030518 +824 -6.476085662841797 +825 -6.217205047607422 +826 -6.519714832305908 +827 -6.162303924560547 +828 -5.954651832580566 +829 -6.105484962463379 +830 -6.357421875 +831 -6.522215843200684 +832 -5.852785587310791 +833 -5.663931369781494 +834 -6.796169281005859 +835 -6.173096656799316 +836 -6.1198410987854 +837 -6.938303470611572 +838 -9.028018951416016 +839 -5.957390785217285 +840 -5.808971881866455 +841 -5.9912567138671875 +842 -5.880850791931152 +843 -6.066991329193115 +844 -7.457096099853516 +845 -6.595844268798828 +846 -6.042691230773926 +847 -6.162496566772461 +848 -6.159731864929199 +849 -6.496885776519775 +850 -5.531920433044434 +851 -5.885787010192871 +852 -5.976831436157227 +853 -6.4167160987854 +854 -5.9384965896606445 +855 -6.384714603424072 +856 -5.6029052734375 +857 -5.764646530151367 +858 -7.621591567993164 +859 -5.694120407104492 +860 -6.0359320640563965 +861 -8.458666801452637 +862 -7.202729225158691 +863 -7.787123203277588 +864 -6.257028579711914 +865 -6.37238883972168 +866 -5.899139404296875 +867 -5.913060188293457 +868 -5.764745235443115 +869 -6.235505104064941 +870 -6.181137561798096 +871 -5.313056468963623 +872 -7.247097015380859 +873 -6.327604293823242 +874 -6.215136528015137 +875 -6.671335220336914 +876 -5.764553546905518 +877 -5.863121032714844 +878 -5.904176712036133 +879 -6.145960807800293 +880 -6.14096736907959 +881 -6.433840274810791 +882 -5.861702919006348 +883 -8.357540130615234 +884 -5.99294376373291 +885 -6.301287651062012 +886 -6.305908679962158 +887 -6.404968738555908 +888 -5.660916805267334 +889 -5.648741722106934 +890 -6.275866508483887 +891 -5.6632256507873535 +892 -6.775638103485107 +893 -5.827068328857422 +894 -6.749810695648193 +895 -5.670848369598389 +896 -5.8788886070251465 +897 -6.534215450286865 +898 -6.119264602661133 +899 -5.780880451202393 +900 -6.6413726806640625 +901 -6.899953842163086 +902 -6.3766093254089355 +903 -5.885010719299316 +904 -7.818888187408447 +905 -8.586676597595215 +906 -6.7899699211120605 +907 -5.540557861328125 +908 -6.638160705566406 +909 -6.096731185913086 +910 -7.021349906921387 +911 -6.718380451202393 +912 -6.1333441734313965 +913 -6.581576347351074 +914 -6.4185261726379395 +915 -5.900995254516602 +916 -6.081063747406006 +917 -6.519725322723389 +918 -5.620876789093018 +919 -5.821130752563477 +920 -6.3179473876953125 +921 -5.876574516296387 +922 -5.849637985229492 +923 -5.965883255004883 +924 -5.89932107925415 +925 -6.03584623336792 +926 -6.206737518310547 +927 -5.598831653594971 +928 -6.654118537902832 +929 -5.884317398071289 +930 -7.065759658813477 +931 -6.716894626617432 +932 -5.972043037414551 +933 -5.773114204406738 +934 -6.352138519287109 +935 -6.177887916564941 +936 -5.670848846435547 +937 -6.00008487701416 +938 -6.22566032409668 +939 -6.224726676940918 +940 -5.695813179016113 +941 -6.289032936096191 +942 -5.680161476135254 +943 -6.143610000610352 +944 -7.137289524078369 +945 -6.82605504989624 +946 -5.866661071777344 +947 -6.077924728393555 +948 -6.3452253341674805 +949 -6.356173515319824 +950 -5.74674129486084 +951 -5.917694568634033 +952 -5.868264198303223 +953 -6.848014831542969 +954 -5.5449113845825195 +955 -6.005123138427734 +956 -6.692074775695801 +957 -5.75406551361084 +958 -5.738658905029297 +959 -6.275951385498047 +960 -6.88272762298584 +961 -6.155731201171875 +962 -7.083715438842773 +963 -6.297204494476318 +964 -6.099371433258057 +965 -5.723237991333008 +966 -6.133114814758301 +967 -6.881274700164795 +968 -5.540557384490967 +969 -6.01681661605835 +970 -6.140902519226074 +971 -6.40484094619751 +972 -6.241222381591797 +973 -5.829936981201172 +974 -7.4493408203125 +975 -6.225032329559326 +976 -6.597903251647949 +977 -5.938767910003662 +978 -6.38035249710083 +979 -6.379406929016113 +980 -8.992624282836914 +981 -6.438797950744629 +982 -6.365108489990234 +983 -6.118430137634277 +984 -5.767266273498535 +985 -7.334374904632568 +986 -6.087532997131348 +987 -6.182542324066162 +988 -6.3076019287109375 +989 -6.207075119018555 +990 -7.029979228973389 +991 -5.992142200469971 +992 -6.724290370941162 +993 -5.588849067687988 +994 -5.981490612030029 +995 -6.106056213378906 +996 -6.832730293273926 +997 -6.870969772338867 +998 -6.462491989135742 +999 -6.008170127868652 diff --git a/example/python_pkg/C_learn/DRAFFLE/DOutput/rlxd_structures_seed0.traj b/example/python_pkg/C_learn/DRAFFLE/DOutput/rlxd_structures_seed0.traj new file mode 100644 index 00000000..44059a1f Binary files /dev/null and b/example/python_pkg/C_learn/DRAFFLE/DOutput/rlxd_structures_seed0.traj differ diff --git a/example/python_pkg/C_learn/DRAFFLE/DOutput/unrlxd_structures_seed0.traj b/example/python_pkg/C_learn/DRAFFLE/DOutput/unrlxd_structures_seed0.traj new file mode 100644 index 00000000..4403428c Binary files /dev/null and b/example/python_pkg/C_learn/DRAFFLE/DOutput/unrlxd_structures_seed0.traj differ diff --git a/example/python_pkg/C_learn/DRAFFLE/analyse_structures.py b/example/python_pkg/C_learn/DRAFFLE/analyse_structures.py index 3f51e613..b0a665cf 100644 --- a/example/python_pkg/C_learn/DRAFFLE/analyse_structures.py +++ b/example/python_pkg/C_learn/DRAFFLE/analyse_structures.py @@ -70,7 +70,7 @@ # %% for seed in range(1): for rlxd_string in ["unrlxd", "rlxd"]: - structures = read("DTMP/"+rlxd_string+"_structures_seed"+str(seed)+".traj", index=":") + structures = read("DOutput/"+rlxd_string+"_structures_seed"+str(seed)+".traj", index=":") for structure in structures: structure.calc = calc @@ -142,12 +142,10 @@ # %% plt.figure(figsize=(10, 6)) plt.scatter(X_reduced[:, 0], X_reduced[:, 1], c=delta_en_per_atom_pca, cmap="viridis") - plt.xlabel('Principal Component 1') - plt.ylabel('Principal Component 2') + plt.xlabel('Principal component 1') + plt.ylabel('Principal component 2') plt.title('PCA of Unique Structures ('+rlxd_string+', seed'+str(seed)+')') plt.xlim(-6, 10) plt.ylim(-6, 10) plt.colorbar(label='Energy above diamond (eV/atom)') plt.savefig('RAFFLE_pca_unique_structures_'+rlxd_string+'_seed'+str(seed)+'.png') - - diff --git a/example/python_pkg/C_learn/DRAFFLE/learn.py b/example/python_pkg/C_learn/DRAFFLE/learn.py index b94681b1..f8bc336a 100644 --- a/example/python_pkg/C_learn/DRAFFLE/learn.py +++ b/example/python_pkg/C_learn/DRAFFLE/learn.py @@ -1,4 +1,5 @@ from chgnet.model import CHGNetCalculator +from ase.calculators.singlepoint import SinglePointCalculator from raffle.generator import raffle_generator from ase import build, Atoms from ase.optimize import FIRE @@ -11,11 +12,11 @@ logging.basicConfig(level=logging.DEBUG) # Function to relax a structure -def process_structure(i, atoms, num_structures_old, calc_params, optimise_structure, iteration): +def process_structure(i, atoms, num_structures_old, calc_params, optimise_structure, iteration, calc): # Check if the structure has already been processed if i < num_structures_old: return None, None, None - + # calc = Vasp(**calc_params, label=f"struct{i}", directory=f"iteration{iteration}/struct{i}/", txt=f"stdout{i}.o") inew = i - num_structures_old atoms.calc = calc @@ -32,7 +33,7 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct except Exception as e: print(f"Optimisation failed: {e}") return None, None, None - + # Save the optimised structure and its energy per atom energy_rlxd = atoms.get_potential_energy() / len(atoms) @@ -46,11 +47,11 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct if distances.min() < 1.0: print(f"Distance too small: {atoms.get_all_distances(mic=True).min()}") return None, None, None - + if abs(energy_rlxd - energy_unrlxd) > 10.0: print(f"Energy difference too large: {energy_rlxd} vs {energy_unrlxd}") return None, None, None - + return atoms, energy_unrlxd, energy_rlxd @@ -89,7 +90,7 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct # Loop over random seeds for seed in range(20): print(f"Seed: {seed}") - + # set up file names energies_rlxd_filename = f"energies_rlxd_seed{seed}.txt" energies_unrlxd_filename = f"energies_unrlxd_seed{seed}.txt" @@ -138,7 +139,7 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct num_structures = 5, stoichiometry = { 'C': num_atoms }, seed = seed*1000+iter, - method_probab = {"void": 0.5, "rand": 0.001, "walk": 0.5, "grow": 0.0, "min": 1.0}, + method_ratio = {"void": 0.5, "rand": 0.001, "walk": 0.5, "grow": 0.0, "min": 1.0}, verbose = 0, ) @@ -160,7 +161,12 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct write(iterdir+f"POSCAR_unrlxd_{i}", generated_structures[num_structures_old + i]) print(f"Structure {i} energy per atom: {generated_structures[num_structures_old + i].get_potential_energy() / len(generated_structures[num_structures_old + i])}") unrlxd_structures.append(generated_structures[num_structures_old + i].copy()) - + unrlxd_structures[-1].calc = SinglePointCalculator( + generated_structures[num_structures_old + i], + energy=generated_structures[num_structures_old + i].get_potential_energy(), + forces=generated_structures[num_structures_old + i].get_forces() + ) + # Start parallel execution print("Starting parallel execution") results = Parallel(n_jobs=5)( @@ -170,11 +176,16 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct # Wait for all futures to complete for j, result in enumerate(results): - generated_structures[j+num_structures_old], energy_unrlxd[j], energy_rlxd[j] = result - if generated_structures[j+num_structures_old] is None: + generated_structures[num_structures_old + j], energy_unrlxd[j], energy_rlxd[j] = result + if generated_structures[num_structures_old + j] is None: print("Structure failed the checks") continue - rlxd_structures.append(generated_structures[j+num_structures_old].copy()) + rlxd_structures.append(generated_structures[num_structures_old + j].copy()) + rlxd_structures[-1].calc = SinglePointCalculator( + generated_structures[j+num_structures_old], + energy=generated_structures[num_structures_old + j].get_potential_energy(), + forces=generated_structures[num_structures_old + j].get_forces() + ) print("All futures completed") # Remove structures that failed the checks @@ -186,7 +197,7 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct del unrlxd_structures[j] del rlxd_structures[j] generator.remove_structure(j) - num_structures_new = len(generated_structures) + num_structures_new = len(generated_structures) # write the structures to files for i in range(num_structures_new - num_structures_old): @@ -235,4 +246,4 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct write(f"rlxd_structures_seed{seed}.traj", rlxd_structures) print("All generated and relaxed structures written") - print("Learning complete") \ No newline at end of file + print("Learning complete") diff --git a/example/python_pkg/C_learn/DRAFFLE/pca.ipynb b/example/python_pkg/C_learn/DRAFFLE/pca.ipynb index 2c490fb9..714bf7be 100644 --- a/example/python_pkg/C_learn/DRAFFLE/pca.ipynb +++ b/example/python_pkg/C_learn/DRAFFLE/pca.ipynb @@ -19,7 +19,8 @@ "from agox.utils.graph_sorting import Analysis\n", "\n", "import numpy as np\n", - "from sklearn.decomposition import PCA" + "from sklearn.decomposition import PCA\n", + "from matplotlib.ticker import (MultipleLocator, AutoMinorLocator)" ] }, { @@ -93,7 +94,7 @@ "outputs": [], "source": [ "## Load the unrelaxed structures\n", - "unrlxd_structures = read(\"DTMP\"+identifier+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "unrlxd_structures = read(\"DOutput\"+identifier+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", "for structure in unrlxd_structures:\n", " structure.calc = calc" ] @@ -105,7 +106,7 @@ "outputs": [], "source": [ "## Load the relaxed structures\n", - "rlxd_structures = read(\"DTMP\"+identifier+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "rlxd_structures = read(\"DOutput\"+identifier+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", "for structure in rlxd_structures:\n", " structure.calc = calc" ] @@ -118,7 +119,7 @@ "source": [ "# read energies from energies_unrlxd_seed0.txt and add to the respective structures using a SinglePointCalculator\n", "# the file has the form \"index energy\"\n", - "filename = \"DTMP\"+identifier+\"/energies_unrlxd_seed\"+str(seed)+\".txt\"\n", + "filename = \"DOutput\"+identifier+\"/energies_unrlxd_seed\"+str(seed)+\".txt\"\n", "with open(filename) as f:\n", " for line in f:\n", " index, energy = line.split()\n", @@ -127,7 +128,7 @@ " unrlxd_structures[index].calc = SinglePointCalculator(unrlxd_structures[index], energy=energy * len(unrlxd_structures[index]))\n", "\n", "\n", - "filename = \"DTMP\"+identifier+\"/energies_rlxd_seed\"+str(seed)+\".txt\"\n", + "filename = \"DOutput\"+identifier+\"/energies_rlxd_seed\"+str(seed)+\".txt\"\n", "with open(filename) as f:\n", " for line in f:\n", " index, energy = line.split()\n", @@ -199,7 +200,7 @@ "source": [ "## Save pca model\n", "import pickle\n", - "if True:\n", + "if False:\n", " pca.fit(np.squeeze([arr for arr in descriptor.get_features(rlxd_structures)]))\n", " with open(\"pca_model\"+identifier+\"_all_rlxd_\"+str(seed)+\".pkl\", \"wb\") as f:\n", " pickle.dump(pca, f)\n", @@ -253,34 +254,29 @@ "for ax in axes:\n", " ax.scatter(rlxd_X_reduced[min_energy_index, 0], rlxd_X_reduced[min_energy_index, 1], s=200, edgecolor='red', facecolor='none', linewidth=2, label='diamond')\n", " if ax == axes[1]:\n", - " ax.legend(fontsize=10)\n", " handles, labels = ax.get_legend_handles_labels()\n", - " ax.legend(handles[::-1], labels[::-1], facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, loc='upper right')\n", + " ax.legend(handles[::-1], labels[::-1], facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, loc='upper right', fontsize=20, handletextpad=0.1)\n", "\n", "## Add labels\n", - "fig.text(0.5, 0.04, 'Principal Component 1', ha='center', fontsize=15)\n", - "axes[0].set_ylabel('Principal Component 2', fontsize=15)\n", - "axes[0].set_title('Unrelaxed')\n", - "axes[1].set_title('Relaxed')\n", - "if identifier == \"_VASP\":\n", - " if rlxd_string == \"rlxd\":\n", + "fig.text(0.5, 0.0, 'Principal component 1', ha='center', fontsize=20)\n", + "axes[0].set_ylabel('Principal component 2', fontsize=20)\n", + "axes[0].set_title('Unrelaxed', fontsize=20)\n", + "axes[1].set_title('Relaxed', fontsize=20)\n", + "if rlxd_string == \"rlxd\":\n", " xlims = [-11, 8]\n", " ylims = [-5, 6]\n", - " else:\n", - " xlims = [-9, 13]\n", - " ylims = [-7, 12]\n", "else:\n", - " if rlxd_string == \"rlxd\":\n", - " xlims = [-11, 8]\n", - " ylims = [-5, 6]\n", - " else:\n", " xlims = [-5, 13]\n", " ylims = [-6.5, 13]\n", "\n", "for ax in axes:\n", - " ax.tick_params(axis='both', direction='in')\n", - " ax.set_xlim(xlims)\n", - " ax.set_ylim(ylims)\n", + " ax.tick_params(axis='both', direction='in', length=6, labelsize=20)\n", + " ax.yaxis.set_major_locator(MultipleLocator(3))\n", + " ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.xaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.tick_params(axis='both', which='minor', length=3, direction='in')\n", + " ax.set_xlim(xlims)\n", + " ax.set_ylim(ylims)\n", "\n", "## Unify tick labels\n", "xticks = axes[0].get_xticks()\n", @@ -299,7 +295,10 @@ "\n", "## Add colorbar next to the axes\n", "cbar = fig.colorbar(axes[1].collections[0], ax=axes, orientation='vertical', fraction=0.085, pad=0.02)\n", - "cbar.set_label('Formation energy (eV/atom)', fontsize=15)\n", + "cbar.ax.tick_params(labelsize=20)\n", + "cbar.ax.yaxis.set_major_locator(MultipleLocator(1))\n", + "cbar.ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + "cbar.set_label('Formation energy (eV/atom)', fontsize=20)\n", "\n", "## Save the figure\n", "plt.savefig('C_RAFFLE'+identifier+'_pca_'+rlxd_string+'_fit_seed'+str(seed)+'.pdf', bbox_inches='tight', pad_inches=0, facecolor=fig.get_facecolor(), edgecolor='none')" diff --git a/example/python_pkg/C_learn/DRSS/DOutput/rlxd_structures_seed0.traj b/example/python_pkg/C_learn/DRSS/DOutput/rlxd_structures_seed0.traj new file mode 100644 index 00000000..d09476e1 Binary files /dev/null and b/example/python_pkg/C_learn/DRSS/DOutput/rlxd_structures_seed0.traj differ diff --git a/example/python_pkg/C_learn/DRSS/DOutput/unrlxd_structures_seed0.traj b/example/python_pkg/C_learn/DRSS/DOutput/unrlxd_structures_seed0.traj new file mode 100644 index 00000000..8dc2988f Binary files /dev/null and b/example/python_pkg/C_learn/DRSS/DOutput/unrlxd_structures_seed0.traj differ diff --git a/example/python_pkg/C_learn/DRSS/analyse_structures.py b/example/python_pkg/C_learn/DRSS/analyse_structures.py index 1975ff65..1d3ba6c8 100644 --- a/example/python_pkg/C_learn/DRSS/analyse_structures.py +++ b/example/python_pkg/C_learn/DRSS/analyse_structures.py @@ -59,7 +59,7 @@ # %% for seed in range(1): for rlxd_string in ["unrlxd", "rlxd"]: - structures = read("DTMP/"+rlxd_string+"_structures_seed"+str(seed)+".traj", index=":") + structures = read("DOutput/"+rlxd_string+"_structures_seed"+str(seed)+".traj", index=":") for structure in structures: structure.calc = calc @@ -131,13 +131,10 @@ # %% plt.figure(figsize=(10, 6)) plt.scatter(X_reduced[:, 0], X_reduced[:, 1], c=delta_en_per_atom_pca, cmap="viridis") - plt.xlabel('Principal Component 1') - plt.ylabel('Principal Component 2') + plt.xlabel('Principal component 1') + plt.ylabel('Principal component 2') plt.title('PCA of Unique Structures ('+rlxd_string+', seed'+str(seed)+')') plt.xlim(-6, 10) plt.ylim(-6, 10) plt.colorbar(label='Energy above diamond (eV/atom)') plt.savefig('RSS_pca_unique_structures_'+rlxd_string+'_seed'+str(seed)+'.png') - - - diff --git a/example/python_pkg/C_learn/DRSS/pca.ipynb b/example/python_pkg/C_learn/DRSS/pca.ipynb index 1edc1e3f..cbbefa15 100644 --- a/example/python_pkg/C_learn/DRSS/pca.ipynb +++ b/example/python_pkg/C_learn/DRSS/pca.ipynb @@ -19,7 +19,8 @@ "from agox.utils.graph_sorting import Analysis\n", "\n", "import numpy as np\n", - "from sklearn.decomposition import PCA" + "from sklearn.decomposition import PCA\n", + "from matplotlib.ticker import (MultipleLocator, AutoMinorLocator)" ] }, { @@ -43,7 +44,7 @@ "source": [ "## Set the plotting parameters\n", "seed = 0\n", - "identifier = \"\"\n", + "identifier = \"_VASP\"\n", "# min_energy = -9.064090728759766" ] }, @@ -92,7 +93,7 @@ "outputs": [], "source": [ "## Load the unrelaxed structures\n", - "unrlxd_structures = read(\"DTMP\"+identifier+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "unrlxd_structures = read(\"DOutput\"+identifier+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", "# for structure in unrlxd_structures:\n", "# structure.calc = calc" ] @@ -104,7 +105,7 @@ "outputs": [], "source": [ "## Load the relaxed structures\n", - "rlxd_structures = read(\"DTMP\"+identifier+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "rlxd_structures = read(\"DOutput\"+identifier+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", "# for structure in rlxd_structures:\n", "# structure.calc = calc" ] @@ -216,34 +217,30 @@ "for ax in axes:\n", " ax.scatter(rlxd_X_reduced[min_energy_index, 0], rlxd_X_reduced[min_energy_index, 1], s=200, edgecolor='red', facecolor='none', linewidth=2, label='diamond')\n", " if ax == axes[1]:\n", - " ax.legend(fontsize=10)\n", " handles, labels = ax.get_legend_handles_labels()\n", - " ax.legend(handles[::-1], labels[::-1], facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, loc='upper right')\n", + " ax.legend(handles[::-1], labels[::-1], facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, loc='upper right', fontsize=20, handletextpad=0.1)\n", + " \n", "\n", "## Add labels\n", - "fig.text(0.5, 0.04, 'Principal Component 1', ha='center', fontsize=15)\n", - "axes[0].set_ylabel('Principal Component 2', fontsize=15)\n", + "fig.text(0.5, 0.0, 'Principal component 1', ha='center', fontsize=20)\n", + "axes[0].set_ylabel('Principal component 2', fontsize=20)\n", "axes[0].set_title('Unrelaxed')\n", "axes[1].set_title('Relaxed')\n", - "if identifier == \"_VASP\":\n", - " if rlxd_string == \"rlxd\":\n", + "if rlxd_string == \"rlxd\":\n", " xlims = [-11, 8]\n", " ylims = [-5, 6]\n", - " else:\n", - " xlims = [-9, 13]\n", - " ylims = [-7, 12]\n", "else:\n", - " if rlxd_string == \"rlxd\":\n", - " xlims = [-11, 8]\n", - " ylims = [-5, 6]\n", - " else:\n", " xlims = [-5, 13]\n", " ylims = [-6.5, 13]\n", "\n", "for ax in axes:\n", - " ax.tick_params(axis='both', direction='in')\n", - " ax.set_xlim(xlims)\n", - " ax.set_ylim(ylims)\n", + " ax.tick_params(axis='both', direction='in', length=6, labelsize=20)\n", + " ax.yaxis.set_major_locator(MultipleLocator(3))\n", + " ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.xaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.tick_params(axis='both', which='minor', length=3, direction='in')\n", + " ax.set_xlim(xlims)\n", + " ax.set_ylim(ylims)\n", "\n", "## Unify tick labels\n", "xticks = axes[0].get_xticks()\n", @@ -262,11 +259,21 @@ "\n", "## Add colorbar next to the axes\n", "cbar = fig.colorbar(axes[1].collections[0], ax=axes, orientation='vertical', fraction=0.085, pad=0.02)\n", - "cbar.set_label('Formation energy (eV/atom)', fontsize=15)\n", + "cbar.ax.tick_params(labelsize=20)\n", + "cbar.ax.yaxis.set_major_locator(MultipleLocator(1))\n", + "cbar.ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + "cbar.set_label('Formation energy (eV/atom)', fontsize=20)\n", "\n", "## Save the figure\n", "plt.savefig('C_RSS'+identifier+'_pca_'+rlxd_string+'_fit_seed'+str(seed)+'.pdf', bbox_inches='tight', pad_inches=0, facecolor=fig.get_facecolor(), edgecolor='none')" ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [] } ], "metadata": { diff --git a/example/python_pkg/C_learn/Dgraphite_diamond/DOutput/energies_rlxd_seed0.txt b/example/python_pkg/C_learn/Dgraphite_diamond/DOutput/energies_rlxd_seed0.txt new file mode 100644 index 00000000..86c17d8c --- /dev/null +++ b/example/python_pkg/C_learn/Dgraphite_diamond/DOutput/energies_rlxd_seed0.txt @@ -0,0 +1,500 @@ +0 -7.874802589416504 +1 -8.700008392333984 +2 -9.182032585144043 +3 -9.069253921508789 +4 -8.445944786071777 +5 -8.363354682922363 +6 -8.707109451293945 +7 -8.55386734008789 +8 -8.584236145019531 +9 -8.691285133361816 +10 -8.215776443481445 +11 -9.182581901550293 +12 -8.177414894104004 +13 -9.180092811584473 +14 -8.224401473999023 +15 -8.172952651977539 +16 -9.137910842895508 +17 -8.710933685302734 +18 -8.532837867736816 +19 -8.426910400390625 +20 -8.48315715789795 +21 -9.181977272033691 +22 -8.255414962768555 +23 -8.019391059875488 +24 -7.653284549713135 +25 -8.176793098449707 +26 -8.701663970947266 +27 -8.552902221679688 +28 -8.706374168395996 +29 -8.01476001739502 +30 -8.046297073364258 +31 -8.703105926513672 +32 -7.919553756713867 +33 -8.329421997070312 +34 -9.138045310974121 +35 -8.290478706359863 +36 -8.58635425567627 +37 -8.705853462219238 +38 -8.175359725952148 +39 -8.535114288330078 +40 -8.534997940063477 +41 -9.138113021850586 +42 -8.224552154541016 +43 -8.553948402404785 +44 -8.046698570251465 +45 -7.909087181091309 +46 -8.191583633422852 +47 -9.181910514831543 +48 -8.176012992858887 +49 -8.189706802368164 +50 -9.137493133544922 +51 -7.965442180633545 +52 -8.55647087097168 +53 -8.529834747314453 +54 -9.138099670410156 +55 -7.9139084815979 +56 -9.138030052185059 +57 -8.554851531982422 +58 -8.555729866027832 +59 -9.178314208984375 +60 -9.18213939666748 +61 -9.181699752807617 +62 -8.530017852783203 +63 -9.18213939666748 +64 -8.332253456115723 +65 -9.18088150024414 +66 -8.036388397216797 +67 -8.55441665649414 +68 -9.138090133666992 +69 -8.150213241577148 +70 -8.534530639648438 +71 -7.759971618652344 +72 -8.177231788635254 +73 -8.07270622253418 +74 -8.176338195800781 +75 -7.803803443908691 +76 -7.741310119628906 +77 -8.531538963317871 +78 -8.373177528381348 +79 -8.702783584594727 +80 -8.58495807647705 +81 -9.182279586791992 +82 -8.281750679016113 +83 -7.769044399261475 +84 -8.33297348022461 +85 -8.554762840270996 +86 -9.180364608764648 +87 -7.689544677734375 +88 -9.182299613952637 +89 -9.182339668273926 +90 -8.17989444732666 +91 -8.554941177368164 +92 -7.766148090362549 +93 -9.138050079345703 +94 -8.552824020385742 +95 -8.327567100524902 +96 -9.137128829956055 +97 -8.439888954162598 +98 -9.180567741394043 +99 -8.414105415344238 +100 -8.177762985229492 +101 -9.180259704589844 +102 -8.313262939453125 +103 -8.555095672607422 +104 -8.535144805908203 +105 -8.181132316589355 +106 -9.182021141052246 +107 -8.535090446472168 +108 -9.180826187133789 +109 -9.182390213012695 +110 -8.167052268981934 +111 -8.534802436828613 +112 -8.548222541809082 +113 -9.13061237335205 +114 -7.970263957977295 +115 -8.507577896118164 +116 -7.977787971496582 +117 -7.876727104187012 +118 -8.710552215576172 +119 -8.532549858093262 +120 -7.746337890625 +121 -8.555209159851074 +122 -9.180192947387695 +123 -8.554110527038574 +124 -9.182315826416016 +125 -8.555584907531738 +126 -8.532674789428711 +127 -8.699102401733398 +128 -8.55321216583252 +129 -8.28201675415039 +130 -9.080124855041504 +131 -8.71194839477539 +132 -8.556342124938965 +133 -9.175802230834961 +134 -9.182513236999512 +135 -9.182541847229004 +136 -9.182629585266113 +137 -9.182580947875977 +138 -9.177474975585938 +139 -8.53437614440918 +140 -8.53403091430664 +141 -7.95330286026001 +142 -8.217447280883789 +143 -8.01370620727539 +144 -8.708102226257324 +145 -9.180418968200684 +146 -8.327499389648438 +147 -8.534353256225586 +148 -8.117856979370117 +149 -9.181097984313965 +150 -9.182743072509766 +151 -8.702118873596191 +152 -9.138077735900879 +153 -8.081853866577148 +154 -8.435635566711426 +155 -8.706955909729004 +156 -8.325594902038574 +157 -8.340533256530762 +158 -8.269538879394531 +159 -8.532530784606934 +160 -9.181463241577148 +161 -9.18053913116455 +162 -8.525288581848145 +163 -7.772726058959961 +164 -8.258329391479492 +165 -7.750502586364746 +166 -9.18270206451416 +167 -7.805087089538574 +168 -7.753687381744385 +169 -7.918637275695801 +170 -8.437520027160645 +171 -7.881850719451904 +172 -8.555794715881348 +173 -8.709779739379883 +174 -7.771698474884033 +175 -8.022178649902344 +176 -8.701336860656738 +177 -7.748412132263184 +178 -8.535040855407715 +179 -8.532988548278809 +180 -9.078936576843262 +181 -9.182281494140625 +182 -7.607821464538574 +183 -8.092323303222656 +184 -7.794521331787109 +185 -8.700119972229004 +186 -7.802603244781494 +187 -8.55336856842041 +188 -8.711277961730957 +189 -8.707738876342773 +190 -8.703132629394531 +191 -9.079705238342285 +192 -8.656771659851074 +193 -8.555854797363281 +194 -8.69921875 +195 -8.217436790466309 +196 -8.27392292022705 +197 -8.56100845336914 +198 -7.898947715759277 +199 -7.889174938201904 +200 -8.604559898376465 +201 -8.711190223693848 +202 -7.575983047485352 +203 -8.534642219543457 +204 -7.956300735473633 +205 -7.938676834106445 +206 -7.981297016143799 +207 -9.181589126586914 +208 -8.047124862670898 +209 -7.875249862670898 +210 -8.526861190795898 +211 -7.7572832107543945 +212 -9.180272102355957 +213 -8.696426391601562 +214 -8.683050155639648 +215 -7.769588470458984 +216 -7.638854026794434 +217 -9.179451942443848 +218 -8.577098846435547 +219 -9.182694435119629 +220 -9.180261611938477 +221 -8.44754695892334 +222 -8.334239959716797 +223 -9.182354927062988 +224 -7.824788570404053 +225 -8.3732271194458 +226 -8.405739784240723 +227 -8.181560516357422 +228 -9.180703163146973 +229 -9.18039608001709 +230 -7.6378703117370605 +231 -8.554484367370605 +232 -9.181242942810059 +233 -8.702606201171875 +234 -7.876440048217773 +235 -7.772895812988281 +236 -9.180137634277344 +237 -8.173130989074707 +238 -8.532177925109863 +239 -9.180801391601562 +240 -8.547064781188965 +241 -8.38403034210205 +242 -8.180800437927246 +243 -7.992019176483154 +244 -9.138062477111816 +245 -8.116147994995117 +246 -8.584463119506836 +247 -8.038355827331543 +248 -9.180168151855469 +249 -9.064809799194336 +250 -7.570407867431641 +251 -9.064083099365234 +252 -7.707298755645752 +253 -7.587961196899414 +254 -8.113285064697266 +255 -7.52957010269165 +256 -7.622230052947998 +257 -8.11328125 +258 -7.799969673156738 +259 -7.598707675933838 +260 -9.064085960388184 +261 -7.739596366882324 +262 -7.717671871185303 +263 -7.478142261505127 +264 -7.532944202423096 +265 -9.064065933227539 +266 -7.837854862213135 +267 -7.169259548187256 +268 -7.20573616027832 +269 -9.064062118530273 +270 -7.717763900756836 +271 -7.8990397453308105 +272 -8.007972717285156 +273 -7.798737525939941 +274 -7.796828746795654 +275 -7.672041416168213 +276 -8.00781536102295 +277 -9.036075592041016 +278 -7.534840106964111 +279 -7.403115272521973 +280 -7.645266532897949 +281 -7.587969779968262 +282 -7.737827777862549 +283 -9.06407356262207 +284 -7.481308937072754 +285 -7.529773235321045 +286 -8.108539581298828 +287 -7.946150302886963 +288 -9.063979148864746 +289 -9.064080238342285 +290 -7.902985095977783 +291 -9.06404972076416 +292 -9.064080238342285 +293 -7.690720558166504 +294 -9.064085006713867 +295 -7.642459392547607 +296 -7.649534702301025 +297 -7.704215049743652 +298 -9.064065933227539 +299 -9.064033508300781 +300 -8.007914543151855 +301 -9.064070701599121 +302 -7.780004978179932 +303 -7.837853908538818 +304 -8.06003475189209 +305 -7.540858745574951 +306 -9.064079284667969 +307 -9.064081192016602 +308 -9.064048767089844 +309 -7.8855061531066895 +310 -7.556260108947754 +311 -7.849704265594482 +312 -7.472034454345703 +313 -9.064071655273438 +314 -9.064048767089844 +315 -7.6768364906311035 +316 -7.614336967468262 +317 -7.905422210693359 +318 -9.029390335083008 +319 -7.738017559051514 +320 -9.064085006713867 +321 -7.515861511230469 +322 -9.064057350158691 +323 -7.89337682723999 +324 -7.897469997406006 +325 -9.064080238342285 +326 -8.059998512268066 +327 -7.570154190063477 +328 -7.629839897155762 +329 -7.606199264526367 +330 -8.11328125 +331 -7.60648775100708 +332 -9.064047813415527 +333 -7.67673921585083 +334 -7.530759811401367 +335 -8.113042831420898 +336 -9.064074516296387 +337 -7.947183609008789 +338 -7.8378586769104 +339 -7.6367716789245605 +340 -8.060042381286621 +341 -7.915335655212402 +342 -8.059349060058594 +343 -9.064062118530273 +344 -7.739648342132568 +345 -7.864784240722656 +346 -7.804868698120117 +347 -7.837834358215332 +348 -9.064085006713867 +349 -7.602251052856445 +350 -8.113288879394531 +351 -7.782646656036377 +352 -7.598203182220459 +353 -8.113293647766113 +354 -7.461287975311279 +355 -9.064064025878906 +356 -7.898471355438232 +357 -7.605252742767334 +358 -9.064054489135742 +359 -7.739680767059326 +360 -9.063946723937988 +361 -7.905354022979736 +362 -7.9053778648376465 +363 -7.802624702453613 +364 -7.8647871017456055 +365 -7.990181922912598 +366 -7.566337585449219 +367 -7.688294887542725 +368 -7.532877445220947 +369 -9.064054489135742 +370 -7.5491743087768555 +371 -7.98347806930542 +372 -7.864801406860352 +373 -9.064079284667969 +374 -7.837832450866699 +375 -7.732754707336426 +376 -7.7219719886779785 +377 -7.5203728675842285 +378 -9.064057350158691 +379 -7.500679969787598 +380 -7.804878234863281 +381 -9.064031600952148 +382 -9.06406307220459 +383 -7.5592451095581055 +384 -7.551187038421631 +385 -9.064064979553223 +386 -7.306140422821045 +387 -7.46463680267334 +388 -9.064082145690918 +389 -9.064085960388184 +390 -8.007878303527832 +391 -9.064058303833008 +392 -7.915650367736816 +393 -9.064085960388184 +394 -7.375304222106934 +395 -9.06406307220459 +396 -7.5756402015686035 +397 -9.064081192016602 +398 -7.336781024932861 +399 -9.06407642364502 +400 -7.687815189361572 +401 -7.72197151184082 +402 -7.528569221496582 +403 -9.06392765045166 +404 -9.064080238342285 +405 -7.915646076202393 +406 -7.798728942871094 +407 -7.278672695159912 +408 -9.063854217529297 +409 -8.007818222045898 +410 -7.4249267578125 +411 -7.475232124328613 +412 -9.063497543334961 +413 -7.739630699157715 +414 -7.606107234954834 +415 -8.11329174041748 +416 -9.063794136047363 +417 -8.039814949035645 +418 -7.476139545440674 +419 -7.915623664855957 +420 -7.658973217010498 +421 -7.739755630493164 +422 -7.632510185241699 +423 -7.804873943328857 +424 -7.837814807891846 +425 -7.83541202545166 +426 -7.725347995758057 +427 -7.813016891479492 +428 -7.520580291748047 +429 -7.413750171661377 +430 -7.734142303466797 +431 -9.064074516296387 +432 -9.064019203186035 +433 -7.2170305252075195 +434 -7.779994964599609 +435 -9.064083099365234 +436 -7.540946006774902 +437 -8.113274574279785 +438 -7.586679458618164 +439 -7.51481819152832 +440 -7.5123820304870605 +441 -7.748267650604248 +442 -7.905398845672607 +443 -7.746760368347168 +444 -7.779972076416016 +445 -9.064068794250488 +446 -7.899105548858643 +447 -7.5496063232421875 +448 -9.064082145690918 +449 -7.645195484161377 +450 -7.58665132522583 +451 -7.53570032119751 +452 -7.915439128875732 +453 -7.40280294418335 +454 -9.060314178466797 +455 -7.994205474853516 +456 -7.9447150230407715 +457 -9.064079284667969 +458 -7.864802360534668 +459 -9.064065933227539 +460 -8.113286018371582 +461 -9.064077377319336 +462 -8.059856414794922 +463 -7.711949825286865 +464 -7.837860584259033 +465 -7.402801513671875 +466 -9.064071655273438 +467 -7.476136207580566 +468 -7.449477195739746 +469 -7.864799499511719 +470 -9.064042091369629 +471 -9.062023162841797 +472 -7.681192874908447 +473 -7.642000198364258 +474 -7.906321048736572 +475 -7.632054805755615 +476 -7.675365924835205 +477 -7.549695014953613 +478 -9.064080238342285 +479 -9.064081192016602 +480 -7.473783493041992 +481 -7.738165378570557 +482 -7.707295894622803 +483 -9.064083099365234 +484 -7.581000328063965 +485 -7.905224800109863 +486 -9.064064025878906 +487 -7.298761367797852 +488 -7.473809242248535 +489 -7.661844253540039 +490 -7.432984352111816 +491 -8.05958080291748 +492 -7.628215312957764 +493 -7.475241184234619 +494 -7.658933639526367 +495 -7.587500095367432 +496 -7.655853748321533 +497 -9.064062118530273 +498 -7.587499618530273 +499 -7.475045204162598 diff --git a/example/python_pkg/C_learn/Dgraphite_diamond/DOutput/energies_unrlxd_seed0.txt b/example/python_pkg/C_learn/Dgraphite_diamond/DOutput/energies_unrlxd_seed0.txt new file mode 100644 index 00000000..76f0b4ed --- /dev/null +++ b/example/python_pkg/C_learn/Dgraphite_diamond/DOutput/energies_unrlxd_seed0.txt @@ -0,0 +1,500 @@ +0 -4.733189582824707 +1 -4.520680904388428 +2 -4.13666296005249 +3 -4.051826000213623 +4 -4.111903190612793 +5 -6.080687522888184 +6 -6.9031219482421875 +7 -7.407827377319336 +8 -7.448488235473633 +9 -7.555734634399414 +10 -7.78084135055542 +11 -6.47303581237793 +12 -6.630053520202637 +13 -7.076043605804443 +14 -5.9767608642578125 +15 -6.70262336730957 +16 -6.136425971984863 +17 -6.902203559875488 +18 -6.579823970794678 +19 -6.646846771240234 +20 -6.127269268035889 +21 -7.497905254364014 +22 -6.445531845092773 +23 -6.5974650382995605 +24 -5.980544090270996 +25 -6.615999221801758 +26 -7.0445170402526855 +27 -6.347937107086182 +28 -7.0173540115356445 +29 -6.437374591827393 +30 -6.147070407867432 +31 -6.391169548034668 +32 -6.3590922355651855 +33 -6.353097915649414 +34 -8.008809089660645 +35 -5.965841770172119 +36 -7.292210578918457 +37 -7.899466514587402 +38 -6.756819725036621 +39 -6.3226318359375 +40 -6.825315952301025 +41 -6.660889625549316 +42 -5.886587142944336 +43 -6.353764057159424 +44 -6.227094650268555 +45 -6.780326843261719 +46 -7.114847183227539 +47 -7.1968560218811035 +48 -6.13397741317749 +49 -6.123825550079346 +50 -6.0895538330078125 +51 -7.0428643226623535 +52 -7.042725563049316 +53 -6.121582984924316 +54 -7.368879795074463 +55 -6.277353763580322 +56 -7.22930383682251 +57 -6.967887878417969 +58 -7.345863342285156 +59 -6.646428108215332 +60 -7.370569229125977 +61 -7.365872859954834 +62 -6.667781829833984 +63 -8.185227394104004 +64 -7.041168212890625 +65 -6.044724464416504 +66 -6.263096809387207 +67 -5.182981491088867 +68 -8.682493209838867 +69 -6.614046096801758 +70 -7.280738830566406 +71 -6.927536964416504 +72 -6.142812252044678 +73 -6.315526962280273 +74 -6.7438645362854 +75 -6.513354778289795 +76 -6.433558940887451 +77 -7.135562896728516 +78 -6.310669422149658 +79 -7.168282508850098 +80 -6.866829872131348 +81 -6.3948845863342285 +82 -6.490623474121094 +83 -6.270306587219238 +84 -6.318187713623047 +85 -7.631749629974365 +86 -7.127025604248047 +87 -6.794121265411377 +88 -7.181210994720459 +89 -7.367888927459717 +90 -6.764581203460693 +91 -7.1813645362854 +92 -7.067885875701904 +93 -7.199504852294922 +94 -4.516867160797119 +95 -6.511425971984863 +96 -6.495255947113037 +97 -6.223054885864258 +98 -6.06960916519165 +99 -6.404546737670898 +100 -6.6063690185546875 +101 -6.839679718017578 +102 -6.511417388916016 +103 -7.165670394897461 +104 -6.636330604553223 +105 -6.686491966247559 +106 -6.178088188171387 +107 -7.184615135192871 +108 -7.327360153198242 +109 -6.4386749267578125 +110 -5.7999162673950195 +111 -7.095001220703125 +112 -7.1128926277160645 +113 -6.483017444610596 +114 -6.324490547180176 +115 -7.265547275543213 +116 -6.941190242767334 +117 -6.556515216827393 +118 -7.278568744659424 +119 -6.697344779968262 +120 -6.692324638366699 +121 -7.655919075012207 +122 -7.435850143432617 +123 -7.419533729553223 +124 -7.3695969581604 +125 -7.269267559051514 +126 -7.34765625 +127 -7.929365634918213 +128 -6.670702934265137 +129 -6.443628311157227 +130 -7.465245723724365 +131 -7.170000076293945 +132 -7.127565860748291 +133 -4.396227836608887 +134 -7.315515041351318 +135 -7.637531280517578 +136 -6.8901824951171875 +137 -7.483570098876953 +138 -6.22567081451416 +139 -5.758413314819336 +140 -7.124645709991455 +141 -7.307458877563477 +142 -7.037891387939453 +143 -6.999596118927002 +144 -7.136890888214111 +145 -7.725980281829834 +146 -6.852178573608398 +147 -7.414962291717529 +148 -6.378384590148926 +149 -6.633126258850098 +150 -8.212347030639648 +151 -7.5561842918396 +152 -7.23483943939209 +153 -5.845646858215332 +154 -7.701530456542969 +155 -7.539637088775635 +156 -6.7817792892456055 +157 -6.121149063110352 +158 -6.689203262329102 +159 -6.017674446105957 +160 -6.469460964202881 +161 -7.456813812255859 +162 -6.988147258758545 +163 -6.860538482666016 +164 -2.213578224182129 +165 -6.694556713104248 +166 -7.024923324584961 +167 -6.660761833190918 +168 -5.877562522888184 +169 -5.206942081451416 +170 -6.495672225952148 +171 -6.342079162597656 +172 -6.739211559295654 +173 -7.5392045974731445 +174 -6.34781551361084 +175 -6.543930530548096 +176 -6.110976696014404 +177 -7.139822959899902 +178 -7.106225967407227 +179 -6.59188175201416 +180 -6.568077087402344 +181 -7.874992370605469 +182 -5.5992584228515625 +183 -4.219982147216797 +184 -6.102270126342773 +185 -7.003897190093994 +186 -3.6006855964660645 +187 -6.8180646896362305 +188 -7.4454145431518555 +189 -6.917773246765137 +190 -2.789076805114746 +191 -6.588169574737549 +192 -6.221066951751709 +193 -7.394400596618652 +194 -6.541873931884766 +195 -6.403388977050781 +196 -5.713691711425781 +197 -6.104606628417969 +198 -6.374581336975098 +199 -6.960023403167725 +200 -6.6156487464904785 +201 -7.544205188751221 +202 -2.349548816680908 +203 -6.739205360412598 +204 -6.3632025718688965 +205 -6.180267333984375 +206 -7.125173568725586 +207 -6.925105094909668 +208 -6.230293273925781 +209 -6.119503974914551 +210 -6.193659782409668 +211 -6.487274646759033 +212 -7.028600692749023 +213 -6.4920334815979 +214 -2.7069387435913086 +215 -5.052302360534668 +216 -6.756130218505859 +217 -5.989614486694336 +218 -7.5646185874938965 +219 -6.355733394622803 +220 -8.31258487701416 +221 -7.534700393676758 +222 -6.893134593963623 +223 -6.632876873016357 +224 -6.397854804992676 +225 -5.8789873123168945 +226 -6.065525054931641 +227 -6.314838886260986 +228 -6.351226806640625 +229 -6.511758804321289 +230 -6.092455863952637 +231 -7.8970537185668945 +232 -5.7023444175720215 +233 -6.603419780731201 +234 -6.934574127197266 +235 -6.501640319824219 +236 -6.03882360458374 +237 -7.253995895385742 +238 -6.693254470825195 +239 -6.938232898712158 +240 -7.086472034454346 +241 -6.848707675933838 +242 -6.739851474761963 +243 -6.570010185241699 +244 -7.325597763061523 +245 -1.2855305671691895 +246 -6.599900722503662 +247 -6.895246505737305 +248 -7.586668014526367 +249 -6.630889892578125 +250 -6.241030693054199 +251 -6.475639343261719 +252 -6.267912864685059 +253 -5.590089797973633 +254 -5.840529441833496 +255 -6.075493335723877 +256 -6.051702499389648 +257 -6.437010765075684 +258 -5.96552038192749 +259 -5.520060062408447 +260 -5.673542022705078 +261 -6.653832912445068 +262 -6.335719108581543 +263 -5.904355049133301 +264 -6.0982160568237305 +265 -5.913632869720459 +266 -6.138339042663574 +267 -6.053518772125244 +268 -6.324610233306885 +269 -5.864858627319336 +270 -5.641994953155518 +271 -6.26695442199707 +272 -6.00189208984375 +273 -6.0163960456848145 +274 -5.855271816253662 +275 -6.4326629638671875 +276 -6.104498386383057 +277 -6.072144985198975 +278 -5.458714008331299 +279 -6.149438858032227 +280 -6.02200984954834 +281 -5.8663716316223145 +282 -5.501838207244873 +283 -6.179512023925781 +284 -6.117656707763672 +285 -5.526101112365723 +286 -5.935279846191406 +287 -4.836230278015137 +288 -5.751322269439697 +289 -6.312319755554199 +290 -5.990147590637207 +291 -5.57404899597168 +292 -5.967996597290039 +293 -5.637962818145752 +294 -5.944985389709473 +295 -6.0103349685668945 +296 -5.6129655838012695 +297 -6.628322601318359 +298 -5.77374267578125 +299 -6.2458295822143555 +300 -6.105099678039551 +301 -5.687417030334473 +302 -6.198840141296387 +303 -5.624304294586182 +304 -5.702301979064941 +305 -5.212109565734863 +306 -5.940113544464111 +307 -6.119422912597656 +308 -6.064929485321045 +309 -6.075342655181885 +310 -6.268614768981934 +311 -5.580484390258789 +312 -4.782373428344727 +313 -6.508336544036865 +314 -6.033935546875 +315 -5.914183616638184 +316 -6.113262176513672 +317 -5.731459617614746 +318 -6.33579158782959 +319 -6.125679016113281 +320 -5.941309928894043 +321 -6.168606758117676 +322 -6.22866153717041 +323 -5.8379058837890625 +324 -5.852757453918457 +325 -5.956174850463867 +326 -5.591094970703125 +327 -5.7429890632629395 +328 -5.766744613647461 +329 -5.821181297302246 +330 -5.864858627319336 +331 -5.372284889221191 +332 -5.9691362380981445 +333 -6.238681793212891 +334 -5.775877475738525 +335 -6.009587287902832 +336 -6.498579978942871 +337 -6.532649993896484 +338 -5.995357036590576 +339 -5.630402088165283 +340 -6.47569465637207 +341 -6.181238174438477 +342 -6.041399955749512 +343 -5.887206077575684 +344 -5.862088680267334 +345 -6.164557456970215 +346 -6.001453399658203 +347 -5.404425621032715 +348 -6.283763408660889 +349 -6.349992752075195 +350 -6.127497673034668 +351 -6.431368350982666 +352 -5.538999557495117 +353 -5.7737860679626465 +354 -6.6211042404174805 +355 -6.055521011352539 +356 -6.44368839263916 +357 -5.921401023864746 +358 -7.068828582763672 +359 -6.087774753570557 +360 -5.697259902954102 +361 -5.579376697540283 +362 -5.7674150466918945 +363 -5.282286643981934 +364 -6.676169395446777 +365 -6.063838481903076 +366 -6.692430019378662 +367 -6.205877304077148 +368 -5.530112266540527 +369 -6.130487442016602 +370 -5.543614864349365 +371 -5.885481834411621 +372 -5.767062187194824 +373 -6.333378791809082 +374 -6.100098609924316 +375 -6.258518218994141 +376 -5.787392616271973 +377 -5.98428201675415 +378 -6.0662455558776855 +379 -6.0096049308776855 +380 -6.223349571228027 +381 -5.98030948638916 +382 -6.269686698913574 +383 -5.588926315307617 +384 -5.717665672302246 +385 -5.913632869720459 +386 -6.069342613220215 +387 -5.115323066711426 +388 -5.746488571166992 +389 -5.759634017944336 +390 -5.417057514190674 +391 -6.197732448577881 +392 -5.534537315368652 +393 -5.929277420043945 +394 -5.811395645141602 +395 -5.467659950256348 +396 -6.15366268157959 +397 -7.13212776184082 +398 -5.498290061950684 +399 -5.430872440338135 +400 -6.1801652908325195 +401 -5.603177070617676 +402 -5.973793029785156 +403 -5.934718608856201 +404 -5.944609642028809 +405 -6.242440700531006 +406 -5.7135419845581055 +407 -5.580460071563721 +408 -5.511180877685547 +409 -6.126045227050781 +410 -5.804171562194824 +411 -6.029266357421875 +412 -5.99835205078125 +413 -5.942510604858398 +414 -6.3921918869018555 +415 -5.887919902801514 +416 -5.83466911315918 +417 -5.493064880371094 +418 -5.518277645111084 +419 -5.972051620483398 +420 -6.002685546875 +421 -5.992749214172363 +422 -6.054223537445068 +423 -6.219393730163574 +424 -5.537904262542725 +425 -5.973163604736328 +426 -5.570975303649902 +427 -5.779242992401123 +428 -5.974055290222168 +429 -5.706428527832031 +430 -6.058033466339111 +431 -6.047204971313477 +432 -6.412889003753662 +433 -5.81953239440918 +434 -5.946566104888916 +435 -5.972046375274658 +436 -5.371531963348389 +437 -5.419005870819092 +438 -5.741760730743408 +439 -6.0420427322387695 +440 -5.726925373077393 +441 -6.020887851715088 +442 -5.619771480560303 +443 -6.113566875457764 +444 -5.885902404785156 +445 -5.723943710327148 +446 -6.76763916015625 +447 -6.34131383895874 +448 -6.538249969482422 +449 -6.116292953491211 +450 -6.282955169677734 +451 -5.248307228088379 +452 -6.348037242889404 +453 -5.415364742279053 +454 -6.666409492492676 +455 -6.2820329666137695 +456 -5.917535305023193 +457 -5.83638334274292 +458 -5.794678688049316 +459 -5.701689720153809 +460 -5.949613094329834 +461 -6.329507827758789 +462 -6.690071105957031 +463 -5.891641139984131 +464 -5.690352439880371 +465 -5.415364742279053 +466 -6.461349010467529 +467 -5.518277645111084 +468 -6.292346000671387 +469 -6.153167724609375 +470 -6.557131767272949 +471 -6.066568374633789 +472 -5.805550575256348 +473 -5.414914131164551 +474 -5.710595607757568 +475 -6.051113128662109 +476 -6.107208728790283 +477 -5.577019691467285 +478 -5.619454383850098 +479 -5.970724105834961 +480 -6.521446228027344 +481 -5.785162925720215 +482 -6.114489555358887 +483 -6.326164245605469 +484 -6.186128616333008 +485 -5.788750648498535 +486 -6.054003715515137 +487 -6.05400276184082 +488 -5.757481575012207 +489 -6.437410354614258 +490 -5.8670172691345215 +491 -6.349555969238281 +492 -6.058478355407715 +493 -6.171907424926758 +494 -5.641151428222656 +495 -5.527095794677734 +496 -5.929989814758301 +497 -6.341378211975098 +498 -5.527095794677734 +499 -5.592202186584473 diff --git a/example/python_pkg/C_learn/Dgraphite_diamond/DOutput/rlxd_structures_seed0.traj b/example/python_pkg/C_learn/Dgraphite_diamond/DOutput/rlxd_structures_seed0.traj new file mode 100644 index 00000000..53d05734 Binary files /dev/null and b/example/python_pkg/C_learn/Dgraphite_diamond/DOutput/rlxd_structures_seed0.traj differ diff --git a/example/python_pkg/C_learn/Dgraphite_diamond/DOutput/unrlxd_structures_seed0.traj b/example/python_pkg/C_learn/Dgraphite_diamond/DOutput/unrlxd_structures_seed0.traj new file mode 100644 index 00000000..c22a1ee6 Binary files /dev/null and b/example/python_pkg/C_learn/Dgraphite_diamond/DOutput/unrlxd_structures_seed0.traj differ diff --git a/example/python_pkg/C_learn/Dgraphite_diamond/learn.py b/example/python_pkg/C_learn/Dgraphite_diamond/learn.py index 5325615d..8c66793f 100644 --- a/example/python_pkg/C_learn/Dgraphite_diamond/learn.py +++ b/example/python_pkg/C_learn/Dgraphite_diamond/learn.py @@ -1,4 +1,5 @@ from chgnet.model import CHGNetCalculator +from ase.calculators.singlepoint import SinglePointCalculator from raffle.generator import raffle_generator from ase import build, Atoms from ase.optimize import FIRE @@ -11,11 +12,11 @@ logging.basicConfig(level=logging.DEBUG) # Function to relax a structure -def process_structure(i, atoms, num_structures_old, calc_params, optimise_structure, iteration): +def process_structure(i, atoms, num_structures_old, calc_params, optimise_structure, iteration, calc): # Check if the structure has already been processed if i < num_structures_old: return None, None, None - + # calc = Vasp(**calc_params, label=f"struct{i}", directory=f"iteration{iteration}/struct{i}/", txt=f"stdout{i}.o") inew = i - num_structures_old atoms.calc = calc @@ -32,7 +33,7 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct except Exception as e: print(f"Optimisation failed: {e}") return None, None, None - + # Save the optimised structure and its energy per atom energy_rlxd = atoms.get_potential_energy() / len(atoms) @@ -46,11 +47,11 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct if distances.min() < 1.0: print(f"Distance too small: {atoms.get_all_distances(mic=True).min()}") return None, None, None - + if abs(energy_rlxd - energy_unrlxd) > 10.0: print(f"Energy difference too large: {energy_rlxd} vs {energy_unrlxd}") return None, None, None - + return atoms, energy_unrlxd, energy_rlxd @@ -86,9 +87,9 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct num_atoms = 7 # Loop over random seeds - for seed in range(20): + for seed in range(1): print(f"Seed: {seed}") - + # set up file names energies_rlxd_filename = f"energies_rlxd_seed{seed}.txt" energies_unrlxd_filename = f"energies_unrlxd_seed{seed}.txt" @@ -131,7 +132,7 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct for host in hosts: # set the host generator.set_host(host) - + # start the iterations for iter in range(50): @@ -140,7 +141,7 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct num_structures = 5, stoichiometry = { 'C': num_atoms }, seed = seed*1000+iter, - method_probab = {"void": 0.5, "rand": 0.001, "walk": 0.5, "grow": 0.0, "min": 1.0}, + method_ratio = {"void": 0.4, "rand": 0.001, "walk": 0.4, "grow": 0.2, "min": 1.0}, verbose = 0, ) @@ -162,7 +163,12 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct write(iterdir+f"POSCAR_unrlxd_{i}", generated_structures[num_structures_old + i]) print(f"Structure {i} energy per atom: {generated_structures[num_structures_old + i].get_potential_energy() / len(generated_structures[num_structures_old + i])}") unrlxd_structures.append(generated_structures[num_structures_old + i].copy()) - + unrlxd_structures[-1].calc = SinglePointCalculator( + generated_structures[num_structures_old + i], + energy=generated_structures[num_structures_old + i].get_potential_energy(), + forces=generated_structures[num_structures_old + i].get_forces() + ) + # Start parallel execution print("Starting parallel execution") results = Parallel(n_jobs=5)( @@ -172,11 +178,16 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct # Wait for all futures to complete for j, result in enumerate(results): - generated_structures[j+num_structures_old], energy_unrlxd[j], energy_rlxd[j] = result - if generated_structures[j+num_structures_old] is None: + generated_structures[num_structures_old + j], energy_unrlxd[j], energy_rlxd[j] = result + if generated_structures[num_structures_old + j] is None: print("Structure failed the checks") continue - rlxd_structures.append(generated_structures[j+num_structures_old].copy()) + rlxd_structures.append(generated_structures[num_structures_old + j].copy()) + rlxd_structures[-1].calc = SinglePointCalculator( + generated_structures[j+num_structures_old], + energy=generated_structures[num_structures_old + j].get_potential_energy(), + forces=generated_structures[num_structures_old + j].get_forces() + ) print("All futures completed") # Remove structures that failed the checks @@ -188,7 +199,7 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct # del unrlxd_structures[j] del rlxd_structures[j] generator.remove_structure(j) - num_structures_new = len(generated_structures) + num_structures_new = len(generated_structures) # write the structures to files for i in range(num_structures_new - num_structures_old): @@ -237,4 +248,4 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct write(f"rlxd_structures_seed{seed}.traj", rlxd_structures) print("All generated and relaxed structures written") - print("Learning complete") \ No newline at end of file + print("Learning complete") diff --git a/example/python_pkg/C_learn/Dgraphite_diamond/pca.ipynb b/example/python_pkg/C_learn/Dgraphite_diamond/pca.ipynb index f9a15885..2587bdd9 100644 --- a/example/python_pkg/C_learn/Dgraphite_diamond/pca.ipynb +++ b/example/python_pkg/C_learn/Dgraphite_diamond/pca.ipynb @@ -19,7 +19,8 @@ "from agox.utils.graph_sorting import Analysis\n", "\n", "import numpy as np\n", - "from sklearn.decomposition import PCA" + "from sklearn.decomposition import PCA\n", + "from matplotlib.ticker import (MultipleLocator, AutoMinorLocator)" ] }, { @@ -43,7 +44,7 @@ "source": [ "## Set the plotting parameters\n", "seed = 0\n", - "identifier = \"\"\n", + "identifier = \"4\"\n", "# min_energy = -9.064090728759766" ] }, @@ -77,7 +78,7 @@ "outputs": [], "source": [ "## Load the unrelaxed structures\n", - "unrlxd_structures = read(\"DTMP\"+identifier+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "unrlxd_structures = read(\"DOutput\"+identifier+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", "for structure in unrlxd_structures:\n", " structure.calc = calc" ] @@ -89,7 +90,7 @@ "outputs": [], "source": [ "## Load the relaxed structures\n", - "rlxd_structures = read(\"DTMP\"+identifier+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "rlxd_structures = read(\"DOutput\"+identifier+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", "for structure in rlxd_structures:\n", " structure.calc = calc" ] @@ -102,7 +103,7 @@ "source": [ "# read energies from energies_unrlxd_seed0.txt and add to the respective structures using a SinglePointCalculator\n", "# the file has the form \"index energy\"\n", - "filename = \"DTMP\"+identifier+\"/energies_unrlxd_seed\"+str(seed)+\".txt\"\n", + "filename = \"DOutput\"+identifier+\"/energies_unrlxd_seed\"+str(seed)+\".txt\"\n", "with open(filename) as f:\n", " for line in f:\n", " index, energy = line.split()\n", @@ -111,7 +112,7 @@ " unrlxd_structures[index].calc = SinglePointCalculator(unrlxd_structures[index], energy=energy * len(unrlxd_structures[index]))\n", "\n", "\n", - "filename = \"DTMP\"+identifier+\"/energies_rlxd_seed\"+str(seed)+\".txt\"\n", + "filename = \"DOutput\"+identifier+\"/energies_rlxd_seed\"+str(seed)+\".txt\"\n", "with open(filename) as f:\n", " for line in f:\n", " index, energy = line.split()\n", @@ -292,34 +293,29 @@ " ax.scatter(diamond_X_reduced[0,0], diamond_X_reduced[0,1], s=200, edgecolor=[1.0, 0.0, 0.0, 0.5], facecolor='none', linewidth=2, label='diamond')\n", " ax.scatter(graphite_X_reduced[0,0], graphite_X_reduced[0,1], s=200, edgecolor=[1.0, 0.0, 0.0, 1.0], facecolor='none', linewidth=2, label='graphite')\n", " if ax == axes[1]:\n", - " ax.legend(fontsize=10)\n", " handles, labels = ax.get_legend_handles_labels()\n", - " ax.legend(handles[::-1], labels[::-1], facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, loc='upper right')\n", + " ax.legend(handles[::-1], labels[::-1], facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, loc='upper right', fontsize=20, handletextpad=0.1)\n", "\n", "## Add labels\n", - "fig.text(0.5, 0.04, 'Principal Component 1', ha='center', fontsize=15)\n", - "axes[0].set_ylabel('Principal Component 2', fontsize=15)\n", - "axes[0].set_title('Unrelaxed')\n", - "axes[1].set_title('Relaxed')\n", - "if identifier == \"_VASP\":\n", - " if rlxd_string == \"rlxd\":\n", - " xlims = [-11, 8]\n", - " ylims = [-5, 6]\n", - " else:\n", - " xlims = [-9, 13]\n", - " ylims = [-7, 12]\n", - "else:\n", - " if rlxd_string == \"rlxd\":\n", + "fig.text(0.5, 0.0, 'Principal component 1', ha='center', fontsize=20)\n", + "axes[0].set_ylabel('Principal component 2', fontsize=20)\n", + "axes[0].set_title('Unrelaxed', fontsize=20)\n", + "axes[1].set_title('Relaxed', fontsize=20)\n", + "if rlxd_string == \"rlxd\":\n", " xlims = [-310, 310]\n", " ylims = [-53, 53]\n", - " else:\n", + "else:\n", " xlims = [-5, 13]\n", " ylims = [-6.5, 13]\n", "\n", "for ax in axes:\n", - " ax.tick_params(axis='both', direction='in')\n", - " ax.set_xlim(xlims)\n", - " ax.set_ylim(ylims)\n", + " ax.tick_params(axis='both', direction='in', length=6, labelsize=20)\n", + " # ax.yaxis.set_major_locator(MultipleLocator(3))\n", + " ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.xaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.tick_params(axis='both', which='minor', length=3, direction='in')\n", + " ax.set_xlim(xlims)\n", + " ax.set_ylim(ylims)\n", "\n", "## Unify tick labels\n", "xticks = axes[0].get_xticks()\n", @@ -338,12 +334,24 @@ "\n", "## Add colorbar next to the axes\n", "cbar = fig.colorbar(axes[1].collections[0], ax=axes, orientation='vertical', fraction=0.085, pad=0.02)\n", - "cbar.set_label('Formation energy (eV/atom)', fontsize=15)\n", + "cbar.ax.tick_params(labelsize=20)\n", + "cbar.ax.yaxis.set_major_locator(MultipleLocator(1))\n", + "cbar.ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + "cbar.set_label('Formation energy (eV/atom)', fontsize=20)\n", "\n", "## Save the figure\n", "plt.savefig('C_RAFFLE'+identifier+'_pca_'+rlxd_string+'_fit_seed'+str(seed)+'.pdf', bbox_inches='tight', pad_inches=0, facecolor=fig.get_facecolor(), edgecolor='none')" ] }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "len(rlxd_structures)" + ] + }, { "cell_type": "code", "execution_count": null, diff --git a/example/python_pkg/C_learn/plot_structures_vs_energies.ipynb b/example/python_pkg/C_learn/plot_structures_vs_energies.ipynb index 9207ce29..06534dce 100644 --- a/example/python_pkg/C_learn/plot_structures_vs_energies.ipynb +++ b/example/python_pkg/C_learn/plot_structures_vs_energies.ipynb @@ -2,7 +2,7 @@ "cells": [ { "cell_type": "code", - "execution_count": 29, + "execution_count": null, "metadata": {}, "outputs": [], "source": [ @@ -35,7 +35,7 @@ "source": [ "## Set the plotting parameters\n", "method = \"RSS\"\n", - "identifier = \"\"\n", + "identifier = \"_seed_test\"\n", "bin_width = 0.1\n", "rlxd_string = \"rlxd\"\n", "seed = 0" @@ -50,7 +50,7 @@ "## Load the data\n", "energies = []\n", "if method == \"RAFFLE\":\n", - " filename = \"D\"+method+\"/DTMP\"+identifier+\"/energies_\"+rlxd_string+\"_seed\"+str(seed)+\".txt\"\n", + " filename = \"D\"+method+\"/DOutput\"+identifier+\"/energies_\"+rlxd_string+\"_seed\"+str(seed)+\".txt\"\n", " with open(filename) as f:\n", " for line in f:\n", " index, energy = line.split()\n", @@ -58,7 +58,7 @@ " energy = float(energy)\n", " energies.append(energy)\n", "else:\n", - " filename = \"D\"+method+\"/DTMP\"+identifier+\"/\"+rlxd_string+\"_structures_seed\"+str(seed)+\".traj\"\n", + " filename = \"D\"+method+\"/DOutput\"+identifier+\"/\"+rlxd_string+\"_structures_seed\"+str(seed)+\".traj\"\n", " traj = read(filename, \":\")\n", " for atoms in traj:\n", " energies.append(atoms.get_potential_energy() / len(atoms))" @@ -87,37 +87,34 @@ "cell_type": "code", "execution_count": null, "metadata": {}, - "outputs": [ - { - "data": { - "image/png": "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", - "text/plain": [ - "
" - ] - }, - "metadata": {}, - "output_type": "display_data" - } - ], + "outputs": [], "source": [ "## Plot the number structures vs the energies per atom\n", "fig = plt.figure(figsize=(6, 6))\n", "ax = fig.add_subplot(111)\n", "plt.bar(delta_en_per_atom_binned, counts, width=0.1)\n", - "plt.xlabel('Energy per atom (eV/atom)', fontsize=15)\n", - "plt.ylabel('Number of structures', fontsize=15)\n", + "plt.xlabel('Energy per atom (eV/atom)', fontsize=25)\n", + "plt.ylabel('Number of structures', fontsize=25)\n", "ax.tick_params(axis='x', which='minor', length=3)\n", - "ax.tick_params(axis='x', which='major', length=6)\n", + "ax.tick_params(axis='x', which='major', length=6, labelsize=20)\n", "ax.tick_params(axis='x', which='both', labelbottom=True, top=True, direction='in')\n", - "ax.tick_params(axis='y', which='both', labelbottom=True, right=True, direction='in')\n", + "ax.tick_params(axis='y', which='both', labelbottom=True, right=True, direction='in', labelsize=20, length=6)\n", "plt.bar(delta_en_per_atom_binned, counts, width=0.1, color='lightgrey', edgecolor='black')\n", "\n", "ax.set_xticks(np.arange(0, max(2.0,max(delta_en_per_atom_binned)) + 0.5, 0.5))\n", "ax.xaxis.set_minor_locator(AutoMinorLocator(2))\n", + "ax.set_ylim(0, 500)\n", "\n", "## Save the plot\n", "plt.savefig(\"C_\"+method+identifier+\"_structures_vs_deltaE_\"+rlxd_string+\"_seed\"+str(seed)+\".pdf\", bbox_inches='tight', pad_inches=0, facecolor=fig.get_facecolor(), edgecolor='none')\n" ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [] } ], "metadata": { @@ -136,7 +133,7 @@ "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", - "version": "3.12.2" + "version": "3.12.8" } }, "nbformat": 4, diff --git a/example/python_pkg/MoS2_learn/DRAFFLE/DOutput/energies_rlxd_seed0.txt b/example/python_pkg/MoS2_learn/DRAFFLE/DOutput/energies_rlxd_seed0.txt new file mode 100644 index 00000000..206d528b --- /dev/null +++ b/example/python_pkg/MoS2_learn/DRAFFLE/DOutput/energies_rlxd_seed0.txt @@ -0,0 +1,1000 @@ +0 -6.792280673980713 +1 -6.794041156768799 +2 -6.70339822769165 +3 -6.744536876678467 +4 -7.5481438636779785 +5 -6.7894721031188965 +6 -6.974768161773682 +7 -7.547606945037842 +8 -7.0563788414001465 +9 -6.80018949508667 +10 -7.450772762298584 +11 -7.547704219818115 +12 -6.9741129875183105 +13 -6.795709609985352 +14 -6.794644832611084 +15 -6.531110763549805 +16 -6.912484645843506 +17 -6.795734882354736 +18 -7.118061542510986 +19 -7.049720764160156 +20 -6.795740604400635 +21 -7.4496917724609375 +22 -7.547769069671631 +23 -6.960535526275635 +24 -7.055090427398682 +25 -7.059820652008057 +26 -7.0492424964904785 +27 -7.0500407218933105 +28 -7.547616481781006 +29 -7.543476581573486 +30 -7.54780387878418 +31 -7.000400066375732 +32 -7.451559543609619 +33 -7.048985958099365 +34 -6.528371334075928 +35 -7.055026531219482 +36 -6.793426036834717 +37 -6.928945064544678 +38 -7.093574523925781 +39 -7.4512553215026855 +40 -7.547883987426758 +41 -7.118072032928467 +42 -7.450419902801514 +43 -7.051103115081787 +44 -7.093567371368408 +45 -6.792665481567383 +46 -6.8844170570373535 +47 -6.792176723480225 +48 -6.703440189361572 +49 -7.451318740844727 +50 -6.79926061630249 +51 -7.451416015625 +52 -6.534665584564209 +53 -7.545140743255615 +54 -7.063046932220459 +55 -6.795613765716553 +56 -6.795386791229248 +57 -7.452168941497803 +58 -7.05672025680542 +59 -6.794837474822998 +60 -6.973861217498779 +61 -7.054813385009766 +62 -7.118104934692383 +63 -7.118074893951416 +64 -7.546197414398193 +65 -7.548015594482422 +66 -6.794826984405518 +67 -7.118091106414795 +68 -6.694921970367432 +69 -6.794334888458252 +70 -7.049549579620361 +71 -7.093614101409912 +72 -7.049741268157959 +73 -7.0564751625061035 +74 -6.79408597946167 +75 -6.79442834854126 +76 -7.056366443634033 +77 -7.451925754547119 +78 -7.547744274139404 +79 -7.051196575164795 +80 -7.093355655670166 +81 -6.794586181640625 +82 -6.705953598022461 +83 -6.993845462799072 +84 -7.118067264556885 +85 -7.118092060089111 +86 -6.863321781158447 +87 -7.355106353759766 +88 -7.547598361968994 +89 -6.7958550453186035 +90 -7.118076801300049 +91 -6.973824977874756 +92 -7.000573635101318 +93 -6.795167446136475 +94 -7.056288242340088 +95 -6.794727802276611 +96 -7.118030548095703 +97 -6.795379638671875 +98 -7.055955410003662 +99 -7.118056774139404 +100 -6.7352471351623535 +101 -6.70592737197876 +102 -6.80095100402832 +103 -6.792179107666016 +104 -7.055765628814697 +105 -7.449882507324219 +106 -6.975030899047852 +107 -7.44994592666626 +108 -7.44961404800415 +109 -7.4499831199646 +110 -7.450760364532471 +111 -7.051044464111328 +112 -7.118031024932861 +113 -6.938619136810303 +114 -6.801756381988525 +115 -6.975296497344971 +116 -7.118058681488037 +117 -7.093355178833008 +118 -7.118096828460693 +119 -7.547285556793213 +120 -6.901442050933838 +121 -6.800256252288818 +122 -6.699023723602295 +123 -7.118047714233398 +124 -6.795648574829102 +125 -6.79419469833374 +126 -6.7961907386779785 +127 -7.051206111907959 +128 -7.055605411529541 +129 -6.793972492218018 +130 -7.450493335723877 +131 -7.543982982635498 +132 -7.451395034790039 +133 -7.546241760253906 +134 -7.000573635101318 +135 -6.794771194458008 +136 -7.547934055328369 +137 -6.979163646697998 +138 -6.408498764038086 +139 -7.544008731842041 +140 -6.9741129875183105 +141 -7.0936279296875 +142 -7.118079662322998 +143 -7.000382900238037 +144 -6.9741129875183105 +145 -7.0145583152771 +146 -6.694661617279053 +147 -7.547605514526367 +148 -7.014558792114258 +149 -7.543476104736328 +150 -7.038877010345459 +151 -6.925787448883057 +152 -6.993545055389404 +153 -7.07607889175415 +154 -7.055955410003662 +155 -7.093623638153076 +156 -7.056204319000244 +157 -7.546648025512695 +158 -7.54796838760376 +159 -6.993999481201172 +160 -7.546676158905029 +161 -6.928403377532959 +162 -7.049292087554932 +163 -7.5474629402160645 +164 -7.09362268447876 +165 -7.546498775482178 +166 -7.0624566078186035 +167 -7.056555271148682 +168 -6.79434061050415 +169 -7.11804723739624 +170 -7.049724102020264 +171 -7.545936584472656 +172 -7.547692775726318 +173 -6.743870258331299 +174 -7.055701732635498 +175 -6.694230556488037 +176 -7.075997829437256 +177 -6.793180465698242 +178 -6.788928985595703 +179 -6.801111698150635 +180 -7.076064586639404 +181 -7.118028163909912 +182 -6.98798131942749 +183 -7.093586444854736 +184 -7.545936584472656 +185 -6.939357280731201 +186 -7.049668788909912 +187 -7.118083953857422 +188 -7.0495991706848145 +189 -7.450479984283447 +190 -7.45042085647583 +191 -6.790079593658447 +192 -7.452465057373047 +193 -7.1180877685546875 +194 -6.78993558883667 +195 -7.54754114151001 +196 -6.9131317138671875 +197 -7.0935821533203125 +198 -6.94746208190918 +199 -7.547868251800537 +200 -7.545810222625732 +201 -7.015101909637451 +202 -7.0713324546813965 +203 -6.7934393882751465 +204 -6.79393196105957 +205 -6.833714962005615 +206 -6.735598087310791 +207 -7.049767971038818 +208 -7.545936584472656 +209 -6.98845911026001 +210 -7.049729824066162 +211 -7.071347713470459 +212 -7.071344375610352 +213 -7.093346118927002 +214 -7.0527191162109375 +215 -7.093505382537842 +216 -6.7918853759765625 +217 -6.796430587768555 +218 -7.5444769859313965 +219 -6.79459810256958 +220 -6.705973148345947 +221 -7.056769847869873 +222 -6.795637130737305 +223 -7.051035404205322 +224 -7.055511474609375 +225 -6.790838241577148 +226 -7.0003790855407715 +227 -7.071342468261719 +228 -7.451817989349365 +229 -7.093559265136719 +230 -7.071347713470459 +231 -6.792500019073486 +232 -6.938619136810303 +233 -7.45187520980835 +234 -6.793357849121094 +235 -7.055026531219482 +236 -6.795333385467529 +237 -6.9734625816345215 +238 -7.093427658081055 +239 -7.093347072601318 +240 -7.547693729400635 +241 -6.795072078704834 +242 -7.049691677093506 +243 -7.014448642730713 +244 -7.451013088226318 +245 -7.118070125579834 +246 -7.0760817527771 +247 -7.1179986000061035 +248 -6.795542240142822 +249 -6.79603910446167 +250 -6.796336650848389 +251 -7.09359884262085 +252 -6.785315036773682 +253 -7.056360244750977 +254 -7.118051528930664 +255 -7.000387668609619 +256 -7.5481133460998535 +257 -7.09363317489624 +258 -7.547688961029053 +259 -6.796844482421875 +260 -7.049676895141602 +261 -7.355258464813232 +262 -7.055830478668213 +263 -6.974466323852539 +264 -6.7967915534973145 +265 -6.7929816246032715 +266 -6.974086284637451 +267 -7.093503952026367 +268 -6.9741129875183105 +269 -6.795542240142822 +270 -7.547661304473877 +271 -6.903995990753174 +272 -7.0760016441345215 +273 -7.056670665740967 +274 -7.071345806121826 +275 -7.44989538192749 +276 -6.87054967880249 +277 -7.118093013763428 +278 -7.055720806121826 +279 -7.055769443511963 +280 -7.118096828460693 +281 -7.118063449859619 +282 -7.055649280548096 +283 -7.118063449859619 +284 -7.547704219818115 +285 -7.051199436187744 +286 -7.449982166290283 +287 -7.544554233551025 +288 -6.699012279510498 +289 -7.056576251983643 +290 -6.795755863189697 +291 -6.7944111824035645 +292 -7.118074893951416 +293 -7.049737930297852 +294 -7.547452449798584 +295 -6.7964396476745605 +296 -7.118095874786377 +297 -6.79506254196167 +298 -6.974538326263428 +299 -7.54723596572876 +300 -7.118078708648682 +301 -7.118093967437744 +302 -6.79083776473999 +303 -6.793087005615234 +304 -6.792905330657959 +305 -7.0564422607421875 +306 -6.912691593170166 +307 -6.7890305519104 +308 -7.093626499176025 +309 -7.054559230804443 +310 -7.052217960357666 +311 -7.452513217926025 +312 -7.076039791107178 +313 -6.79083776473999 +314 -7.049720287322998 +315 -7.118093013763428 +316 -7.1180596351623535 +317 -6.794987201690674 +318 -7.547613143920898 +319 -6.79436731338501 +320 -7.062562465667725 +321 -6.974087238311768 +322 -7.093546390533447 +323 -7.45000696182251 +324 -7.548007488250732 +325 -7.543725490570068 +326 -6.789056301116943 +327 -7.050931453704834 +328 -7.450761795043945 +329 -6.919955730438232 +330 -7.055379390716553 +331 -6.800774097442627 +332 -6.974720478057861 +333 -6.9741129875183105 +334 -7.118100643157959 +335 -6.991363048553467 +336 -7.056768894195557 +337 -6.9299445152282715 +338 -7.547704219818115 +339 -7.057007312774658 +340 -7.118075847625732 +341 -7.450760364532471 +342 -6.796535491943359 +343 -7.118089199066162 +344 -6.793002605438232 +345 -7.548403263092041 +346 -7.45275354385376 +347 -6.7957329750061035 +348 -7.1180739402771 +349 -7.452520847320557 +350 -6.790770053863525 +351 -7.543221950531006 +352 -7.449737548828125 +353 -6.973404407501221 +354 -7.093588352203369 +355 -7.052438259124756 +356 -7.545936584472656 +357 -7.548431396484375 +358 -7.093504428863525 +359 -7.356741428375244 +360 -6.833041667938232 +361 -7.450052738189697 +362 -7.093588352203369 +363 -7.45063591003418 +364 -7.118040561676025 +365 -6.800370693206787 +366 -7.449830532073975 +367 -7.450357913970947 +368 -7.076040744781494 +369 -6.529397487640381 +370 -7.0936126708984375 +371 -7.451420307159424 +372 -7.451467990875244 +373 -7.056180953979492 +374 -7.093528747558594 +375 -7.118083477020264 +376 -7.071295261383057 +377 -6.793174743652344 +378 -6.939357280731201 +379 -6.793039321899414 +380 -7.015140056610107 +381 -7.093564987182617 +382 -7.0760674476623535 +383 -7.118093013763428 +384 -7.014062404632568 +385 -7.54796838760376 +386 -7.452874660491943 +387 -6.7949700355529785 +388 -7.052183628082275 +389 -6.795648574829102 +390 -7.548141956329346 +391 -7.051041126251221 +392 -7.547778606414795 +393 -6.833192825317383 +394 -6.796964645385742 +395 -7.056127071380615 +396 -6.9607768058776855 +397 -7.547815799713135 +398 -7.055971622467041 +399 -6.979189395904541 +400 -7.076076030731201 +401 -7.118072986602783 +402 -6.535424709320068 +403 -7.012924671173096 +404 -7.093328952789307 +405 -6.570941925048828 +406 -6.979247570037842 +407 -6.795249938964844 +408 -7.093627452850342 +409 -6.832804203033447 +410 -6.534426212310791 +411 -7.063030242919922 +412 -7.076086044311523 +413 -6.799936294555664 +414 -7.452254772186279 +415 -6.795644283294678 +416 -7.0510711669921875 +417 -7.07134485244751 +418 -7.050948619842529 +419 -6.735005855560303 +420 -7.118087291717529 +421 -7.051215648651123 +422 -7.548511981964111 +423 -7.449944972991943 +424 -7.547759532928467 +425 -7.355775356292725 +426 -7.449982166290283 +427 -7.093588352203369 +428 -7.1180419921875 +429 -6.7944722175598145 +430 -7.093616962432861 +431 -7.450815200805664 +432 -6.782032489776611 +433 -6.694646835327148 +434 -7.0554327964782715 +435 -6.8163743019104 +436 -7.118086338043213 +437 -7.547998428344727 +438 -6.795627117156982 +439 -7.056451320648193 +440 -7.450361251831055 +441 -7.451667308807373 +442 -7.051040172576904 +443 -6.9752197265625 +444 -7.054964065551758 +445 -7.355825901031494 +446 -6.79556131362915 +447 -7.54604959487915 +448 -7.118052959442139 +449 -7.449545383453369 +450 -7.450524806976318 +451 -7.545499324798584 +452 -7.118101119995117 +453 -6.791558742523193 +454 -6.793214321136475 +455 -6.795389652252197 +456 -7.056283473968506 +457 -6.794449329376221 +458 -7.546039581298828 +459 -7.056440830230713 +460 -6.79640007019043 +461 -7.071335315704346 +462 -7.015003204345703 +463 -7.450542449951172 +464 -7.118027210235596 +465 -6.693685054779053 +466 -7.0003790855407715 +467 -7.118080139160156 +468 -7.049734115600586 +469 -6.8019633293151855 +470 -7.0496506690979 +471 -6.975009441375732 +472 -7.07620096206665 +473 -7.076080799102783 +474 -7.093490123748779 +475 -6.794278621673584 +476 -7.056010723114014 +477 -6.938619136810303 +478 -7.452325820922852 +479 -6.735257625579834 +480 -6.4228668212890625 +481 -6.795542240142822 +482 -7.450073719024658 +483 -6.975090503692627 +484 -7.451712131500244 +485 -7.063527584075928 +486 -7.00037956237793 +487 -7.450342178344727 +488 -6.795682907104492 +489 -6.795304775238037 +490 -7.1180572509765625 +491 -7.449953556060791 +492 -7.44994592666626 +493 -6.9131317138671875 +494 -7.118081569671631 +495 -7.547609806060791 +496 -7.118062496185303 +497 -7.050836563110352 +498 -7.093593597412109 +499 -7.543862819671631 +500 -6.9131317138671875 +501 -6.735559940338135 +502 -7.547426700592041 +503 -6.7944722175598145 +504 -7.093587875366211 +505 -7.0003790855407715 +506 -7.450085163116455 +507 -7.0560455322265625 +508 -7.076084613800049 +509 -6.9382195472717285 +510 -6.79681921005249 +511 -7.0762104988098145 +512 -7.548101425170898 +513 -7.0935797691345215 +514 -7.547604084014893 +515 -7.056440830230713 +516 -6.793079853057861 +517 -6.973405361175537 +518 -7.547814846038818 +519 -7.055473804473877 +520 -7.451193332672119 +521 -6.832804203033447 +522 -6.79563570022583 +523 -7.015115261077881 +524 -6.845769882202148 +525 -6.705879211425781 +526 -6.793431758880615 +527 -6.694604873657227 +528 -7.000391006469727 +529 -7.11809778213501 +530 -7.0934739112854 +531 -7.449759006500244 +532 -7.451932430267334 +533 -7.3551812171936035 +534 -7.355480194091797 +535 -7.117987155914307 +536 -6.796993255615234 +537 -7.547852993011475 +538 -7.118097305297852 +539 -6.795240879058838 +540 -7.093587398529053 +541 -7.093616485595703 +542 -7.050866603851318 +543 -6.979300022125244 +544 -6.8669891357421875 +545 -7.547975063323975 +546 -6.97487211227417 +547 -7.544571399688721 +548 -6.534919261932373 +549 -7.355827808380127 +550 -6.795518398284912 +551 -6.883955001831055 +552 -7.355777740478516 +553 -7.546701908111572 +554 -6.79536771774292 +555 -6.408140182495117 +556 -6.732981204986572 +557 -7.355419635772705 +558 -7.4499592781066895 +559 -7.055391788482666 +560 -7.547332763671875 +561 -7.076051712036133 +562 -6.794159412384033 +563 -7.118078231811523 +564 -7.051096439361572 +565 -6.795648097991943 +566 -7.450733661651611 +567 -7.547943592071533 +568 -7.548460483551025 +569 -6.88385009765625 +570 -7.093633651733398 +571 -7.5435004234313965 +572 -7.055004119873047 +573 -6.698968410491943 +574 -6.938619136810303 +575 -7.547517776489258 +576 -6.795461654663086 +577 -6.979152202606201 +578 -7.547445774078369 +579 -7.118039608001709 +580 -7.0760650634765625 +581 -7.547216892242432 +582 -7.056590557098389 +583 -7.547325611114502 +584 -7.056236267089844 +585 -6.79446268081665 +586 -7.051144123077393 +587 -7.118089199066162 +588 -7.450321197509766 +589 -7.547998905181885 +590 -7.118100643157959 +591 -7.052661895751953 +592 -6.97391939163208 +593 -7.00037956237793 +594 -6.794467449188232 +595 -6.9300618171691895 +596 -7.055269241333008 +597 -7.118062496185303 +598 -7.451452732086182 +599 -7.051042079925537 +600 -7.452213764190674 +601 -6.794419765472412 +602 -6.9380202293396 +603 -7.547853946685791 +604 -6.800437927246094 +605 -6.790533542633057 +606 -6.790838241577148 +607 -6.795252323150635 +608 -7.450433254241943 +609 -7.093505382537842 +610 -7.0559983253479 +611 -7.450641632080078 +612 -7.451322078704834 +613 -6.734971523284912 +614 -7.055050373077393 +615 -7.052182674407959 +616 -7.057013034820557 +617 -7.118040084838867 +618 -6.795623779296875 +619 -7.449697971343994 +620 -7.052667140960693 +621 -6.9734320640563965 +622 -7.093608856201172 +623 -7.5476813316345215 +624 -7.056381702423096 +625 -7.071313858032227 +626 -6.919869899749756 +627 -6.739645481109619 +628 -7.547878742218018 +629 -7.076051712036133 +630 -6.795541763305664 +631 -7.118095874786377 +632 -6.799676895141602 +633 -7.450692653656006 +634 -7.118077754974365 +635 -6.973918914794922 +636 -7.055017948150635 +637 -7.548015594482422 +638 -7.063028812408447 +639 -6.4105401039123535 +640 -7.118093490600586 +641 -6.795114994049072 +642 -7.000559329986572 +643 -6.797097682952881 +644 -7.5478196144104 +645 -6.787492275238037 +646 -7.449957370758057 +647 -6.9024176597595215 +648 -7.548079013824463 +649 -6.5878167152404785 +650 -6.791421413421631 +651 -6.973581790924072 +652 -7.546756267547607 +653 -6.7962775230407715 +654 -7.54797887802124 +655 -7.118103504180908 +656 -7.545783996582031 +657 -6.794075012207031 +658 -7.5455451011657715 +659 -7.000509262084961 +660 -7.050867557525635 +661 -7.049722671508789 +662 -7.056087970733643 +663 -7.118086338043213 +664 -7.055910110473633 +665 -6.991558074951172 +666 -7.449909210205078 +667 -7.071330547332764 +668 -7.547307968139648 +669 -7.118089199066162 +670 -7.118081569671631 +671 -6.97390604019165 +672 -6.705953121185303 +673 -7.056116104125977 +674 -7.093586444854736 +675 -6.911586284637451 +676 -6.7956695556640625 +677 -6.793838977813721 +678 -7.450006008148193 +679 -7.548017501831055 +680 -7.049726963043213 +681 -6.97343635559082 +682 -6.793079376220703 +683 -7.000574588775635 +684 -7.5479416847229 +685 -6.975077152252197 +686 -7.547660827636719 +687 -7.059468746185303 +688 -6.929785251617432 +689 -6.7953925132751465 +690 -7.015134334564209 +691 -7.056008815765381 +692 -6.922573566436768 +693 -7.547341823577881 +694 -7.450155735015869 +695 -7.547985076904297 +696 -7.118096828460693 +697 -6.7937541007995605 +698 -7.118086338043213 +699 -6.795268535614014 +700 -7.049726963043213 +701 -6.792974472045898 +702 -6.800388336181641 +703 -6.938317775726318 +704 -7.049749851226807 +705 -7.0935492515563965 +706 -6.7917962074279785 +707 -7.118074417114258 +708 -7.00037956237793 +709 -7.449945449829102 +710 -6.97391939163208 +711 -7.547308444976807 +712 -6.7926249504089355 +713 -7.049745559692383 +714 -7.547998905181885 +715 -7.052751064300537 +716 -7.076063632965088 +717 -7.118097305297852 +718 -7.450429916381836 +719 -7.076028823852539 +720 -7.09358024597168 +721 -6.8832526206970215 +722 -7.547231197357178 +723 -7.041876316070557 +724 -6.938507556915283 +725 -7.071341037750244 +726 -7.545936584472656 +727 -7.056385517120361 +728 -6.7954277992248535 +729 -7.056314945220947 +730 -6.795114994049072 +731 -6.833192825317383 +732 -7.055979251861572 +733 -6.919764041900635 +734 -6.5352959632873535 +735 -7.547536849975586 +736 -7.051942348480225 +737 -7.118096828460693 +738 -7.451775074005127 +739 -7.076035976409912 +740 -6.99116849899292 +741 -6.86334753036499 +742 -6.789884090423584 +743 -7.547327041625977 +744 -7.5477681159973145 +745 -7.052680969238281 +746 -7.050801753997803 +747 -7.118037700653076 +748 -6.79696798324585 +749 -7.451900959014893 +750 -7.093596935272217 +751 -7.05642557144165 +752 -7.012556552886963 +753 -7.5446457862854 +754 -7.450630187988281 +755 -6.80097770690918 +756 -6.732892990112305 +757 -7.093583583831787 +758 -6.794825077056885 +759 -7.45224142074585 +760 -7.547611713409424 +761 -7.547619342803955 +762 -6.792788982391357 +763 -7.5478668212890625 +764 -6.733665943145752 +765 -7.118093490600586 +766 -7.050754547119141 +767 -6.793259143829346 +768 -6.790770053863525 +769 -6.570189952850342 +770 -7.07133674621582 +771 -6.795138835906982 +772 -7.076071262359619 +773 -7.547903537750244 +774 -6.695297718048096 +775 -7.017659664154053 +776 -7.356459140777588 +777 -6.796417713165283 +778 -7.076040267944336 +779 -7.547998905181885 +780 -6.801106929779053 +781 -7.450023651123047 +782 -7.056777477264404 +783 -7.056472301483154 +784 -7.54778528213501 +785 -7.093597888946533 +786 -7.451836109161377 +787 -6.939576625823975 +788 -7.049720287322998 +789 -6.79296350479126 +790 -7.451681137084961 +791 -7.118099212646484 +792 -7.449954509735107 +793 -7.0567145347595215 +794 -6.795648574829102 +795 -7.063523769378662 +796 -6.993637561798096 +797 -6.974069118499756 +798 -7.546550750732422 +799 -7.04976224899292 +800 -7.118076801300049 +801 -7.547937870025635 +802 -6.928316593170166 +803 -6.974112033843994 +804 -7.54681396484375 +805 -6.7957444190979 +806 -7.544535160064697 +807 -7.1180806159973145 +808 -7.056577205657959 +809 -7.451760768890381 +810 -6.79155969619751 +811 -7.0003790855407715 +812 -7.093578815460205 +813 -7.055897235870361 +814 -7.4501423835754395 +815 -7.0713372230529785 +816 -6.792510986328125 +817 -7.547631740570068 +818 -7.055552005767822 +819 -6.53529691696167 +820 -7.547544002532959 +821 -6.8323073387146 +822 -7.545813083648682 +823 -7.056602954864502 +824 -7.450036525726318 +825 -7.449932098388672 +826 -6.695016384124756 +827 -6.790156841278076 +828 -7.5478596687316895 +829 -7.546595096588135 +830 -7.05658483505249 +831 -7.11810302734375 +832 -7.0518798828125 +833 -7.450073719024658 +834 -7.0597991943359375 +835 -6.705933094024658 +836 -7.0563836097717285 +837 -7.5485615730285645 +838 -6.570793151855469 +839 -7.041849613189697 +840 -6.798913478851318 +841 -7.449491024017334 +842 -7.547626972198486 +843 -6.794447422027588 +844 -6.793570041656494 +845 -6.919256210327148 +846 -7.093590259552002 +847 -7.118095874786377 +848 -7.055201053619385 +849 -6.793481349945068 +850 -7.449952602386475 +851 -7.118095874786377 +852 -7.055713653564453 +853 -6.793504238128662 +854 -7.000387668609619 +855 -7.093346118927002 +856 -6.8323073387146 +857 -6.97458028793335 +858 -7.118070125579834 +859 -7.11810302734375 +860 -7.118040561676025 +861 -7.063049793243408 +862 -7.5480170249938965 +863 -7.056722164154053 +864 -6.524348735809326 +865 -6.795313358306885 +866 -7.3563714027404785 +867 -7.11809778213501 +868 -7.076030731201172 +869 -7.012964725494385 +870 -6.97487211227417 +871 -7.0936126708984375 +872 -6.978243350982666 +873 -6.795133590698242 +874 -6.97389554977417 +875 -7.354966640472412 +876 -7.093624591827393 +877 -7.5474467277526855 +878 -7.055596828460693 +879 -7.076204776763916 +880 -7.118040084838867 +881 -7.093614101409912 +882 -6.794797420501709 +883 -7.449982166290283 +884 -7.0934224128723145 +885 -7.451720714569092 +886 -6.800495147705078 +887 -6.975096225738525 +888 -7.543332576751709 +889 -7.4508376121521 +890 -6.79259729385376 +891 -6.736965656280518 +892 -6.705909729003906 +893 -7.1180901527404785 +894 -7.547464847564697 +895 -7.051747798919678 +896 -6.791293621063232 +897 -7.071336269378662 +898 -7.5479416847229 +899 -7.544759750366211 +900 -7.452630996704102 +901 -6.79743766784668 +902 -6.938318252563477 +903 -7.54794454574585 +904 -7.093641757965088 +905 -6.792789459228516 +906 -6.735498905181885 +907 -6.953569412231445 +908 -7.450072765350342 +909 -7.4500885009765625 +910 -6.793933391571045 +911 -7.093616008758545 +912 -7.076068878173828 +913 -6.938619136810303 +914 -7.0558905601501465 +915 -6.832804203033447 +916 -7.546874523162842 +917 -6.793607234954834 +918 -7.0128607749938965 +919 -7.118096828460693 +920 -7.056488037109375 +921 -7.000463485717773 +922 -7.546735763549805 +923 -7.450560092926025 +924 -6.7953925132751465 +925 -7.012757778167725 +926 -7.118092060089111 +927 -6.7967963218688965 +928 -7.547704219818115 +929 -7.547206878662109 +930 -7.542959690093994 +931 -7.051050186157227 +932 -7.0510993003845215 +933 -7.356588840484619 +934 -7.05280065536499 +935 -7.056349277496338 +936 -7.449815273284912 +937 -7.049251556396484 +938 -6.7951788902282715 +939 -7.450057506561279 +940 -7.547722339630127 +941 -7.118076801300049 +942 -6.6941046714782715 +943 -7.11810302734375 +944 -7.546945095062256 +945 -7.45086145401001 +946 -7.547333240509033 +947 -6.799951076507568 +948 -7.548094272613525 +949 -6.9380202293396 +950 -7.093568325042725 +951 -6.78973913192749 +952 -7.056407451629639 +953 -6.832804203033447 +954 -7.055813312530518 +955 -6.792795658111572 +956 -7.0555500984191895 +957 -7.076071262359619 +958 -7.076155185699463 +959 -7.547591686248779 +960 -6.705955982208252 +961 -6.9379496574401855 +962 -7.052740573883057 +963 -6.792765140533447 +964 -7.547813892364502 +965 -7.062536239624023 +966 -7.056725978851318 +967 -6.698997497558594 +968 -6.736448287963867 +969 -6.9741129875183105 +970 -6.9741129875183105 +971 -7.450236797332764 +972 -6.736626148223877 +973 -7.0521159172058105 +974 -7.049663066864014 +975 -6.794753551483154 +976 -7.450061798095703 +977 -7.048206806182861 +978 -6.93267297744751 +979 -6.698988437652588 +980 -6.790439128875732 +981 -6.789027690887451 +982 -7.449626922607422 +983 -7.546258449554443 +984 -6.79923677444458 +985 -6.794271945953369 +986 -7.051040172576904 +987 -7.071336269378662 +988 -7.093534469604492 +989 -6.795745372772217 +990 -7.5476555824279785 +991 -7.076021194458008 +992 -7.056188106536865 +993 -6.80238676071167 +994 -7.0935797691345215 +995 -7.451638698577881 +996 -6.698973178863525 +997 -7.542781352996826 +998 -7.547001361846924 +999 -7.450721263885498 diff --git a/example/python_pkg/MoS2_learn/DRAFFLE/DOutput/energies_unrlxd_seed0.txt b/example/python_pkg/MoS2_learn/DRAFFLE/DOutput/energies_unrlxd_seed0.txt new file mode 100644 index 00000000..81d9dd56 --- /dev/null +++ b/example/python_pkg/MoS2_learn/DRAFFLE/DOutput/energies_unrlxd_seed0.txt @@ -0,0 +1,1000 @@ +0 -5.439432621002197 +1 -5.11580753326416 +2 -4.524250030517578 +3 -4.929441452026367 +4 -5.55303430557251 +5 -6.014692306518555 +6 -6.832276821136475 +7 -7.458506107330322 +8 -5.084995269775391 +9 -6.263925552368164 +10 -7.427446365356445 +11 -7.333681583404541 +12 -6.963590145111084 +13 -6.237878799438477 +14 -6.50153112411499 +15 -6.245410442352295 +16 -6.870492458343506 +17 -6.6146559715271 +18 -6.23619270324707 +19 -5.786721706390381 +20 -6.594813823699951 +21 -5.650233745574951 +22 -7.099336624145508 +23 -6.2539753913879395 +24 -6.311925411224365 +25 -5.731717586517334 +26 -5.786869525909424 +27 -5.970468997955322 +28 -6.520917892456055 +29 -7.2151665687561035 +30 -7.152090072631836 +31 -6.5993332862854 +32 -7.026910305023193 +33 -6.4532341957092285 +34 -6.333413600921631 +35 -6.7963547706604 +36 -6.162900924682617 +37 -6.8585333824157715 +38 -5.8158135414123535 +39 -7.270334720611572 +40 -6.1862711906433105 +41 -6.99377965927124 +42 -7.2041802406311035 +43 -6.417511463165283 +44 -6.081853866577148 +45 -6.502580165863037 +46 -6.57855749130249 +47 -5.904983997344971 +48 -6.15108060836792 +49 -6.58893346786499 +50 -5.91943883895874 +51 -6.588097095489502 +52 -5.8205180168151855 +53 -7.38686990737915 +54 -6.4697723388671875 +55 -6.588369846343994 +56 -5.717360019683838 +57 -6.468092441558838 +58 -6.785816192626953 +59 -5.2465033531188965 +60 -6.758375644683838 +61 -6.01371431350708 +62 -6.7003254890441895 +63 -6.561551570892334 +64 -6.806068420410156 +65 -6.93960428237915 +66 -6.615834712982178 +67 -5.652075290679932 +68 -5.776089191436768 +69 -5.239260673522949 +70 -6.046995639801025 +71 -6.706953048706055 +72 -6.042680263519287 +73 -6.501880168914795 +74 -5.432919025421143 +75 -6.5365447998046875 +76 -6.543062686920166 +77 -6.748092174530029 +78 -6.702897548675537 +79 -6.865842342376709 +80 -6.358603000640869 +81 -6.53521203994751 +82 -6.03813362121582 +83 -6.533372402191162 +84 -7.003140926361084 +85 -6.218671798706055 +86 -6.776834487915039 +87 -5.119011878967285 +88 -6.553421497344971 +89 -6.458396911621094 +90 -6.445089817047119 +91 -6.795530319213867 +92 -6.969998836517334 +93 -5.254971981048584 +94 -6.713369846343994 +95 -6.512434005737305 +96 -6.943491458892822 +97 -6.483182430267334 +98 -6.819857120513916 +99 -6.496835708618164 +100 -6.266757488250732 +101 -5.707845687866211 +102 -6.28787088394165 +103 -5.904983997344971 +104 -6.8084588050842285 +105 -6.6459808349609375 +106 -6.840667724609375 +107 -7.398207187652588 +108 -5.4475932121276855 +109 -6.64308500289917 +110 -6.694264888763428 +111 -6.4276509284973145 +112 -6.350383758544922 +113 -6.81370735168457 +114 -6.205540180206299 +115 -6.783894062042236 +116 -6.914034366607666 +117 -6.583817005157471 +118 -6.158435821533203 +119 -7.076754093170166 +120 -6.483573913574219 +121 -5.538898944854736 +122 -5.8620285987854 +123 -6.816553115844727 +124 -6.050753116607666 +125 -6.48281717300415 +126 -5.828145503997803 +127 -6.792993068695068 +128 -6.791433811187744 +129 -6.129571437835693 +130 -7.124813556671143 +131 -7.535360336303711 +132 -7.194090366363525 +133 -6.46245813369751 +134 -6.969998836517334 +135 -6.262345790863037 +136 -7.4951090812683105 +137 -6.9068474769592285 +138 -6.3098320960998535 +139 -7.3826751708984375 +140 -6.963590145111084 +141 -6.676525115966797 +142 -6.420027256011963 +143 -6.417478084564209 +144 -6.963590145111084 +145 -6.422353267669678 +146 -4.922670364379883 +147 -6.9754462242126465 +148 -6.422353267669678 +149 -7.2151665687561035 +150 -6.2622199058532715 +151 -6.646862506866455 +152 -6.559709072113037 +153 -6.623446941375732 +154 -6.57042932510376 +155 -6.469446659088135 +156 -6.564374923706055 +157 -6.369218349456787 +158 -6.900975704193115 +159 -6.643192291259766 +160 -5.521336078643799 +161 -6.869662761688232 +162 -5.90110445022583 +163 -6.561341762542725 +164 -6.262453556060791 +165 -6.179017543792725 +166 -5.43718957901001 +167 -6.0749359130859375 +168 -4.8434038162231445 +169 -6.9521260261535645 +170 -6.0298027992248535 +171 -7.528890132904053 +172 -6.261254787445068 +173 -6.1130051612854 +174 -6.724157810211182 +175 -4.710474014282227 +176 -6.266735076904297 +177 -5.804323196411133 +178 -6.488542079925537 +179 -6.263902187347412 +180 -6.153462886810303 +181 -6.576426029205322 +182 -6.6710524559021 +183 -5.986611843109131 +184 -7.528890132904053 +185 -6.535951614379883 +186 -6.475011348724365 +187 -6.664536952972412 +188 -6.143489837646484 +189 -6.561971664428711 +190 -6.904020309448242 +191 -6.715170383453369 +192 -7.359335422515869 +193 -6.168903350830078 +194 -6.02813720703125 +195 -7.212800979614258 +196 -6.791616439819336 +197 -6.509400844573975 +198 -6.825297832489014 +199 -6.779115200042725 +200 -7.119298934936523 +201 -6.704564571380615 +202 -6.716461181640625 +203 -6.077487945556641 +204 -6.389312744140625 +205 -6.17611837387085 +206 -6.29960298538208 +207 -6.185794353485107 +208 -7.528890132904053 +209 -6.395829677581787 +210 -6.5348219871521 +211 -5.9736328125 +212 -6.069209575653076 +213 -6.581323623657227 +214 -6.269323348999023 +215 -6.0857834815979 +216 -6.2429351806640625 +217 -3.6318159103393555 +218 -7.493330478668213 +219 -6.626527786254883 +220 -5.715890407562256 +221 -6.6082377433776855 +222 -5.9836506843566895 +223 -6.8286566734313965 +224 -6.748507022857666 +225 -6.604272365570068 +226 -6.572208881378174 +227 -6.142858982086182 +228 -5.806737422943115 +229 -6.8693623542785645 +230 -5.9736409187316895 +231 -5.863032817840576 +232 -6.8137078285217285 +233 -6.58391809463501 +234 -6.6051154136657715 +235 -6.796355724334717 +236 -6.472498416900635 +237 -6.486466884613037 +238 -6.105308532714844 +239 -6.581323623657227 +240 -7.440075397491455 +241 -6.398521423339844 +242 -6.217629909515381 +243 -6.422922611236572 +244 -6.11127233505249 +245 -6.530052661895752 +246 -6.742369174957275 +247 -5.892446041107178 +248 -6.602901935577393 +249 -6.487863063812256 +250 -4.57205867767334 +251 -6.680997848510742 +252 -5.788084506988525 +253 -6.473611354827881 +254 -6.623183727264404 +255 -6.619886875152588 +256 -6.5448317527771 +257 -6.34209680557251 +258 -7.32492208480835 +259 -6.249735355377197 +260 -6.111673831939697 +261 -6.850626468658447 +262 -6.424472332000732 +263 -6.918135166168213 +264 -6.119846343994141 +265 -6.472494602203369 +266 -6.2743353843688965 +267 -6.164763927459717 +268 -6.963590145111084 +269 -6.602901935577393 +270 -7.037768840789795 +271 -6.8938422203063965 +272 -6.853514194488525 +273 -6.62541389465332 +274 -6.0763115882873535 +275 -6.542837619781494 +276 -6.692052364349365 +277 -6.987529754638672 +278 -6.812807559967041 +279 -6.384835720062256 +280 -6.352645397186279 +281 -5.970815181732178 +282 -6.74426794052124 +283 -6.505674839019775 +284 -7.4016432762146 +285 -6.657721996307373 +286 -6.78918981552124 +287 -7.31533670425415 +288 -6.108827590942383 +289 -6.812328338623047 +290 -5.552459716796875 +291 -5.955678462982178 +292 -6.984707355499268 +293 -6.5137763023376465 +294 -6.88118314743042 +295 -5.554352283477783 +296 -6.140628814697266 +297 -6.337731838226318 +298 -6.921431064605713 +299 -7.491060256958008 +300 -6.189545154571533 +301 -6.510129928588867 +302 -6.604272365570068 +303 -6.565860271453857 +304 -6.222854137420654 +305 -6.789473056793213 +306 -6.631296157836914 +307 -6.139902591705322 +308 -6.794895172119141 +309 -5.1736674308776855 +310 -6.289361476898193 +311 -5.400145053863525 +312 -6.532407283782959 +313 -6.604272365570068 +314 -6.242578029632568 +315 -6.993659496307373 +316 -6.8803839683532715 +317 -6.307785511016846 +318 -7.241577625274658 +319 -5.775209426879883 +320 -6.712375640869141 +321 -6.559083461761475 +322 -6.680887222290039 +323 -7.440653324127197 +324 -6.220164775848389 +325 -6.828342437744141 +326 -6.219682693481445 +327 -6.786186695098877 +328 -6.577478408813477 +329 -6.87502908706665 +330 -6.740280628204346 +331 -5.7283935546875 +332 -6.849809169769287 +333 -6.963590145111084 +334 -6.8819966316223145 +335 -6.364305019378662 +336 -6.6082377433776855 +337 -6.480153560638428 +338 -7.333681583404541 +339 -6.147084712982178 +340 -5.6249871253967285 +341 -6.694264888763428 +342 -6.3686981201171875 +343 -5.595339298248291 +344 -5.739292621612549 +345 -6.253220081329346 +346 -7.298761367797852 +347 -6.041726589202881 +348 -6.9149651527404785 +349 -6.824799060821533 +350 -6.644278049468994 +351 -7.409420013427734 +352 -6.643351078033447 +353 -6.9622979164123535 +354 -6.707007884979248 +355 -6.020771503448486 +356 -7.528890132904053 +357 -7.297929763793945 +358 -6.697061538696289 +359 -6.596800327301025 +360 -6.707036972045898 +361 -7.040356159210205 +362 -6.707008361816406 +363 -6.132541656494141 +364 -6.586143493652344 +365 -5.488561153411865 +366 -7.4068145751953125 +367 -4.551242828369141 +368 -6.284719944000244 +369 -5.692460536956787 +370 -5.9079508781433105 +371 -6.6305060386657715 +372 -5.786531925201416 +373 -6.225355625152588 +374 -6.843893527984619 +375 -6.858268737792969 +376 -6.4770660400390625 +377 -6.523928165435791 +378 -6.535951614379883 +379 -5.844699382781982 +380 -6.16433572769165 +381 -6.768784999847412 +382 -6.816064834594727 +383 -6.993659496307373 +384 -5.179678916931152 +385 -6.900975704193115 +386 -7.237449645996094 +387 -6.65650749206543 +388 -6.648919582366943 +389 -6.050753116607666 +390 -6.124139308929443 +391 -6.356044292449951 +392 -7.277647018432617 +393 -6.228721618652344 +394 -6.289602756500244 +395 -6.602822780609131 +396 -6.913888931274414 +397 -6.820362091064453 +398 -6.870138168334961 +399 -6.499908447265625 +400 -6.345492839813232 +401 -6.964742660522461 +402 -6.232656478881836 +403 -5.365877628326416 +404 -6.5760498046875 +405 -6.328838348388672 +406 -6.5232696533203125 +407 -6.26872444152832 +408 -6.026834487915039 +409 -6.8053412437438965 +410 -6.277908802032471 +411 -5.9957804679870605 +412 -5.980494022369385 +413 -6.1477227210998535 +414 -7.23296594619751 +415 -6.481069087982178 +416 -6.545502185821533 +417 -5.7827229499816895 +418 -6.769728183746338 +419 -6.302679061889648 +420 -6.177715301513672 +421 -5.965219974517822 +422 -6.116540431976318 +423 -6.0991530418396 +424 -7.13026762008667 +425 -6.23612642288208 +426 -6.78918981552124 +427 -6.707008361816406 +428 -6.208907604217529 +429 -6.108955383300781 +430 -6.390949726104736 +431 -6.322463512420654 +432 -5.704238414764404 +433 -5.689025402069092 +434 -6.80035400390625 +435 -6.486325740814209 +436 -6.7910003662109375 +437 -6.708517074584961 +438 -6.128723621368408 +439 -6.803218364715576 +440 -6.575963497161865 +441 -6.701356410980225 +442 -6.356044769287109 +443 -6.964282989501953 +444 -6.822352886199951 +445 -6.738226413726807 +446 -6.353747844696045 +447 -5.900901794433594 +448 -6.016167163848877 +449 -7.430659770965576 +450 -7.06836462020874 +451 -6.664663314819336 +452 -5.945468902587891 +453 -5.879587650299072 +454 -5.426715850830078 +455 -6.280966281890869 +456 -6.130030155181885 +457 -6.582733631134033 +458 -7.49097204208374 +459 -6.244431972503662 +460 -6.239319324493408 +461 -6.7427496910095215 +462 -5.592893123626709 +463 -7.383040904998779 +464 -6.99420690536499 +465 -5.916861057281494 +466 -6.572208881378174 +467 -6.420027256011963 +468 -6.43418550491333 +469 -6.205414295196533 +470 -6.265059947967529 +471 -6.653570652008057 +472 -6.700724124908447 +473 -6.229970455169678 +474 -6.488996982574463 +475 -5.631058216094971 +476 -6.7928900718688965 +477 -6.8137078285217285 +478 -6.242016315460205 +479 -6.166800022125244 +480 -6.284239292144775 +481 -6.602901935577393 +482 -6.667200565338135 +483 -6.795027256011963 +484 -6.91208028793335 +485 -6.268290996551514 +486 -6.572208881378174 +487 -6.535984039306641 +488 -6.444800853729248 +489 -6.181887149810791 +490 -5.941664218902588 +491 -6.215440273284912 +492 -6.107812881469727 +493 -6.791616439819336 +494 -6.697607040405273 +495 -7.541717052459717 +496 -6.81866455078125 +497 -6.296201229095459 +498 -6.702157497406006 +499 -6.846564769744873 +500 -6.791616916656494 +501 -5.457101345062256 +502 -7.2896728515625 +503 -6.108955383300781 +504 -5.978688716888428 +505 -6.572208881378174 +506 -7.034632205963135 +507 -6.8066325187683105 +508 -6.267288684844971 +509 -6.357181549072266 +510 -6.665124416351318 +511 -6.244955539703369 +512 -6.788855075836182 +513 -6.549797534942627 +514 -6.741611003875732 +515 -6.244431972503662 +516 -5.399784564971924 +517 -6.9622979164123535 +518 -7.221188068389893 +519 -6.7863450050354 +520 -5.993732452392578 +521 -6.8053412437438965 +522 -5.786211013793945 +523 -6.519505023956299 +524 -6.576207637786865 +525 -4.336033821105957 +526 -6.208768844604492 +527 -6.081243515014648 +528 -5.890411853790283 +529 -6.996330738067627 +530 -6.583486080169678 +531 -6.659826278686523 +532 -6.512658596038818 +533 -6.891537189483643 +534 -6.359731197357178 +535 -6.8530731201171875 +536 -6.286237716674805 +537 -7.492401123046875 +538 -6.137361526489258 +539 -6.219372272491455 +540 -6.109287261962891 +541 -6.610209941864014 +542 -6.415506839752197 +543 -6.005786895751953 +544 -6.678064346313477 +545 -7.529987812042236 +546 -6.964075565338135 +547 -6.703866958618164 +548 -5.979489803314209 +549 -6.409290790557861 +550 -5.662775039672852 +551 -6.8150105476379395 +552 -6.289505481719971 +553 -6.7112250328063965 +554 -6.630361080169678 +555 -6.2968268394470215 +556 -6.063464641571045 +557 -6.545027256011963 +558 -7.356126308441162 +559 -5.7204670906066895 +560 -7.26866340637207 +561 -6.55731725692749 +562 -6.1603522300720215 +563 -6.838881015777588 +564 -6.76262903213501 +565 -6.050753116607666 +566 -5.890600681304932 +567 -6.596292495727539 +568 -5.327243804931641 +569 -5.677021503448486 +570 -6.7565765380859375 +571 -7.219502925872803 +572 -5.704214572906494 +573 -6.177651882171631 +574 -6.8137078285217285 +575 -6.91039514541626 +576 -5.704305171966553 +577 -6.764313220977783 +578 -7.330379486083984 +579 -6.604794025421143 +580 -6.425343036651611 +581 -5.912895679473877 +582 -6.779933929443359 +583 -6.469249248504639 +584 -6.774111270904541 +585 -6.355940341949463 +586 -6.820471286773682 +587 -6.531894683837891 +588 -7.074878692626953 +589 -7.537587642669678 +590 -6.998938083648682 +591 -5.534280300140381 +592 -6.963221073150635 +593 -6.572208881378174 +594 -6.483057022094727 +595 -5.878391265869141 +596 -6.806909084320068 +597 -6.983592987060547 +598 -5.756591320037842 +599 -6.847940921783447 +600 -7.424535751342773 +601 -6.294111251831055 +602 -6.300839900970459 +603 -6.882969379425049 +604 -6.048686504364014 +605 -5.468034267425537 +606 -6.604272365570068 +607 -6.561145305633545 +608 -6.6458420753479 +609 -5.308788776397705 +610 -6.79315710067749 +611 -5.998427867889404 +612 -6.7740607261657715 +613 -6.319569110870361 +614 -6.794179439544678 +615 -6.781343936920166 +616 -6.238060474395752 +617 -6.392381191253662 +618 -6.126582622528076 +619 -5.4970383644104 +620 -6.691104888916016 +621 -6.590138912200928 +622 -5.337392807006836 +623 -5.636280059814453 +624 -6.623285293579102 +625 -6.340274333953857 +626 -6.6312479972839355 +627 -6.3155131340026855 +628 -6.221874237060547 +629 -6.410015106201172 +630 -6.602901935577393 +631 -7.003117084503174 +632 -5.7939229011535645 +633 -6.862178802490234 +634 -6.090446949005127 +635 -6.963221073150635 +636 -6.696075439453125 +637 -6.93960428237915 +638 -6.622761249542236 +639 -6.294520854949951 +640 -6.366597652435303 +641 -6.4755682945251465 +642 -6.950560092926025 +643 -4.903691291809082 +644 -6.939820766448975 +645 -6.0360589027404785 +646 -6.7011542320251465 +647 -5.626280307769775 +648 -6.818963527679443 +649 -5.185654163360596 +650 -6.252720355987549 +651 -6.929134368896484 +652 -6.14686393737793 +653 -6.581165313720703 +654 -6.775871276855469 +655 -6.341787815093994 +656 -7.540250778198242 +657 -5.929459095001221 +658 -6.833700180053711 +659 -6.974298000335693 +660 -6.811090469360352 +661 -6.2633957862854 +662 -6.693480968475342 +663 -7.006764888763428 +664 -6.1568732261657715 +665 -6.616025924682617 +666 -5.320479869842529 +667 -5.709953308105469 +668 -6.290004253387451 +669 -6.531886577606201 +670 -5.991270065307617 +671 -6.43444299697876 +672 -4.867857933044434 +673 -6.489899158477783 +674 -5.986611843109131 +675 -6.148913860321045 +676 -5.902590274810791 +677 -6.680528163909912 +678 -6.712636470794678 +679 -7.270643711090088 +680 -6.243566989898682 +681 -6.962347030639648 +682 -6.270507335662842 +683 -6.407174587249756 +684 -6.737786769866943 +685 -6.843289852142334 +686 -6.6748528480529785 +687 -6.258306980133057 +688 -6.881114482879639 +689 -6.30425500869751 +690 -6.650346279144287 +691 -5.836801052093506 +692 -6.228392124176025 +693 -7.472253322601318 +694 -6.599390506744385 +695 -5.029875755310059 +696 -5.741118907928467 +697 -6.285105228424072 +698 -6.320761203765869 +699 -6.20680570602417 +700 -6.71416711807251 +701 -5.089524269104004 +702 -6.196092128753662 +703 -6.007960796356201 +704 -6.795953750610352 +705 -6.736456394195557 +706 -6.660743236541748 +707 -5.936204433441162 +708 -6.572208881378174 +709 -6.798946857452393 +710 -6.963221073150635 +711 -5.870168209075928 +712 -5.991008281707764 +713 -6.639972686767578 +714 -7.537587642669678 +715 -6.804408550262451 +716 -6.495702743530273 +717 -6.768346786499023 +718 -7.349646091461182 +719 -6.02607536315918 +720 -6.43428373336792 +721 -5.130282402038574 +722 -6.699483394622803 +723 -6.814485549926758 +724 -6.826610088348389 +725 -6.242460250854492 +726 -7.528890132904053 +727 -6.758763790130615 +728 -6.365781307220459 +729 -6.168005466461182 +730 -6.475568771362305 +731 -6.228721618652344 +732 -6.6228461265563965 +733 -6.169544696807861 +734 -6.221654415130615 +735 -6.681626796722412 +736 -6.275174617767334 +737 -6.8372368812561035 +738 -6.252910614013672 +739 -6.485711574554443 +740 -6.647480487823486 +741 -6.520710468292236 +742 -6.6698174476623535 +743 -6.97860860824585 +744 -6.670053958892822 +745 -4.725570201873779 +746 -6.792317867279053 +747 -6.321675777435303 +748 -6.650041103363037 +749 -7.2047038078308105 +750 -6.583908557891846 +751 -6.626328945159912 +752 -6.3831305503845215 +753 -7.54131555557251 +754 -6.023910999298096 +755 -4.674920082092285 +756 -6.063464641571045 +757 -6.2264018058776855 +758 -5.98655366897583 +759 -6.735864162445068 +760 -7.199441432952881 +761 -6.350137233734131 +762 -6.485189914703369 +763 -7.347785472869873 +764 -6.201258182525635 +765 -6.9917426109313965 +766 -6.470944881439209 +767 -6.060783386230469 +768 -6.644278049468994 +769 -6.297891139984131 +770 -6.0140533447265625 +771 -6.099843502044678 +772 -6.854241847991943 +773 -6.615113735198975 +774 -5.802405834197998 +775 -6.674457550048828 +776 -7.270304203033447 +777 -6.157346248626709 +778 -6.4153618812561035 +779 -7.537587642669678 +780 -6.294668674468994 +781 -5.688279628753662 +782 -6.612044811248779 +783 -6.119148254394531 +784 -6.600870609283447 +785 -6.880878925323486 +786 -7.1023383140563965 +787 -6.734464168548584 +788 -6.405989170074463 +789 -6.32459831237793 +790 -6.811116695404053 +791 -6.3221917152404785 +792 -6.481805324554443 +793 -6.61353874206543 +794 -6.050753116607666 +795 -6.568681240081787 +796 -6.261021137237549 +797 -6.94320821762085 +798 -6.15363073348999 +799 -5.596400737762451 +800 -5.994585037231445 +801 -6.845506191253662 +802 -6.829324722290039 +803 -6.963590145111084 +804 -6.794052600860596 +805 -6.600881099700928 +806 -7.294731616973877 +807 -6.284246444702148 +808 -6.812328338623047 +809 -5.84301233291626 +810 -5.879587650299072 +811 -6.572208881378174 +812 -6.800414562225342 +813 -6.820638179779053 +814 -6.5776519775390625 +815 -6.736337184906006 +816 -6.436402797698975 +817 -7.413949489593506 +818 -6.799455165863037 +819 -6.221654415130615 +820 -6.922023296356201 +821 -6.8048996925354 +822 -7.4141387939453125 +823 -6.206987380981445 +824 -6.766625881195068 +825 -7.224491119384766 +826 -5.832010269165039 +827 -5.904642581939697 +828 -6.6377129554748535 +829 -6.094560146331787 +830 -6.646139621734619 +831 -6.455507755279541 +832 -6.514032363891602 +833 -7.3250956535339355 +834 -6.19838285446167 +835 -6.060161590576172 +836 -6.80927848815918 +837 -5.788600921630859 +838 -5.725934982299805 +839 -6.477161407470703 +840 -6.5047078132629395 +841 -7.2284836769104 +842 -7.148924350738525 +843 -5.874205112457275 +844 -4.947024345397949 +845 -6.322462558746338 +846 -6.691103458404541 +847 -6.947090148925781 +848 -6.4085259437561035 +849 -5.709211826324463 +850 -7.342225551605225 +851 -7.00311803817749 +852 -5.179906845092773 +853 -6.457396030426025 +854 -6.619886875152588 +855 -6.581323623657227 +856 -6.804899215698242 +857 -6.947991847991943 +858 -6.387490749359131 +859 -6.708332061767578 +860 -6.973057270050049 +861 -5.850315570831299 +862 -6.93960428237915 +863 -6.862849712371826 +864 -6.177799701690674 +865 -6.629499435424805 +866 -6.122666835784912 +867 -7.003610610961914 +868 -5.899200916290283 +869 -5.720164775848389 +870 -6.964075565338135 +871 -6.74318265914917 +872 -6.447465896606445 +873 -6.198060989379883 +874 -6.963236331939697 +875 -7.2687087059021 +876 -6.56741189956665 +877 -7.330379486083984 +878 -6.693480014801025 +879 -6.578784942626953 +880 -6.973056793212891 +881 -6.36438512802124 +882 -6.317582607269287 +883 -6.78918981552124 +884 -6.722846508026123 +885 -7.207687854766846 +886 -5.579321384429932 +887 -6.84853982925415 +888 -7.212961673736572 +889 -6.807468414306641 +890 -6.153398036956787 +891 -6.087053298950195 +892 -6.163703918457031 +893 -6.241784572601318 +894 -7.189981937408447 +895 -6.8228278160095215 +896 -6.2049241065979 +897 -6.65678596496582 +898 -7.500913143157959 +899 -6.640174388885498 +900 -7.400453090667725 +901 -6.129035472869873 +902 -6.047262668609619 +903 -6.685324192047119 +904 -6.461513042449951 +905 -6.485189914703369 +906 -6.318548202514648 +907 -6.7126007080078125 +908 -6.086910247802734 +909 -6.1151442527771 +910 -5.32199239730835 +911 -6.701694488525391 +912 -6.0071892738342285 +913 -6.8137078285217285 +914 -6.753758907318115 +915 -6.8053412437438965 +916 -7.47405481338501 +917 -6.402263164520264 +918 -4.875614166259766 +919 -6.349202632904053 +920 -5.859485149383545 +921 -6.637302398681641 +922 -6.770124912261963 +923 -6.1208720207214355 +924 -6.30425500869751 +925 -6.470655918121338 +926 -6.324474811553955 +927 -6.499925136566162 +928 -7.333681583404541 +929 -7.381059169769287 +930 -6.687955379486084 +931 -6.725160121917725 +932 -6.627099514007568 +933 -6.24368143081665 +934 -6.676666259765625 +935 -6.3375020027160645 +936 -6.160376071929932 +937 -6.812517166137695 +938 -5.851600646972656 +939 -4.767414093017578 +940 -7.414329528808594 +941 -6.354286193847656 +942 -5.61029577255249 +943 -6.376203536987305 +944 -6.243474960327148 +945 -7.147165775299072 +946 -6.815592288970947 +947 -6.347068786621094 +948 -5.729650974273682 +949 -6.300839900970459 +950 -6.827298641204834 +951 -6.022019863128662 +952 -6.820248126983643 +953 -6.8053412437438965 +954 -6.697537899017334 +955 -6.642275333404541 +956 -6.822595119476318 +957 -6.783483028411865 +958 -6.690282344818115 +959 -6.864137172698975 +960 -5.718269348144531 +961 -6.424543380737305 +962 -6.248586177825928 +963 -5.698877811431885 +964 -6.100618839263916 +965 -5.878108978271484 +966 -6.109066486358643 +967 -5.1904096603393555 +968 -6.304131984710693 +969 -6.963590145111084 +970 -6.963590145111084 +971 -6.906280994415283 +972 -6.288158416748047 +973 -6.198832035064697 +974 -6.370333194732666 +975 -6.522592067718506 +976 -6.124022006988525 +977 -6.7445902824401855 +978 -6.222469806671143 +979 -6.096157073974609 +980 -5.84026575088501 +981 -5.74895715713501 +982 -7.362472057342529 +983 -6.835141658782959 +984 -5.98054313659668 +985 -6.0611572265625 +986 -6.356044292449951 +987 -6.199060916900635 +988 -6.320735931396484 +989 -6.600881099700928 +990 -6.229368686676025 +991 -5.646134853363037 +992 -6.131338596343994 +993 -4.546936988830566 +994 -6.8321051597595215 +995 -7.196407794952393 +996 -5.6539740562438965 +997 -7.382803440093994 +998 -5.803358554840088 +999 -6.826992034912109 diff --git a/example/python_pkg/MoS2_learn/DRAFFLE/DOutput/rlxd_structures_seed0.traj b/example/python_pkg/MoS2_learn/DRAFFLE/DOutput/rlxd_structures_seed0.traj new file mode 100644 index 00000000..d6a0e974 Binary files /dev/null and b/example/python_pkg/MoS2_learn/DRAFFLE/DOutput/rlxd_structures_seed0.traj differ diff --git a/example/python_pkg/MoS2_learn/DRAFFLE/DOutput/unrlxd_structures_seed0.traj b/example/python_pkg/MoS2_learn/DRAFFLE/DOutput/unrlxd_structures_seed0.traj new file mode 100644 index 00000000..7a6ab7ba Binary files /dev/null and b/example/python_pkg/MoS2_learn/DRAFFLE/DOutput/unrlxd_structures_seed0.traj differ diff --git a/example/python_pkg/MoS2_learn/learn.py b/example/python_pkg/MoS2_learn/DRAFFLE/learn.py similarity index 88% rename from example/python_pkg/MoS2_learn/learn.py rename to example/python_pkg/MoS2_learn/DRAFFLE/learn.py index 2966fbf2..38d61596 100644 --- a/example/python_pkg/MoS2_learn/learn.py +++ b/example/python_pkg/MoS2_learn/DRAFFLE/learn.py @@ -1,4 +1,5 @@ from chgnet.model import CHGNetCalculator +from ase.calculators.singlepoint import SinglePointCalculator from raffle.generator import raffle_generator from ase import build, Atoms from ase.optimize import FIRE @@ -125,7 +126,7 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct num_structures = 5, stoichiometry = { 'Mo': 1 , 'S': 4 }, seed = seed*1000+iter, - method_probab = {"void": 0.5, "rand": 0.05, "walk": 0.5, "grow": 0.0, "min": 1.0}, + method_ratio = {"void": 0.5, "rand": 0.05, "walk": 0.5, "grow": 0.0, "min": 1.0}, verbose = 0, ) @@ -147,21 +148,31 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct write(iterdir+f"POSCAR_unrlxd_{i}", generated_structures[num_structures_old + i]) print(f"Structure {i} energy per atom: {generated_structures[num_structures_old + i].get_potential_energy() / len(generated_structures[num_structures_old + i])}") unrlxd_structures.append(generated_structures[num_structures_old + i].copy()) + unrlxd_structures[-1].calc = SinglePointCalculator( + generated_structures[num_structures_old + i], + energy=generated_structures[num_structures_old + i].get_potential_energy(), + forces=generated_structures[num_structures_old + i].get_forces() + ) # Start parallel execution print("Starting parallel execution") results = Parallel(n_jobs=5)( - delayed(process_structure)(i, generated_structures[i], num_structures_old, calc_params, optimise_structure, iteration=seed, calc=calc) + delayed(process_structure)(i, generated_structures[i].copy(), num_structures_old, calc_params, optimise_structure, iteration=seed, calc=calc) for i in range(num_structures_old, num_structures_new) ) # Wait for all futures to complete for j, result in enumerate(results): - generated_structures[j+num_structures_old], energy_unrlxd[j], energy_rlxd[j] = result - if generated_structures[j+num_structures_old] is None: + generated_structures[num_structures_old + j], energy_unrlxd[j], energy_rlxd[j] = result + if generated_structures[num_structures_old + j] is None: print("Structure failed the checks") continue - rlxd_structures.append(generated_structures[j+num_structures_old].copy()) + rlxd_structures.append(generated_structures[num_structures_old + j].copy()) + rlxd_structures[-1].calc = SinglePointCalculator( + generated_structures[j+num_structures_old], + energy=generated_structures[num_structures_old + j].get_potential_energy(), + forces=generated_structures[num_structures_old + j].get_forces() + ) print("All futures completed") # Remove structures that failed the checks diff --git a/example/python_pkg/MoS2_learn/pca.ipynb b/example/python_pkg/MoS2_learn/DRAFFLE/pca.ipynb similarity index 85% rename from example/python_pkg/MoS2_learn/pca.ipynb rename to example/python_pkg/MoS2_learn/DRAFFLE/pca.ipynb index 39f2d639..353d99f7 100644 --- a/example/python_pkg/MoS2_learn/pca.ipynb +++ b/example/python_pkg/MoS2_learn/DRAFFLE/pca.ipynb @@ -17,7 +17,8 @@ "from agox.utils.graph_sorting import Analysis\n", "\n", "import numpy as np\n", - "from sklearn.decomposition import PCA" + "from sklearn.decomposition import PCA\n", + "from matplotlib.ticker import (MultipleLocator, AutoMinorLocator)" ] }, { @@ -55,7 +56,7 @@ "from agox.models.descriptors.fingerprint import Fingerprint\n", "# from agox.models.descriptors import Voronoi\n", "\n", - "template = read(\"DTMP\"+identifier+\"/unrlxd_structures_seed0.traj\")\n", + "template = read(\"DOutput\"+identifier+\"/unrlxd_structures_seed0.traj\")\n", "# diamond = bulk(\"C\", \"diamond\", a=3.567) # Lattice constant for diamond cubic carbon\n", "confinement_cell = template.cell.copy()\n", "confinement_corner = np.array([0, 0, 0])\n", @@ -91,7 +92,7 @@ "outputs": [], "source": [ "## Load the unrelaxed structures\n", - "unrlxd_structures = read(\"DTMP\"+identifier+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "unrlxd_structures = read(\"DOutput\"+identifier+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", "for structure in unrlxd_structures:\n", " structure.calc = calc" ] @@ -103,7 +104,7 @@ "outputs": [], "source": [ "## Load the relaxed structures\n", - "rlxd_structures = read(\"DTMP\"+identifier+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "rlxd_structures = read(\"DOutput\"+identifier+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", "for structure in rlxd_structures:\n", " structure.calc = calc" ] @@ -115,10 +116,10 @@ "outputs": [], "source": [ "## Get MoS2 H-phase and T-phase and attach calculator and calculate energy\n", - "H_phase = read(\"MoS2_H-phase.poscar\")\n", + "H_phase = read(\"../MoS2_H-phase.poscar\")\n", "H_phase.set_cell(rlxd_structures[0].get_cell())\n", "H_phase.calc = calc\n", - "T_phase = read(\"MoS2_T-phase.poscar\")\n", + "T_phase = read(\"../MoS2_T-phase.poscar\")\n", "T_phase.set_cell(rlxd_structures[0].get_cell())\n", "T_phase.calc = calc\n", "energies_per_atom = [H_phase.get_potential_energy() / len(H_phase), T_phase.get_potential_energy() / len(T_phase)]\n", @@ -135,7 +136,7 @@ "## Read energies from energies_unrlxd_seed0.txt and add to the respective structures using a SinglePointCalculator\n", "## The file has the form \"index energy\"\n", "## This is done because there seem to be issues with storing the energy in the ASE trajectory file for some setups\n", - "filename = \"DTMP\"+identifier+\"/energies_unrlxd_seed\"+str(seed)+\".txt\"\n", + "filename = \"DOutput\"+identifier+\"/energies_unrlxd_seed\"+str(seed)+\".txt\"\n", "with open(filename) as f:\n", " for line in f:\n", " index, energy = line.split()\n", @@ -144,7 +145,7 @@ " unrlxd_structures[index].calc = SinglePointCalculator(unrlxd_structures[index], energy=energy * len(unrlxd_structures[index]))\n", "\n", "\n", - "filename = \"DTMP\"+identifier+\"/energies_rlxd_seed\"+str(seed)+\".txt\"\n", + "filename = \"DOutput\"+identifier+\"/energies_rlxd_seed\"+str(seed)+\".txt\"\n", "with open(filename) as f:\n", " for line in f:\n", " index, energy = line.split()\n", @@ -183,8 +184,8 @@ "metadata": {}, "outputs": [], "source": [ - "print(\"H-phase cell:\", read(\"MoS2_H-phase.poscar\").get_cell())\n", - "print(\"T-phase cell:\", read(\"MoS2_T-phase.poscar\").get_cell())\n", + "print(\"H-phase cell:\", read(\"../MoS2_H-phase.poscar\").get_cell())\n", + "print(\"T-phase cell:\", read(\"../MoS2_T-phase.poscar\").get_cell())\n", "print(\"Unrelaxed cell:\", unrlxd_structures[0].get_cell())\n", "print(\"Relaxed cell:\", rlxd_structures[0].get_cell())" ] @@ -288,32 +289,29 @@ " if ax == axes[1]:\n", " ax.legend(fontsize=10)\n", " handles, labels = ax.get_legend_handles_labels()\n", - " ax.legend(handles[::-1], labels[::-1], facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, loc='upper right')\n", + " ax.legend(handles[::-1], labels[::-1], facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, loc='upper right', fontsize=20, handletextpad=0.1)\n", "\n", "## Add labels\n", - "fig.text(0.5, 0.04, 'Principal Component 1', ha='center', fontsize=15)\n", - "axes[0].set_ylabel('Principal Component 2', fontsize=15)\n", - "axes[0].set_title('Unrelaxed')\n", - "axes[1].set_title('Relaxed')\n", - "if identifier == \"_VASP\":\n", - " if rlxd_string == \"rlxd\":\n", - " xlims = [-11, 8]\n", - " ylims = [-5, 6]\n", - " else:\n", - " xlims = [-9, 13]\n", - " ylims = [-7, 12]\n", - "else:\n", - " if rlxd_string == \"rlxd\":\n", + "fig.text(0.5, 0.0, 'Principal component 1', ha='center', fontsize=20)\n", + "axes[0].set_ylabel('Principal component 2', fontsize=20)\n", + "axes[0].set_title('Unrelaxed', fontsize=20)\n", + "axes[1].set_title('Relaxed', fontsize=20)\n", + "if rlxd_string == \"rlxd\":\n", " xlims = [-15, 6]\n", " ylims = [-3, 11]\n", - " else:\n", + "else:\n", " xlims = [-10, 39]\n", " ylims = [-3, 30]\n", "\n", "for ax in axes:\n", - " ax.tick_params(axis='both', direction='in')\n", - " ax.set_xlim(xlims)\n", - " ax.set_ylim(ylims)\n", + " # ax.set_xticks(np.arange(xlims[0], xlims[1]+1, 5), minor=True)\n", + " ax.tick_params(axis='both', direction='in', length=6, labelsize=20)\n", + " # ax.yaxis.set_major_locator(MultipleLocator(3))\n", + " ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.xaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.tick_params(axis='both', which='minor', length=3, direction='in')\n", + " ax.set_xlim(xlims)\n", + " ax.set_ylim(ylims)\n", "\n", "## Unify tick labels\n", "xticks = axes[0].get_xticks()\n", @@ -334,7 +332,10 @@ "\n", "## Add colorbar next to the axes\n", "cbar = fig.colorbar(axes[1].collections[0], ax=axes, orientation='vertical', fraction=0.085, pad=0.02)\n", - "cbar.set_label('Formation energy (eV/atom)', fontsize=15)\n", + "cbar.ax.tick_params(labelsize=20)\n", + "cbar.ax.yaxis.set_major_locator(MultipleLocator(1))\n", + "cbar.ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + "cbar.set_label('Formation energy (eV/atom)', fontsize=20)\n", "\n", "## Save the figure\n", "plt.savefig('MoS2_RAFFLE'+identifier+'_pca_'+rlxd_string+'_fit_seed'+str(seed)+'.pdf', bbox_inches='tight', pad_inches=0, facecolor=fig.get_facecolor(), edgecolor='none')" @@ -357,7 +358,7 @@ "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", - "version": "3.12.2" + "version": "3.12.8" } }, "nbformat": 4, diff --git a/example/python_pkg/MoS2_learn/DRSS/DOutput/rlxd_structures_seed0.traj b/example/python_pkg/MoS2_learn/DRSS/DOutput/rlxd_structures_seed0.traj new file mode 100644 index 00000000..34da8917 Binary files /dev/null and b/example/python_pkg/MoS2_learn/DRSS/DOutput/rlxd_structures_seed0.traj differ diff --git a/example/python_pkg/MoS2_learn/DRSS/DOutput/unrlxd_structures_seed0.traj b/example/python_pkg/MoS2_learn/DRSS/DOutput/unrlxd_structures_seed0.traj new file mode 100644 index 00000000..9cd76795 Binary files /dev/null and b/example/python_pkg/MoS2_learn/DRSS/DOutput/unrlxd_structures_seed0.traj differ diff --git a/example/python_pkg/MoS2_learn/DRSS/pca.ipynb b/example/python_pkg/MoS2_learn/DRSS/pca.ipynb new file mode 100644 index 00000000..b3bb0c17 --- /dev/null +++ b/example/python_pkg/MoS2_learn/DRSS/pca.ipynb @@ -0,0 +1,372 @@ +{ + "cells": [ + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "import matplotlib.pyplot as plt\n", + "%matplotlib inline\n", + "\n", + "# matplotlib.use(\"Agg\")\n", + "\n", + "from ase.io import read\n", + "from agox.databases import Database\n", + "from agox.environments import Environment\n", + "from agox.utils.graph_sorting import Analysis\n", + "\n", + "import numpy as np\n", + "from sklearn.decomposition import PCA\n", + "from matplotlib.ticker import (MultipleLocator, AutoMinorLocator)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set up the plotting environment\n", + "# matplotlib.rcParams.update(matplotlib.rcParamsDefault)\n", + "plt.rc('text', usetex=True)\n", + "plt.rc('font', family='cmr10', size=12)\n", + "plt.rcParams[\"axes.formatter.use_mathtext\"] = True" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set the plotting parameters\n", + "seed = 0\n", + "identifier = \"\"\n", + "# min_energy = -" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set the descriptors\n", + "from agox.models.descriptors.fingerprint import Fingerprint\n", + "# from agox.models.descriptors import Voronoi\n", + "\n", + "template = read(\"DOutput\"+identifier+\"/unrlxd_structures_seed0.traj\")\n", + "# diamond = bulk(\"C\", \"diamond\", a=3.567) # Lattice constant for diamond cubic carbon\n", + "confinement_cell = template.cell.copy()\n", + "confinement_corner = np.array([0, 0, 0])\n", + "environment = Environment(\n", + " template=template,\n", + " symbols=\"\",\n", + " confinement_cell=confinement_cell,\n", + " confinement_corner=confinement_corner,\n", + " box_constraint_pbc=[True, True, True], # Confinement is periodic in all directions.\n", + ")\n", + "descriptor = Fingerprint(environment=environment)\n", + "# graph_descriptor = Voronoi(\n", + "# covalent_bond_scale_factor=1.3, n_points=8, angle_from_central_atom=20, environment=None\n", + "# )\n" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set the calculators\n", + "from chgnet.model import CHGNetCalculator\n", + "from ase.calculators.singlepoint import SinglePointCalculator\n", + "calc = CHGNetCalculator()" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Load the unrelaxed structures\n", + "unrlxd_structures = read(\"DOutput\"+identifier+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "for structure in unrlxd_structures:\n", + " structure.calc = calc" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Load the relaxed structures\n", + "rlxd_structures = read(\"DOutput\"+identifier+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "for structure in rlxd_structures:\n", + " structure.calc = calc" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Get MoS2 H-phase and T-phase and attach calculator and calculate energy\n", + "H_phase = read(\"../MoS2_H-phase.poscar\")\n", + "H_phase.set_cell(rlxd_structures[0].get_cell())\n", + "H_phase.calc = calc\n", + "T_phase = read(\"../MoS2_T-phase.poscar\")\n", + "T_phase.set_cell(rlxd_structures[0].get_cell())\n", + "T_phase.calc = calc\n", + "energies_per_atom = [H_phase.get_potential_energy() / len(H_phase), T_phase.get_potential_energy() / len(T_phase)]\n", + "min_energy = np.min(energies_per_atom)\n", + "print(\"H/T-phase min energy: \", min_energy)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "# ## Read energies from energies_unrlxd_seed0.txt and add to the respective structures using a SinglePointCalculator\n", + "# ## The file has the form \"index energy\"\n", + "# ## This is done because there seem to be issues with storing the energy in the ASE trajectory file for some setups\n", + "# filename = \"DOutput\"+identifier+\"/energies_unrlxd_seed\"+str(seed)+\".txt\"\n", + "# with open(filename) as f:\n", + "# for line in f:\n", + "# index, energy = line.split()\n", + "# index = int(index)\n", + "# energy = float(energy)\n", + "# unrlxd_structures[index].calc = SinglePointCalculator(unrlxd_structures[index], energy=energy * len(unrlxd_structures[index]))\n", + "\n", + "\n", + "# filename = \"DOutput\"+identifier+\"/energies_rlxd_seed\"+str(seed)+\".txt\"\n", + "# with open(filename) as f:\n", + "# for line in f:\n", + "# index, energy = line.split()\n", + "# index = int(index)\n", + "# energy = float(energy)\n", + "# rlxd_structures[index].calc = SinglePointCalculator(rlxd_structures[index], energy=energy * len(rlxd_structures[index]))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Calculate energies per atom for each unrelaxed structure\n", + "energies_per_atom = [structure.get_potential_energy() / len(structure) for structure in unrlxd_structures]\n", + "unrlxd_delta_en_per_atom = np.array(energies_per_atom) - min_energy\n", + "print(\"Unrelaxed min energy: \", np.min(energies_per_atom))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Calculate energies per atom for each relaxed structure\n", + "energies_per_atom = [structure.get_potential_energy() / len(structure) for structure in rlxd_structures]\n", + "rlxd_delta_en_per_atom = np.array(energies_per_atom) - min_energy\n", + "print(\"Relaxed min energy: \", np.min(energies_per_atom))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "print(\"H-phase cell:\", read(\"../MoS2_H-phase.poscar\").get_cell())\n", + "print(\"T-phase cell:\", read(\"../MoS2_T-phase.poscar\").get_cell())\n", + "print(\"Unrelaxed cell:\", unrlxd_structures[0].get_cell())\n", + "print(\"Relaxed cell:\", rlxd_structures[0].get_cell())" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "if abs( np.min(energies_per_atom) - min_energy ) > 5e-2:\n", + " print(\"Minimum energy per atom is not zero. Check the energy calculation.\")" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set up the PCA\n", + "pca = PCA(n_components=2)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Fit the PCA model to the unrelaxed or relaxed structures\n", + "rlxd_string = \"rlxd\"" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Save pca model\n", + "import pickle\n", + "if False:\n", + " # pca.fit(np.squeeze([arr for arr in descriptor.get_features(unrlxd_structures + [H_phase, T_phase])]))\n", + " # with open(\"pca_model\"+identifier+\"_all_unrlxd_\"+str(seed)+\".pkl\", \"wb\") as f:\n", + " pca.fit(np.squeeze([arr for arr in descriptor.get_features(unrlxd_structures + [H_phase] + [T_phase])]))\n", + " with open(\"pca_model\"+identifier+\"_all_unrlxd_\"+str(seed)+\".pkl\", \"wb\") as f:\n", + " pickle.dump(pca, f)\n", + "\n", + "## Load pca model\n", + "with open(\"../DRAFFLE/pca_model_all_\"+rlxd_string+\"_0.pkl\", \"rb\") as f:\n", + " pca = pickle.load(f)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Transform the unrelaxed and relaxed structures to the reduced space\n", + "unrlxd_X_reduced = pca.transform(np.squeeze([arr for arr in descriptor.get_features(unrlxd_structures)]))\n", + "rlxd_X_reduced = pca.transform(np.squeeze([arr for arr in descriptor.get_features(rlxd_structures)])) # + [H_phase] + [T_phase])]))\n", + "H_phase_X_reduced = pca.transform(descriptor.get_features(H_phase))\n", + "T_phase_X_reduced = pca.transform(descriptor.get_features(T_phase))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the index of the structure with the minimum energy\n", + "min_energy_index = np.argmin(rlxd_delta_en_per_atom)\n", + "print(min_energy_index)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Plot the PCA\n", + "fig, axes = plt.subplots(nrows=1, ncols=2, figsize=(8, 6))\n", + "\n", + "plt.subplots_adjust(wspace=0.05, hspace=0)\n", + "\n", + "## Get the maximum energy for the colourbar\n", + "max_en = min(3.5, max(np.max(unrlxd_delta_en_per_atom), np.max(rlxd_delta_en_per_atom)))\n", + "\n", + "## Plot the PCA\n", + "axes[0].scatter(unrlxd_X_reduced[:, 0], unrlxd_X_reduced[:, 1], c=unrlxd_delta_en_per_atom, cmap=\"viridis\", vmin = 0, vmax = max_en)\n", + "axes[1].scatter(rlxd_X_reduced[:, 0], rlxd_X_reduced[:, 1], c=rlxd_delta_en_per_atom, cmap=\"viridis\", vmin = 0, vmax = max_en)\n", + "\n", + "## Add the minimum energy structures to the plot\n", + "for ax in axes:\n", + " ax.scatter(T_phase_X_reduced[0,0], T_phase_X_reduced[0,1], s=200, edgecolor=[1.0, 0.5, 0.5, 0.8], facecolor='none', linewidth=2, label='T-phase')\n", + " ax.scatter(H_phase_X_reduced[0,0], H_phase_X_reduced[0,1], s=200, edgecolor='red', facecolor='none', linewidth=2, label='H-phase')\n", + " if ax == axes[1]:\n", + " handles, labels = ax.get_legend_handles_labels()\n", + " ax.legend(handles[::-1], labels[::-1], facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, loc='upper right', fontsize=20, handletextpad=0.1)\n", + "\n", + "## Add labels\n", + "fig.text(0.5, 0.0, 'Principal component 1', ha='center', fontsize=20)\n", + "axes[0].set_ylabel('Principal component 2', fontsize=20)\n", + "axes[0].set_title('Unrelaxed', fontsize=20)\n", + "axes[1].set_title('Relaxed', fontsize=20)\n", + "if rlxd_string == \"rlxd\":\n", + " xlims = [-15, 6]\n", + " ylims = [-3, 11]\n", + "else:\n", + " xlims = [-10, 39]\n", + " ylims = [-3, 30]\n", + "\n", + "for ax in axes:\n", + " # ax.set_xticks(np.arange(xlims[0], xlims[1]+1, 5), minor=True)\n", + " ax.tick_params(axis='both', direction='in', length=6, labelsize=20)\n", + " ax.yaxis.set_major_locator(MultipleLocator(3))\n", + " ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.xaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.tick_params(axis='both', which='minor', length=3, direction='in')\n", + " ax.set_xlim(xlims)\n", + " ax.set_ylim(ylims)\n", + "\n", + "## Unify tick labels\n", + "xticks = axes[0].get_xticks()\n", + "xticks = xticks[(xticks >= xlims[0]) & (xticks <= xlims[1])]\n", + "xticklabels = [ text for text in axes[0].get_xticklabels() if float(text.get_position()[0]) >= xlims[0] and float(text.get_position()[0]) <= xlims[1] ]\n", + "axes[0].set_xticks(xticks)\n", + "axes[1].set_xticks(xticks)\n", + "axes[1].set_xticklabels(xticklabels)\n", + "axes[1].set_yticklabels([])\n", + "axes[0].tick_params(axis='x', labelbottom=True, top=True)\n", + "axes[1].tick_params(axis='x', labelbottom=True, top=True)\n", + "axes[0].tick_params(axis='y', labelbottom=True, right=True)\n", + "axes[1].tick_params(axis='y', labelbottom=True, right=True)\n", + "\n", + "## Make axes[0] and axes[1] the same width\n", + "axes[0].set_box_aspect(1.7)\n", + "axes[1].set_box_aspect(1.7)\n", + "\n", + "## Add colorbar next to the axes\n", + "cbar = fig.colorbar(axes[1].collections[0], ax=axes, orientation='vertical', fraction=0.085, pad=0.02)\n", + "cbar.ax.tick_params(labelsize=20)\n", + "cbar.ax.yaxis.set_major_locator(MultipleLocator(1))\n", + "cbar.ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + "cbar.set_label('Formation energy (eV/atom)', fontsize=20)\n", + "\n", + "## Save the figure\n", + "plt.savefig('MoS2_RSS'+identifier+'_pca_'+rlxd_string+'_fit_seed'+str(seed)+'.pdf', bbox_inches='tight', pad_inches=0, facecolor=fig.get_facecolor(), edgecolor='none')" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [] + } + ], + "metadata": { + "kernelspec": { + "display_name": "raffle_env", + "language": "python", + "name": "python3" + }, + "language_info": { + "codemirror_mode": { + "name": "ipython", + "version": 3 + }, + "file_extension": ".py", + "mimetype": "text/x-python", + "name": "python", + "nbconvert_exporter": "python", + "pygments_lexer": "ipython3", + "version": "3.12.8" + } + }, + "nbformat": 4, + "nbformat_minor": 2 +} diff --git a/example/python_pkg/MoS2_learn/DRSS/rss.py b/example/python_pkg/MoS2_learn/DRSS/rss.py new file mode 100644 index 00000000..123b89ea --- /dev/null +++ b/example/python_pkg/MoS2_learn/DRSS/rss.py @@ -0,0 +1,133 @@ +# https://agox.gitlab.io/agox/command_line_tools/command_line.html + +import matplotlib + +matplotlib.use("Agg") + + +import numpy as np +from ase import Atoms +from ase.io import write + +from agox import AGOX +from agox.databases import Database +from agox.environments import Environment +from agox.evaluators import LocalOptimizationEvaluator +from agox.generators import RandomGenerator +from agox.postprocessors import MinimumDistPostProcess + + +database_index = 0 +iteration_directory = "iteration" + +############################################################################## +# Calculator +############################################################################## + +# from mace.calculators import mace_mp +from chgnet.model import CHGNetCalculator +from ase.build import bulk +import os + +# calc = mace_mp() +calc = CHGNetCalculator() + +############################################################################## +# System & general settings: +############################################################################## + + +post1 = MinimumDistPostProcess(order=1.5, c1=0.75) +post2 = MinimumDistPostProcess(order=2.5, c1=0.75) + +a = 3.19 +MoS2 = Atoms('Mo', positions=[(0, 0, 0)], cell=[ + [a * 0.5, a * -np.sqrt(3.0)/2.0, 0.0], + [a * 0.5, a * np.sqrt(3.0)/2.0, 0.0], + [0.0, 0.0, 13.1] + ], pbc=True, calculator=calc) + +# Make an empty template with a cubic cell of size 6x6x6 with periodic boundary conditions +# in all directions +iteration = 0 +template = Atoms("", + cell=[ + [a * 0.5, a * -np.sqrt(3.0)/2.0, 0.0], + [a * 0.5, a * np.sqrt(3.0)/2.0, 0.0], + [0.0, 0.0, 13.1] + ], + pbc=True) + + +# Confinement cell matches the template cell in all dimensions and is placed at +# the origin of the template cell. +confinement_cell = template.cell.copy() +confinement_corner = np.array([0, 0, 0]) + +environment = Environment( + template=template, + symbols="Mo2S4", + confinement_cell=confinement_cell, + confinement_corner=confinement_corner, + box_constraint_pbc=[True, True, True], # Confinement is periodic in all directions. +) + +# Database +db_directory = iteration_directory+"{}".format(iteration)+"/" +if not os.path.exists(db_directory): + os.makedirs(db_directory) +db_path = db_directory+"db{}.db".format(database_index) # From input argument! + +for seed in range(1): + database = Database(filename=db_path, order=3, initialize=True) + + ############################################################################## + # Search Settings: + ############################################################################## + + random_generator = RandomGenerator(**environment.get_confinement(), environment=environment, order=1) + + # Wont relax fully with steps:5 - more realistic setting would be 100+. + evaluator = LocalOptimizationEvaluator( + calc, + gets={"get_key": "candidates"}, + optimizer_run_kwargs={"fmax": 0.05, "steps": 100}, + store_trajectory=True, + order=2, + constraints=environment.get_constraints(), + ) + + ############################################################################## + # Let get the show running! + ############################################################################## + + agox = AGOX(random_generator, database, evaluator, seed=seed) + + agox.run(N_iterations=1000) + + database.restore_to_memory() + structure_data = database.get_all_structures_data() + # check iteration number has changed + iteration_check = -1 + unrlxd_structures = [] + rlxd_structures = [] + for idx, structure in enumerate(structure_data): + if structure["iteration"] != iteration_check: + iteration_check = structure["iteration"] + unrlxd_structures.append(database.db_to_atoms(structure)) + if idx != 0: + rlxd_structures.append(database.db_to_atoms(structure_data[idx-1])) + if len(rlxd_structures) != len(unrlxd_structures): + rlxd_structures.append(database.db_to_atoms(structure_data[-1])) + + for structure in unrlxd_structures: + structure.calc = None + for structure in rlxd_structures: + structure.calc = None + print("Unrelaxed structures", len(unrlxd_structures)) + print("Relaxed structures", len(rlxd_structures)) + write(f"unrlxd_structures_seed{seed}.traj", unrlxd_structures) + write(f"rlxd_structures_seed{seed}.traj", rlxd_structures) + +# database.restore_to_memory() +# structures = database.get_all_candidates() # this is an Atoms object with some more stuff diff --git a/example/python_pkg/README.md b/example/python_pkg/README.md index 5f46fabc..c9b2b295 100644 --- a/example/python_pkg/README.md +++ b/example/python_pkg/README.md @@ -15,8 +15,6 @@ python_pkg/ └── DRSS # Directory containing example random structure search script using AGOX ├── rss.py # Script to run RSS └── pca.ipynb # Notebook to plot principal component analysis of RSS results - ├── learn.ipynb # Script to run RSS generating and learning - └── pca.py # Notebook to plot principal component analysis of RAFFLE results ``` ## File Descriptions @@ -28,28 +26,31 @@ python_pkg/ ## Execution Order To run a RAFFLE example and analyse the results, the following order must be performed. -1. Move to the desired `SYSTEM_learn/` directory (other than `C_learn/`, where this will instead be in `C_learn/DRAFFLE/`) and create a directory to work in: +1. Move to the desired `SYSTEM_learn/DRAFFLE` directory and create a directory to work in: ```bash cd SYSTEM_learn - mkdir DTMP - cd DTMP + mkdir DOutput + cd DOutput ``` 2. Run the `learn.py` script: ```bash - python learn.py + python ../learn.py ``` -3. Go to parent directory and open the notebook, run all the cells. +3. Go to parent directory and open the notebook `pca.ipynb`, run all the cells. NOTE: for the `C_learn/DRSS/` example, the `pca.ipynb` notebook expects that the `C_learn/DRAFFLE/` example script and notebook have been fully run first. This is because it attempts to use the PCA fit to the RAFFLE results to transform its data. Doing so enables the two techniques to be properly compared. +The `[un]rlxd_structures_seed0.traj` files are provided (as are the `energies_[un]rlxd+seed0.txt`) as the key outputs from the `learn.py` runs. +For the `rss.py` scripts, the `[un]rlxd_structures_seed0.traj` files are provided. +Whilst other output files are generated during the RAFFLE runs, these are optional files with mostly redundant data. + ## Prerequisites - Python 3.11 or higher - raffle package installed (`pip install .`) - `ase` for handling atomic structure data - `CHGNet`, `MACE-0`, `VASP`, or some other `ase`-compatible calculator - diff --git a/example/python_pkg/ScS2-Li_learn/DRAFFLE/DOutput/energies_rlxd_seed0.txt b/example/python_pkg/ScS2-Li_learn/DRAFFLE/DOutput/energies_rlxd_seed0.txt new file mode 100644 index 00000000..def02ef2 --- /dev/null +++ b/example/python_pkg/ScS2-Li_learn/DRAFFLE/DOutput/energies_rlxd_seed0.txt @@ -0,0 +1,250 @@ +0 -5.197293281555176 +1 -5.197293758392334 +2 -5.197293758392334 +3 -5.197293758392334 +4 -5.197293758392334 +5 -3.9501519203186035 +6 -3.9492645263671875 +7 -4.1981730461120605 +8 -4.198167324066162 +9 -3.9501662254333496 +10 -5.350067138671875 +11 -5.350067615509033 +12 -5.350067138671875 +13 -5.350066661834717 +14 -5.350067138671875 +15 -4.304778099060059 +16 -4.2760138511657715 +17 -4.304804801940918 +18 -4.304819107055664 +19 -4.304825782775879 +20 -5.354612350463867 +21 -5.354619979858398 +22 -5.354608058929443 +23 -5.354602336883545 +24 -5.354613780975342 +25 -4.465170383453369 +26 -4.465167999267578 +27 -4.475955009460449 +28 -4.475955009460449 +29 -4.465153694152832 +30 -5.271121025085449 +31 -5.271093368530273 +32 -5.241171836853027 +33 -5.271121025085449 +34 -5.271130561828613 +35 -4.588056564331055 +36 -4.588050365447998 +37 -4.588067531585693 +38 -4.588066101074219 +39 -4.58806848526001 +40 -5.16950798034668 +41 -5.178687572479248 +42 -5.178738594055176 +43 -5.178704261779785 +44 -5.178701877593994 +45 -4.438231945037842 +46 -4.438248634338379 +47 -4.652371406555176 +48 -4.66633939743042 +49 -4.654650688171387 +50 -5.938078880310059 +51 -5.760022163391113 +52 -5.760019302368164 +53 -5.938079357147217 +54 -5.7600226402282715 +55 -4.680095195770264 +56 -4.928336143493652 +57 -4.903783321380615 +58 -4.92833948135376 +59 -4.928335666656494 +60 -5.890810489654541 +61 -5.913825511932373 +62 -5.977759838104248 +63 -5.9778008460998535 +64 -5.913825988769531 +65 -5.079046249389648 +66 -5.079040050506592 +67 -5.105108737945557 +68 -4.809535980224609 +69 -5.079045295715332 +70 -5.912981986999512 +71 -5.912947654724121 +72 -5.912947654724121 +73 -5.912947654724121 +74 -5.912947654724121 +75 -4.78941535949707 +76 -5.071550369262695 +77 -5.139162540435791 +78 -5.1391921043396 +79 -5.1391921043396 +80 -5.811561584472656 +81 -5.832507133483887 +82 -5.841716766357422 +83 -5.812049865722656 +84 -5.832564353942871 +85 -5.1685919761657715 +86 -5.182934761047363 +87 -5.168599605560303 +88 -5.16862678527832 +89 -5.168600082397461 +90 -5.797730922698975 +91 -5.79892110824585 +92 -5.798904895782471 +93 -5.797741413116455 +94 -5.797750949859619 +95 -5.2015204429626465 +96 -5.192843437194824 +97 -5.192821979522705 +98 -4.907331466674805 +99 -5.192802429199219 +100 -6.073056697845459 +101 -6.093416690826416 +102 -6.073028087615967 +103 -6.093376159667969 +104 -6.093329429626465 +105 -5.292612552642822 +106 -5.292593479156494 +107 -5.292583465576172 +108 -5.2925896644592285 +109 -5.29261589050293 +110 -6.0897216796875 +111 -6.089711666107178 +112 -6.068423748016357 +113 -6.065622806549072 +114 -6.068423748016357 +115 -5.381234645843506 +116 -5.381257057189941 +117 -5.336787223815918 +118 -5.336789131164551 +119 -5.336781978607178 +120 -6.034333229064941 +121 -6.034256458282471 +122 -6.0037150382995605 +123 -6.034256935119629 +124 -6.034305572509766 +125 -5.334656238555908 +126 -5.334653377532959 +127 -5.3671674728393555 +128 -5.334631443023682 +129 -5.334658622741699 +130 -5.965152263641357 +131 -5.939094066619873 +132 -5.939094543457031 +133 -5.986936569213867 +134 -5.939094543457031 +135 -5.35932731628418 +136 -5.334920883178711 +137 -5.334939002990723 +138 -5.33491325378418 +139 -5.334899425506592 +140 -5.967466354370117 +141 -5.945490837097168 +142 -5.967391014099121 +143 -5.967391014099121 +144 -5.909952163696289 +145 -5.360093593597412 +146 -5.36010217666626 +147 -5.3379082679748535 +148 -5.360090255737305 +149 -5.337904930114746 +150 -6.037515163421631 +151 -6.037520408630371 +152 -6.03754186630249 +153 -6.037517547607422 +154 -6.037514686584473 +155 -5.303253650665283 +156 -5.303305625915527 +157 -5.303257942199707 +158 -5.369649410247803 +159 -5.30330753326416 +160 -5.9884562492370605 +161 -5.988531112670898 +162 -5.988455772399902 +163 -5.9884562492370605 +164 -5.988542079925537 +165 -5.289036750793457 +166 -5.2891035079956055 +167 -5.289065361022949 +168 -5.289064407348633 +169 -5.289054870605469 +170 -5.9499430656433105 +171 -5.8879313468933105 +172 -5.884000778198242 +173 -5.949910640716553 +174 -5.949944019317627 +175 -5.267183303833008 +176 -5.205958366394043 +177 -5.267146110534668 +178 -5.313364028930664 +179 -5.313332557678223 +180 -5.8670220375061035 +181 -5.943231582641602 +182 -5.866943836212158 +183 -5.94324254989624 +184 -5.855208396911621 +185 -5.310813903808594 +186 -5.261920928955078 +187 -5.261280536651611 +188 -5.258203029632568 +189 -5.261255741119385 +190 -5.939988613128662 +191 -5.939988613128662 +192 -5.9399943351745605 +193 -5.9399919509887695 +194 -5.939996719360352 +195 -5.311786651611328 +196 -5.311791896820068 +197 -5.2571234703063965 +198 -5.31179141998291 +199 -5.3117876052856445 +200 -5.807187080383301 +201 -5.80729341506958 +202 -5.807285785675049 +203 -5.807281017303467 +204 -5.805758476257324 +205 -5.22076416015625 +206 -5.220106601715088 +207 -5.220184326171875 +208 -5.220706939697266 +209 -5.285614013671875 +210 -5.7312235832214355 +211 -5.785342216491699 +212 -5.731439590454102 +213 -5.73176908493042 +214 -5.731440544128418 +215 -5.1603193283081055 +216 -5.2654948234558105 +217 -5.168919563293457 +218 -5.167083740234375 +219 -5.162196636199951 +220 -5.779191017150879 +221 -5.779166221618652 +222 -5.779186248779297 +223 -5.779176712036133 +224 -5.7791948318481445 +225 -5.164179801940918 +226 -5.164151668548584 +227 -5.258593559265137 +228 -5.164211750030518 +229 -5.164211273193359 +230 -5.777128219604492 +231 -5.7771501541137695 +232 -5.777130603790283 +233 -5.777130126953125 +234 -5.777161598205566 +235 -5.164718151092529 +236 -5.164696216583252 +237 -5.164718151092529 +238 -5.151337146759033 +239 -5.164699554443359 +240 -5.776548862457275 +241 -5.776552677154541 +242 -5.776544094085693 +243 -5.776545524597168 +244 -5.77656888961792 +245 -5.16516637802124 +246 -5.165175914764404 +247 -5.16516637802124 +248 -5.165149688720703 +249 -5.16516637802124 diff --git a/example/python_pkg/ScS2-Li_learn/DRAFFLE/DOutput/energies_unrlxd_seed0.txt b/example/python_pkg/ScS2-Li_learn/DRAFFLE/DOutput/energies_unrlxd_seed0.txt new file mode 100644 index 00000000..c7938c63 --- /dev/null +++ b/example/python_pkg/ScS2-Li_learn/DRAFFLE/DOutput/energies_unrlxd_seed0.txt @@ -0,0 +1,250 @@ +0 -3.902194023132324 +1 -3.902194023132324 +2 -3.902194023132324 +3 -3.902194023132324 +4 -3.902194023132324 +5 -3.0095326900482178 +6 -3.2049460411071777 +7 -2.876801013946533 +8 -2.876801013946533 +9 -3.552215099334717 +10 -4.969838619232178 +11 -4.6301727294921875 +12 -4.6301727294921875 +13 -4.6301727294921875 +14 -4.6301727294921875 +15 -3.3525009155273438 +16 -3.3990509510040283 +17 -3.8568873405456543 +18 -3.8337626457214355 +19 -4.1041646003723145 +20 -5.009335517883301 +21 -5.183376789093018 +22 -4.968523025512695 +23 -5.138014793395996 +24 -5.009335517883301 +25 -3.5831379890441895 +26 -4.167985916137695 +27 -3.770373821258545 +28 -3.770373582839966 +29 -3.4965834617614746 +30 -5.128014087677002 +31 -5.167351722717285 +32 -5.088748455047607 +33 -5.128014087677002 +34 -5.058918476104736 +35 -4.3469953536987305 +36 -4.473069667816162 +37 -4.196581840515137 +38 -3.853349208831787 +39 -4.007944583892822 +40 -5.041675090789795 +41 -5.086215019226074 +42 -5.013214111328125 +43 -5.116482257843018 +44 -5.116482257843018 +45 -3.4465606212615967 +46 -3.3963828086853027 +47 -4.403440952301025 +48 -4.2900614738464355 +49 -4.26747989654541 +50 -5.624143600463867 +51 -4.696742534637451 +52 -5.664988994598389 +53 -5.624143600463867 +54 -5.6845903396606445 +55 -3.9787793159484863 +56 -4.360049247741699 +57 -4.602295875549316 +58 -4.660881519317627 +59 -4.311729431152344 +60 -5.546262264251709 +61 -5.734936237335205 +62 -5.6928582191467285 +63 -5.727543830871582 +64 -5.166667461395264 +65 -4.907829284667969 +66 -4.671273708343506 +67 -4.610535621643066 +68 -4.570350170135498 +69 -4.9855828285217285 +70 -5.632088661193848 +71 -5.673320770263672 +72 -5.673320770263672 +73 -5.673320770263672 +74 -5.673320770263672 +75 -4.154111385345459 +76 -4.805665016174316 +77 -5.018904685974121 +78 -4.761384963989258 +79 -4.761384963989258 +80 -5.734736442565918 +81 -5.45305061340332 +82 -5.749500751495361 +83 -5.658263683319092 +84 -5.744053363800049 +85 -5.005982398986816 +86 -4.878253936767578 +87 -4.980637073516846 +88 -5.063147068023682 +89 -4.82891845703125 +90 -5.518569469451904 +91 -5.527747631072998 +92 -5.433112144470215 +93 -5.534992218017578 +94 -5.384411334991455 +95 -4.803538799285889 +96 -4.56854772567749 +97 -4.48412561416626 +98 -4.165621757507324 +99 -4.424216270446777 +100 -5.644046306610107 +101 -5.8696064949035645 +102 -5.868980407714844 +103 -5.897206783294678 +104 -5.9985456466674805 +105 -5.166532516479492 +106 -4.970554351806641 +107 -5.051138877868652 +108 -4.98717737197876 +109 -4.985198497772217 +110 -6.038233280181885 +111 -6.012582778930664 +112 -5.970481872558594 +113 -5.972426414489746 +114 -5.970481872558594 +115 -4.860891819000244 +116 -5.0832295417785645 +117 -5.166046619415283 +118 -4.8951873779296875 +119 -4.992530822753906 +120 -4.525882720947266 +121 -5.787267684936523 +122 -5.875301361083984 +123 -5.787267684936523 +124 -5.902554988861084 +125 -4.904093265533447 +126 -5.128218173980713 +127 -5.266751766204834 +128 -4.993950843811035 +129 -5.206273078918457 +130 -5.643583297729492 +131 -5.677096366882324 +132 -5.677096366882324 +133 -5.751668930053711 +134 -5.677096366882324 +135 -5.148991584777832 +136 -4.893090724945068 +137 -5.074514389038086 +138 -5.08896541595459 +139 -4.74986457824707 +140 -5.511662006378174 +141 -5.504583835601807 +142 -5.489218711853027 +143 -5.489218711853027 +144 -5.275155067443848 +145 -4.438625335693359 +146 -4.9410247802734375 +147 -4.170555591583252 +148 -4.831180095672607 +149 -4.27830171585083 +150 -5.955852031707764 +151 -5.858462810516357 +152 -5.94709587097168 +153 -5.78511905670166 +154 -5.955852031707764 +155 -5.249693870544434 +156 -5.119163990020752 +157 -4.890987873077393 +158 -5.051628112792969 +159 -5.1757636070251465 +160 -5.817748546600342 +161 -5.8108811378479 +162 -5.817748546600342 +163 -5.817748546600342 +164 -5.7551703453063965 +165 -5.118488788604736 +166 -4.992713451385498 +167 -5.1359028816223145 +168 -4.893326282501221 +169 -5.1242523193359375 +170 -5.390294075012207 +171 -5.168456077575684 +172 -5.676529407501221 +173 -5.70081901550293 +174 -5.469979763031006 +175 -4.971701622009277 +176 -4.3953423500061035 +177 -5.037075042724609 +178 -4.814744472503662 +179 -4.976309776306152 +180 -5.475522994995117 +181 -5.527698993682861 +182 -5.471573829650879 +183 -5.503111839294434 +184 -5.473193645477295 +185 -4.860629081726074 +186 -4.832109451293945 +187 -4.789526462554932 +188 -4.9785966873168945 +189 -4.379780292510986 +190 -5.253356456756592 +191 -5.253356456756592 +192 -4.7336249351501465 +193 -5.2406439781188965 +194 -4.954418182373047 +195 -4.8262858390808105 +196 -4.878174304962158 +197 -4.852414608001709 +198 -4.878174304962158 +199 -4.234766483306885 +200 -5.38184118270874 +201 -5.207092761993408 +202 -4.944859981536865 +203 -5.227406978607178 +204 -5.181713104248047 +205 -4.749608039855957 +206 -5.05873441696167 +207 -4.747393608093262 +208 -4.987704753875732 +209 -4.913477897644043 +210 -5.497002601623535 +211 -5.095462322235107 +212 -5.489414215087891 +213 -5.522545337677002 +214 -5.489414215087891 +215 -4.9429192543029785 +216 -4.570065498352051 +217 -4.862813949584961 +218 -4.885910511016846 +219 -4.986788749694824 +220 -5.280392169952393 +221 -5.362484931945801 +222 -5.353952407836914 +223 -4.827139377593994 +224 -5.121610164642334 +225 -4.827130317687988 +226 -4.745603084564209 +227 -4.5340776443481445 +228 -4.849211692810059 +229 -4.849211692810059 +230 -5.072274208068848 +231 -5.090425968170166 +232 -5.072274208068848 +233 -5.072274208068848 +234 -5.072274208068848 +235 -4.660343170166016 +236 -4.650132179260254 +237 -4.757264137268066 +238 -4.715063571929932 +239 -4.280849933624268 +240 -4.866795063018799 +241 -4.851679801940918 +242 -4.866795063018799 +243 -4.866794586181641 +244 -4.847502708435059 +245 -4.60818338394165 +246 -4.528399467468262 +247 -4.60818338394165 +248 -4.472186088562012 +249 -4.60818338394165 diff --git a/example/python_pkg/ScS2-Li_learn/DRAFFLE/DOutput/rlxd_structures_seed0.traj b/example/python_pkg/ScS2-Li_learn/DRAFFLE/DOutput/rlxd_structures_seed0.traj new file mode 100644 index 00000000..12f863c7 Binary files /dev/null and b/example/python_pkg/ScS2-Li_learn/DRAFFLE/DOutput/rlxd_structures_seed0.traj differ diff --git a/example/python_pkg/ScS2-Li_learn/DRAFFLE/DOutput/unrlxd_structures_seed0.traj b/example/python_pkg/ScS2-Li_learn/DRAFFLE/DOutput/unrlxd_structures_seed0.traj new file mode 100644 index 00000000..b10a80a5 Binary files /dev/null and b/example/python_pkg/ScS2-Li_learn/DRAFFLE/DOutput/unrlxd_structures_seed0.traj differ diff --git a/example/python_pkg/ScS2-Li_learn/learn.py b/example/python_pkg/ScS2-Li_learn/DRAFFLE/learn.py similarity index 89% rename from example/python_pkg/ScS2-Li_learn/learn.py rename to example/python_pkg/ScS2-Li_learn/DRAFFLE/learn.py index 7da45e9b..90dca467 100644 --- a/example/python_pkg/ScS2-Li_learn/learn.py +++ b/example/python_pkg/ScS2-Li_learn/DRAFFLE/learn.py @@ -1,4 +1,5 @@ from chgnet.model import CHGNetCalculator +from ase.calculators.singlepoint import SinglePointCalculator from raffle.generator import raffle_generator from ase import Atoms from ase.optimize import FIRE @@ -16,7 +17,6 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct # calc = Vasp(**calc_params, label=f"struct{i}", directory=f"iteration{iteration}/struct{i}/", txt=f"stdout{i}.o") inew = i - num_structures_old atoms.calc = calc - # positions_initial = atoms.get_positions() # Calculate and save the initial energy per atom energy_unrlxd = atoms.get_potential_energy() / len(atoms) @@ -142,7 +142,7 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct num_structures = 5, stoichiometry = { 'Li': num_atoms }, seed = seed*1000+iter, - method_probab = {"void": 1.0, "rand": 0.5, "walk": 1.0, "grow": 0.0, "min": 1.0}, + method_ratio = {"void": 1.0, "rand": 0.5, "walk": 1.0, "grow": 0.0, "min": 1.0}, verbose = 0, ) @@ -164,21 +164,32 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct write(iterdir+f"POSCAR_unrlxd_{i}", generated_structures[num_structures_old + i]) print(f"Structure {i} energy per atom: {generated_structures[num_structures_old + i].get_potential_energy() / len(generated_structures[num_structures_old + i])}") unrlxd_structures.append(generated_structures[num_structures_old + i].copy()) + unrlxd_structures[-1].calc = SinglePointCalculator( + generated_structures[num_structures_old + i], + energy=generated_structures[num_structures_old + i].get_potential_energy(), + forces=generated_structures[num_structures_old + i].get_forces() + ) + # Start parallel execution print("Starting parallel execution") results = Parallel(n_jobs=5)( - delayed(process_structure)(i, generated_structures[i], num_structures_old, calc_params, optimise_structure, iteration=seed, calc=calc) + delayed(process_structure)(i, generated_structures[i].copy(), num_structures_old, calc_params, optimise_structure, iteration=seed, calc=calc) for i in range(num_structures_old, num_structures_new) ) # Wait for all futures to complete for j, result in enumerate(results): - generated_structures[j+num_structures_old], energy_unrlxd[j], energy_rlxd[j] = result - if generated_structures[j+num_structures_old] is None: + generated_structures[num_structures_old + j], energy_unrlxd[j], energy_rlxd[j] = result + if generated_structures[num_structures_old + j] is None: print("Structure failed the checks") continue - rlxd_structures.append(generated_structures[j+num_structures_old].copy()) + rlxd_structures.append(generated_structures[num_structures_old + j].copy()) + rlxd_structures[-1].calc = SinglePointCalculator( + generated_structures[j+num_structures_old], + energy=generated_structures[num_structures_old + j].get_potential_energy(), + forces=generated_structures[num_structures_old + j].get_forces() + ) print("All futures completed") diff --git a/example/python_pkg/ScS2-Li_learn/pca.ipynb b/example/python_pkg/ScS2-Li_learn/DRAFFLE/pca.ipynb similarity index 88% rename from example/python_pkg/ScS2-Li_learn/pca.ipynb rename to example/python_pkg/ScS2-Li_learn/DRAFFLE/pca.ipynb index d51fd341..c79d3f5f 100644 --- a/example/python_pkg/ScS2-Li_learn/pca.ipynb +++ b/example/python_pkg/ScS2-Li_learn/DRAFFLE/pca.ipynb @@ -17,7 +17,8 @@ "from agox.utils.graph_sorting import Analysis\n", "\n", "import numpy as np\n", - "from sklearn.decomposition import PCA" + "from sklearn.decomposition import PCA\n", + "from matplotlib.ticker import (MultipleLocator, AutoMinorLocator)" ] }, { @@ -43,7 +44,7 @@ "seed = 0\n", "identifier = \"\"\n", "use_AGOX = True\n", - "insert_images = True" + "insert_images = False" ] }, { @@ -80,7 +81,7 @@ "outputs": [], "source": [ "## Load the unrelaxed structures\n", - "unrlxd_structures = read(\"DTMP\"+identifier+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "unrlxd_structures = read(\"DOutput\"+identifier+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", "for structure in unrlxd_structures:\n", " structure.calc = calc" ] @@ -92,7 +93,7 @@ "outputs": [], "source": [ "## Load the relaxed structures\n", - "rlxd_structures = read(\"DTMP\"+identifier+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "rlxd_structures = read(\"DOutput\"+identifier+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", "for structure in rlxd_structures:\n", " structure.calc = calc" ] @@ -106,7 +107,7 @@ "## Read energies from energies_unrlxd_seed0.txt and add to the respective structures using a SinglePointCalculator\n", "## The file has the form \"index energy\"\n", "## This is done because there seem to be issues with storing the energy in the ASE trajectory file for some setups\n", - "filename = \"DTMP\"+identifier+\"/energies_unrlxd_seed\"+str(seed)+\".txt\"\n", + "filename = \"DOutput\"+identifier+\"/energies_unrlxd_seed\"+str(seed)+\".txt\"\n", "with open(filename) as f:\n", " for line in f:\n", " index, energy = line.split()\n", @@ -115,7 +116,7 @@ " unrlxd_structures[index].calc = SinglePointCalculator(unrlxd_structures[index], energy=energy * len(unrlxd_structures[index]))\n", "\n", "\n", - "filename = \"DTMP\"+identifier+\"/energies_rlxd_seed\"+str(seed)+\".txt\"\n", + "filename = \"DOutput\"+identifier+\"/energies_rlxd_seed\"+str(seed)+\".txt\"\n", "with open(filename) as f:\n", " for line in f:\n", " index, energy = line.split()\n", @@ -285,26 +286,29 @@ " ax.scatter(rlxd_X_reduced[103, 0], rlxd_X_reduced[103, 1], s=200, edgecolor=[1.0, 0.5, 0.5, 0.8], facecolor='none', linewidth=2, label='Tetrahedral')\n", " ax.scatter(rlxd_X_reduced[101, 0], rlxd_X_reduced[101, 1], s=200, edgecolor='red', facecolor='none', linewidth=2, label='T-phase')\n", " if ax == axes[1]:\n", - " ax.legend(fontsize=10)\n", " handles, labels = ax.get_legend_handles_labels()\n", - " ax.legend(handles[::-1], labels[::-1], facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, loc='upper right')\n", - "\n", + " ax.legend(handles[::-1], labels[::-1], facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, bbox_to_anchor=(1.04, 1.02), fontsize=20, handletextpad=0.2, borderpad=0.3, handlelength=1)\n", + " \n", "## Add labels\n", - "fig.text(0.5, 0.04, 'Principal Component 1', ha='center', fontsize=15)\n", - "axes[0].set_ylabel('Principal Component 2', fontsize=15)\n", - "axes[0].set_title('Unrelaxed')\n", - "axes[1].set_title('Relaxed')\n", + "fig.text(0.5, 0.0, 'Principal component 1', ha='center', fontsize=20)\n", + "axes[0].set_ylabel('Principal component 2', fontsize=20)\n", + "axes[0].set_title('Unrelaxed', fontsize=20)\n", + "axes[1].set_title('Relaxed', fontsize=20)\n", "if rlxd_string == \"rlxd\":\n", - " xlims = [-20, 90]\n", - " ylims = [-20, 30]\n", + " xlims = [-20, 90]\n", + " ylims = [-20, 30]\n", "else:\n", - " xlims = [-20, 90]\n", - " ylims = [-30, 30]\n", + " xlims = [-20, 90]\n", + " ylims = [-30, 30]\n", "\n", "for ax in axes:\n", - " ax.tick_params(axis='both', direction='in')\n", - " ax.set_xlim(xlims)\n", - " ax.set_ylim(ylims)\n", + " ax.tick_params(axis='both', direction='in', length=6, labelsize=20)\n", + " # ax.yaxis.set_major_locator(MultipleLocator(3))\n", + " ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.xaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.tick_params(axis='both', which='minor', length=3, direction='in')\n", + " ax.set_xlim(xlims)\n", + " ax.set_ylim(ylims)\n", "\n", "## Unify tick labels\n", "xticks = axes[0].get_xticks()\n", @@ -322,7 +326,10 @@ "\n", "## Add colorbar next to the axes\n", "cbar = fig.colorbar(axes[1].collections[0], ax=axes, orientation='vertical', fraction=0.085, pad=0.02)\n", - "cbar.set_label('Formation energy (eV/atom)', fontsize=15)\n", + "cbar.ax.tick_params(labelsize=20)\n", + "cbar.ax.yaxis.set_major_locator(MultipleLocator(1))\n", + "cbar.ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + "cbar.set_label('Formation energy (eV/atom)', fontsize=20)\n", "\n", "\n", "# Define the position and size parameters\n", diff --git a/example/python_pkg/Si-Ge_learn/DRAFFLE/DOutput/energies_rlxd_seed0.txt b/example/python_pkg/Si-Ge_learn/DRAFFLE/DOutput/energies_rlxd_seed0.txt new file mode 100644 index 00000000..60e21864 --- /dev/null +++ b/example/python_pkg/Si-Ge_learn/DRAFFLE/DOutput/energies_rlxd_seed0.txt @@ -0,0 +1,200 @@ +0 -4.914972305297852 +1 -4.91649169921875 +2 -4.861606216430664 +3 -4.855623626708985 +4 -4.855409240722656 +5 -4.878281784057617 +6 -4.887422943115235 +7 -4.901992416381836 +8 -4.903535079956055 +9 -4.882128524780273 +10 -4.88164176940918 +11 -4.8969158172607425 +12 -4.906864929199219 +13 -4.877632522583008 +14 -4.893371963500977 +15 -4.897794342041015 +16 -4.886429214477539 +17 -4.866251373291016 +18 -4.885772705078125 +19 -4.9011882781982425 +20 -4.888833236694336 +21 -4.894488906860351 +22 -4.880154418945312 +23 -4.885638046264648 +24 -4.879172515869141 +25 -4.891361236572266 +26 -4.875225067138672 +27 -4.890724945068359 +28 -4.888699722290039 +29 -4.874675369262695 +30 -4.895965194702148 +31 -4.894282531738281 +32 -4.899742507934571 +33 -4.876846694946289 +34 -4.892966842651367 +35 -4.892748641967773 +36 -4.889076232910156 +37 -4.89398307800293 +38 -4.882550811767578 +39 -4.888446426391601 +40 -4.880241775512696 +41 -4.903352355957031 +42 -4.894754409790039 +43 -4.909047317504883 +44 -4.894018173217773 +45 -4.893288421630859 +46 -4.890397262573242 +47 -4.893740463256836 +48 -4.8951068878173825 +49 -4.89024658203125 +50 -4.901031875610352 +51 -4.903420257568359 +52 -4.8731342315673825 +53 -4.903898620605469 +54 -4.886251831054688 +55 -4.88873291015625 +56 -4.885586929321289 +57 -4.87108268737793 +58 -4.880144500732422 +59 -4.922010040283203 +60 -4.907477569580078 +61 -4.889593887329101 +62 -4.885894012451172 +63 -4.880735397338867 +64 -4.888919830322266 +65 -4.872313690185547 +66 -4.868569564819336 +67 -4.880554962158203 +68 -4.90867805480957 +69 -4.872788619995117 +70 -4.88622932434082 +71 -4.899290466308594 +72 -4.899893951416016 +73 -4.90754508972168 +74 -4.8909660339355465 +75 -4.89494514465332 +76 -4.8738037109375 +77 -4.900898361206055 +78 -4.894425964355468 +79 -4.879955673217774 +80 -4.8811180114746096 +81 -4.879557418823242 +82 -4.885642242431641 +83 -4.911777496337891 +84 -4.902692794799805 +85 -4.882935333251953 +86 -4.888240814208984 +87 -4.899281692504883 +88 -4.887091827392578 +89 -4.892605972290039 +90 -4.870666885375977 +91 -4.899197769165039 +92 -4.9049327850341795 +93 -4.874461364746094 +94 -4.870742416381836 +95 -4.862278747558594 +96 -4.873507308959961 +97 -4.887075424194336 +98 -4.899689865112305 +99 -4.901652145385742 +100 -4.891659545898437 +101 -4.892141723632813 +102 -4.864310455322266 +103 -4.8948486328125 +104 -4.918062591552735 +105 -4.865977478027344 +106 -4.908528900146484 +107 -4.8898876190185545 +108 -4.8711189270019535 +109 -4.873516845703125 +110 -4.874154663085937 +111 -4.885936737060547 +112 -4.904039764404297 +113 -4.886112213134766 +114 -4.8923194885253904 +115 -4.8799591064453125 +116 -4.891947937011719 +117 -4.871723937988281 +118 -4.872768402099609 +119 -4.888679122924804 +120 -4.889215469360352 +121 -4.877410888671875 +122 -4.867169952392578 +123 -4.8661354064941404 +124 -4.88546142578125 +125 -4.88348503112793 +126 -4.886756515502929 +127 -4.883444976806641 +128 -4.8866729736328125 +129 -4.870816802978515 +130 -4.884921264648438 +131 -4.8856159210205075 +132 -4.879690933227539 +133 -4.902304840087891 +134 -4.890494918823242 +135 -4.911536407470703 +136 -4.87796630859375 +137 -4.909608840942383 +138 -4.921651840209961 +139 -4.886025238037109 +140 -4.892271041870117 +141 -4.884712982177734 +142 -4.937671661376953 +143 -4.889350509643554 +144 -4.86771240234375 +145 -4.887294769287109 +146 -4.871640396118164 +147 -4.874458694458008 +148 -4.878175354003906 +149 -4.879819107055664 +150 -4.883909606933594 +151 -4.8896228790283205 +152 -4.887221908569336 +153 -4.893557357788086 +154 -4.873178482055664 +155 -4.896877670288086 +156 -4.886516189575195 +157 -4.868564224243164 +158 -4.912376022338867 +159 -4.884773635864258 +160 -4.899208831787109 +161 -4.871421051025391 +162 -4.885197448730469 +163 -4.8793495178222654 +164 -4.920566558837891 +165 -4.9044189453125 +166 -4.88873519897461 +167 -4.893503189086914 +168 -4.867198944091797 +169 -4.884555816650391 +170 -4.875222015380859 +171 -4.884209823608399 +172 -4.8826038360595705 +173 -4.901235961914063 +174 -4.913423538208008 +175 -4.87219009399414 +176 -4.875072860717774 +177 -4.888148498535156 +178 -4.906456756591797 +179 -4.901366424560547 +180 -4.87957649230957 +181 -4.908529663085938 +182 -4.879862213134766 +183 -4.8976593017578125 +184 -4.882303237915039 +185 -4.880528259277344 +186 -4.938621902465821 +187 -4.8662464141845705 +188 -4.882993698120117 +189 -4.886720275878906 +190 -4.880290222167969 +191 -4.882056427001953 +192 -4.924828338623047 +193 -4.874137496948242 +194 -4.906658554077149 +195 -4.894911193847657 +196 -4.90538330078125 +197 -4.906739044189453 +198 -4.890327835083008 +199 -4.881915664672851 diff --git a/example/python_pkg/Si-Ge_learn/DRAFFLE/DOutput/energies_unrlxd_seed0.txt b/example/python_pkg/Si-Ge_learn/DRAFFLE/DOutput/energies_unrlxd_seed0.txt new file mode 100644 index 00000000..d3a72f2f --- /dev/null +++ b/example/python_pkg/Si-Ge_learn/DRAFFLE/DOutput/energies_unrlxd_seed0.txt @@ -0,0 +1,200 @@ +0 -4.453202819824218 +1 -4.504172134399414 +2 -4.6408546447753904 +3 -4.63459587097168 +4 -4.516173934936523 +5 -4.410512161254883 +6 -4.46300163269043 +7 -4.431527709960937 +8 -4.49969711303711 +9 -4.420805740356445 +10 -4.448611450195313 +11 -4.494855117797852 +12 -4.481899261474609 +13 -4.3776897430419925 +14 -4.401117324829102 +15 -4.39771842956543 +16 -4.445943450927734 +17 -4.453267288208008 +18 -4.384496688842773 +19 -4.586454391479492 +20 -4.469540023803711 +21 -4.387693786621094 +22 -4.513351058959961 +23 -4.444543838500977 +24 -4.505443572998047 +25 -4.516176986694336 +26 -4.416852951049805 +27 -4.47453498840332 +28 -4.559367370605469 +29 -4.396646499633789 +30 -4.580905914306641 +31 -4.507269668579101 +32 -4.5136566162109375 +33 -4.45918083190918 +34 -4.515206909179687 +35 -4.500501251220703 +36 -4.404730606079101 +37 -4.470790863037109 +38 -4.483791351318359 +39 -4.404285049438476 +40 -4.394823837280273 +41 -4.490650177001953 +42 -4.474962615966797 +43 -4.441206359863282 +44 -4.408433151245117 +45 -4.515719604492188 +46 -4.5389141082763675 +47 -4.490047454833984 +48 -4.468499755859375 +49 -4.524095153808593 +50 -4.5234222412109375 +51 -4.376375579833985 +52 -4.411101913452148 +53 -4.50413703918457 +54 -4.383007431030274 +55 -4.448178482055664 +56 -4.4815418243408205 +57 -4.369570541381836 +58 -4.369534301757812 +59 -4.5478675842285154 +60 -4.416166687011719 +61 -4.479610824584961 +62 -4.451063537597657 +63 -4.44030532836914 +64 -4.497214126586914 +65 -4.4202110290527346 +66 -4.5455974578857425 +67 -4.487796020507813 +68 -4.369594955444336 +69 -4.456621932983398 +70 -4.389879989624023 +71 -4.4011962890625 +72 -4.438508605957031 +73 -4.507590103149414 +74 -4.4116260528564455 +75 -4.422320556640625 +76 -4.511064529418945 +77 -4.627801513671875 +78 -4.386912536621094 +79 -4.49513053894043 +80 -4.504476928710938 +81 -4.472342681884766 +82 -4.599071502685547 +83 -4.461201858520508 +84 -4.400399780273437 +85 -4.559006118774414 +86 -4.433550643920898 +87 -4.3803668975830075 +88 -4.529462814331055 +89 -4.557731246948242 +90 -4.378111267089844 +91 -4.4428760528564455 +92 -4.59844970703125 +93 -4.469930648803711 +94 -4.501279830932617 +95 -4.423347854614258 +96 -4.4697105407714846 +97 -4.463986206054687 +98 -4.523093032836914 +99 -4.462126541137695 +100 -4.473728942871094 +101 -4.391287994384766 +102 -4.543589782714844 +103 -4.436207962036133 +104 -4.419996643066407 +105 -4.3694000244140625 +106 -4.510407257080078 +107 -4.377021789550781 +108 -4.602657318115234 +109 -4.332642364501953 +110 -4.431227111816407 +111 -4.359136581420898 +112 -4.491495132446289 +113 -4.407060623168945 +114 -4.533096694946289 +115 -4.465452194213867 +116 -4.427890014648438 +117 -4.4576770782470705 +118 -4.590351867675781 +119 -4.3997650146484375 +120 -4.4159893035888675 +121 -4.322970962524414 +122 -4.441549682617188 +123 -4.460046005249024 +124 -4.3837230682373045 +125 -4.460969924926758 +126 -4.409426879882813 +127 -4.40191650390625 +128 -4.454932785034179 +129 -4.364422225952149 +130 -4.508897399902343 +131 -4.539888763427735 +132 -4.504233169555664 +133 -4.659821701049805 +134 -4.386347961425781 +135 -4.441254043579102 +136 -4.388945388793945 +137 -4.397981262207031 +138 -4.44323501586914 +139 -4.462754440307617 +140 -4.460346603393555 +141 -4.348915481567383 +142 -4.445657730102539 +143 -4.484442901611328 +144 -4.469877243041992 +145 -4.452066040039062 +146 -4.468696594238281 +147 -4.48945198059082 +148 -4.522359848022461 +149 -4.493000793457031 +150 -4.53687629699707 +151 -4.409241104125977 +152 -4.443413543701172 +153 -4.454759216308593 +154 -4.507298278808594 +155 -4.474824905395508 +156 -4.510904312133789 +157 -4.479224395751953 +158 -4.563150787353516 +159 -4.553173065185547 +160 -4.525261306762696 +161 -4.415293121337891 +162 -4.534302139282227 +163 -4.438970947265625 +164 -4.417642211914062 +165 -4.469867706298828 +166 -4.509925079345703 +167 -4.462126922607422 +168 -4.407186889648438 +169 -4.497385406494141 +170 -4.480976486206055 +171 -4.482896041870117 +172 -4.507286834716797 +173 -4.495151138305664 +174 -4.455961990356445 +175 -4.346749114990234 +176 -4.566693496704102 +177 -4.521957778930664 +178 -4.478157424926758 +179 -4.460347366333008 +180 -4.565155410766602 +181 -4.410587310791016 +182 -4.450661468505859 +183 -4.544831848144531 +184 -4.515465545654297 +185 -4.400769424438477 +186 -4.429144287109375 +187 -4.470453262329102 +188 -4.447067642211914 +189 -4.495766448974609 +190 -4.3717506408691404 +191 -4.4245960235595705 +192 -4.471554565429687 +193 -4.4578601837158205 +194 -4.424975204467773 +195 -4.444546890258789 +196 -4.557712554931641 +197 -4.518783187866211 +198 -4.343213653564453 +199 -4.420653915405273 diff --git a/example/python_pkg/Si-Ge_learn/DRAFFLE/DOutput/rlxd_structures_seed0.traj b/example/python_pkg/Si-Ge_learn/DRAFFLE/DOutput/rlxd_structures_seed0.traj new file mode 100644 index 00000000..f65c2105 Binary files /dev/null and b/example/python_pkg/Si-Ge_learn/DRAFFLE/DOutput/rlxd_structures_seed0.traj differ diff --git a/example/python_pkg/Si-Ge_learn/DRAFFLE/DOutput/unrlxd_structures_seed0.traj b/example/python_pkg/Si-Ge_learn/DRAFFLE/DOutput/unrlxd_structures_seed0.traj new file mode 100644 index 00000000..da6bce6e Binary files /dev/null and b/example/python_pkg/Si-Ge_learn/DRAFFLE/DOutput/unrlxd_structures_seed0.traj differ diff --git a/example/python_pkg/Si-Ge_learn/DRAFFLE/learn.py b/example/python_pkg/Si-Ge_learn/DRAFFLE/learn.py new file mode 100644 index 00000000..ffa6d318 --- /dev/null +++ b/example/python_pkg/Si-Ge_learn/DRAFFLE/learn.py @@ -0,0 +1,265 @@ +from mace.calculators import mace_mp +from ase.calculators.singlepoint import SinglePointCalculator +from raffle.generator import raffle_generator +from ase import build +from ase.optimize import FIRE +from ase.io import write +import numpy as np +import os +from joblib import Parallel, delayed + +import logging +logging.basicConfig(level=logging.DEBUG) + +# Function to relax a structure +def process_structure(i, atoms, num_structures_old, calc_params, optimise_structure, iteration, calc): + # Check if the structure has already been processed + if i < num_structures_old: + return None, None, None + + # calc = Vasp(**calc_params, label=f"struct{i}", directory=f"iteration{iteration}/struct{i}/", txt=f"stdout{i}.o") + inew = i - num_structures_old + atoms.calc = calc + + # Calculate and save the initial energy per atom + energy_unrlxd = atoms.get_potential_energy() / len(atoms) + print(f"Initial energy per atom: {energy_unrlxd}") + + # Optimise the structure if requested + if optimise_structure: + optimizer = FIRE(atoms, trajectory = f"traje{inew}.traj", logfile=f"optimisation{inew}.log") + try: + optimizer.run(fmax=0.05, steps=100) + except Exception as e: + print(f"Optimisation failed: {e}") + return None, None, None + + # Save the optimised structure and its energy per atom + energy_rlxd = atoms.get_potential_energy() / len(atoms) + + # Get the distance matrix + distances = atoms.get_all_distances(mic=True) + + # Set self-distances (diagonal entries) to infinity to ignore them + np.fill_diagonal(distances, np.inf) + + # Check if the minimum non-self distance is below 1.5 + if distances.min() < 1.0: + print(f"Distance too small: {atoms.get_all_distances(mic=True).min()}") + return None, None, None + + if abs(energy_rlxd - energy_unrlxd) > 10.0: + print(f"Energy difference too large: {energy_rlxd} vs {energy_unrlxd}") + return None, None, None + + return atoms, energy_unrlxd, energy_rlxd + + +if __name__ == "__main__": + + # set up the calculator + calc_params = { 'model': "../mace-mpa-0-medium.model" } + calc = mace_mp(**calc_params) + + # set up the hosts + hosts = [] + + Si_bulk = build.bulk("Si", crystalstructure="diamond", a=5.43) + Si_bulk.calc = calc + Si_reference_energy = Si_bulk.get_potential_energy() / len(Si_bulk) + Si_cubic = build.make_supercell(Si_bulk, [[-1, 1, 1], [1, -1, 1], [1, 1, -1]]) + Ge_bulk = build.bulk("Ge", crystalstructure="diamond", a=5.65) + Ge_bulk.calc = calc + Ge_cubic = build.make_supercell(Ge_bulk, [[-1, 1, 1], [1, -1, 1], [1, 1, -1]]) + Ge_reference_energy = Ge_bulk.get_potential_energy() / len(Ge_bulk) + + Si_supercell = build.make_supercell(Si_cubic, [[2, 0, 0], [0, 2, 0], [0, 0, 1]]) + Ge_supercell = build.make_supercell(Ge_cubic, [[2, 0, 0], [0, 2, 0], [0, 0, 1]]) + + Si_surface = build.surface(Si_supercell, indices=(0, 0, 1), layers=2) + Ge_surface = build.surface(Ge_supercell, indices=(0, 0, 1), layers=2) + + Si_slab = build.surface(Si_supercell, indices=(0, 0, 1), layers=2, vacuum=12, periodic=True) + Si_slab.calc = calc + Ge_slab = build.surface(Ge_supercell, indices=(0, 0, 1), layers=2, vacuum=12, periodic=True) + Ge_slab.calc = calc + + host = build.stack(Si_surface, Ge_surface, axis=2, distance= 5.43/2 + 5.65/2) + cell = host.get_cell() + print("Host cell: ", host.get_cell()) + cell[2, 2] -= 3.8865 # (5.43 + 5.65) / 2 * 3/4 + host.set_cell(cell, scale_atoms=False) + + hosts.append(host) + + # set the parameters for the generator + generator = raffle_generator() + generator.distributions.set_element_energies( + { + 'Si': Si_reference_energy, + 'Ge': Ge_reference_energy, + } + ) + + # set energy scale + generator.distributions.set_kBT(0.2) + + # set the distribution function widths (2-body, 3-body, 4-body) + generator.distributions.set_width([0.04, np.pi/160.0, np.pi/160.0]) + + # set the initial database + initial_database = [Si_bulk, Ge_bulk] + generator.distributions.create(initial_database, deallocate_systems=False) + + # set the parameters for the generator + seed = 0 + + # check if the energies file exists, if not create it + energies_rlxd_filename = f"energies_rlxd_seed{seed}.txt" + energies_unrlxd_filename = f"energies_unrlxd_seed{seed}.txt" + + if os.path.exists(energies_rlxd_filename): + with open(energies_rlxd_filename, "w") as energy_file: + pass + else: + open(energies_rlxd_filename, "w").close() + + if os.path.exists(energies_unrlxd_filename): + with open(energies_unrlxd_filename, "w") as energy_file: + pass + else: + open(energies_unrlxd_filename, "w").close() + + # initialise the number of structures generated + iter = -1 + unrlxd_structures = [] + rlxd_structures = [] + num_structures_old = 0 + optimise_structure = True + # start the iterations, loop over the hosts, then repeat the process X times + for ival in range(40): + for host in hosts: + print("setting host") + generator.set_host(host) + generator.set_bounds([[0, 0, 0.34], [1, 1, 0.52]]) + + iter += 1 + print(f"Iteration {iter}") + + # generate the structures + generator.generate( + num_structures = 5, + stoichiometry = { 'Si': 16, 'Ge': 16 }, + seed = seed*1000+iter, + method_ratio = {"void": 0.1, "rand": 0.01, "walk": 0.25, "grow": 0.25, "min": 1.0}, + verbose = 0, + ) + + # print the number of structures generated + print("Total number of structures generated: ", generator.num_structures) + generated_structures = generator.get_structures(calc) + num_structures_new = len(generated_structures) + + # check if directory iteration[iter] exists, if not create it + iterdir = f"iteration{iter}/" + if not os.path.exists(iterdir): + os.makedirs(iterdir) + generator.print_settings(iterdir+"generator_settings.txt") + + # set up list of energies + energy_unrlxd = np.zeros(num_structures_new - num_structures_old) + energy_rlxd = np.zeros(num_structures_new - num_structures_old) + for i in range(num_structures_new - num_structures_old): + write(iterdir+f"POSCAR_unrlxd_{i}", generated_structures[num_structures_old + i]) + print(f"Structure {i} energy per atom: {generated_structures[num_structures_old + i].get_potential_energy() / len(generated_structures[num_structures_old + i])}") + # print(f"Structure {i} energy per unit area: {( generated_structures[num_structures_old + i].get_potential_energy() - Si_slab.get_potential_energy() - Ge_slab.get_potential_energy() ) / (2 * ( cell[0, 0] * cell[1, 1] ) )}") + unrlxd_structures.append(generated_structures[num_structures_old + i].copy()) + unrlxd_structures[-1].calc = SinglePointCalculator( + generated_structures[num_structures_old + i], + energy=generated_structures[num_structures_old + i].get_potential_energy(), + forces=generated_structures[num_structures_old + i].get_forces() + ) + + # Start parallel execution + print("Starting parallel execution") + results = Parallel(n_jobs=5)( + delayed(process_structure)(i, generated_structures[i].copy(), num_structures_old, calc_params, optimise_structure, iteration=seed, calc=calc) + for i in range(num_structures_old, num_structures_new) + ) + + # Wait for all futures to complete + for j, result in enumerate(results): + generated_structures[num_structures_old + j], energy_unrlxd[j], energy_rlxd[j] = result + if generated_structures[num_structures_old + j] is None: + print("Structure failed the checks") + continue + rlxd_structures.append(generated_structures[num_structures_old + j].copy()) + rlxd_structures[-1].calc = SinglePointCalculator( + generated_structures[j+num_structures_old], + energy=generated_structures[num_structures_old + j].get_potential_energy(), + forces=generated_structures[num_structures_old + j].get_forces() + ) + print("All futures completed") + + # Remove structures that failed the checks + for j, atoms in reversed(list(enumerate(generated_structures))): + if j < num_structures_old: + continue + if atoms is None: + energy_unrlxd = np.delete(energy_unrlxd, j-num_structures_old) + energy_rlxd = np.delete(energy_rlxd, j-num_structures_old) + del generated_structures[j] + del unrlxd_structures[j] + del rlxd_structures[j] + generator.remove_structure(j) + num_structures_new = len(generated_structures) + + # write the structures to files + for i in range(num_structures_new - num_structures_old): + write(iterdir+f"POSCAR_{i}", generated_structures[num_structures_old + i]) + print(f"Structure {i} energy per atom: {energy_rlxd[i]}") + # append energy per atom to the 'energies_unrlxd_filename' file + with open(energies_unrlxd_filename, "a") as energy_file: + energy_file.write(f"{i+num_structures_old} {energy_unrlxd[i]}\n") + # append energy per atom to the 'energies_rlxd_filename' file + with open(energies_rlxd_filename, "a") as energy_file: + energy_file.write(f"{i+num_structures_old} {energy_rlxd[i]}\n") + + # update the distribution functions + print("Updating distributions") + generator.distributions.update(generated_structures[num_structures_old:], from_host=False, deallocate_systems=False) + + # print the new distribution functions to a file + print("Printing distributions") + generator.distributions.write_dfs(iterdir+"distributions.txt") + generator.distributions.write_2body(iterdir+"df2.txt") + generator.distributions.write_3body(iterdir+"df3.txt") + generator.distributions.write_4body(iterdir+"df4.txt") + generator.distributions.deallocate_systems() + + # update the number of structures generated + num_structures_old = num_structures_new + + + # Write the final distribution functions to a file + generator.distributions.write_gdfs(f"gdfs_seed{seed}.txt") + + # Read energies from the file + with open(energies_rlxd_filename, "r") as energy_file: + energies = energy_file.readlines() + + # Parse and sort the energies + energies = [line.strip().split() for line in energies] + energies = sorted(energies, key=lambda x: float(x[1])) + + # Write the sorted energies back to the file + with open(f"sorted_{energies_rlxd_filename}", "w") as energy_file: + for entry in energies: + energy_file.write(f"{int(entry[0])} {float(entry[1])}\n") + + # Write the structures to files + write(f"unrlxd_structures_seed{seed}.traj", unrlxd_structures) + write(f"rlxd_structures_seed{seed}.traj", rlxd_structures) + print("All generated and relaxed structures written") + + print("Learning complete") \ No newline at end of file diff --git a/example/python_pkg/Si-Ge_learn/DRAFFLE/pca.ipynb b/example/python_pkg/Si-Ge_learn/DRAFFLE/pca.ipynb new file mode 100644 index 00000000..60054ec0 --- /dev/null +++ b/example/python_pkg/Si-Ge_learn/DRAFFLE/pca.ipynb @@ -0,0 +1,623 @@ +{ + "cells": [ + { + "cell_type": "code", + "execution_count": 6, + "metadata": {}, + "outputs": [], + "source": [ + "import matplotlib.pyplot as plt\n", + "%matplotlib inline\n", + "\n", + "# matplotlib.use(\"Agg\")\n", + "\n", + "from ase import build\n", + "from ase.optimize import FIRE\n", + "from ase.io import read\n", + "from agox.databases import Database\n", + "from agox.environments import Environment\n", + "from agox.utils.graph_sorting import Analysis\n", + "\n", + "import numpy as np\n", + "from sklearn.decomposition import PCA\n", + "from matplotlib.ticker import (MultipleLocator, AutoMinorLocator)" + ] + }, + { + "cell_type": "code", + "execution_count": 7, + "metadata": {}, + "outputs": [], + "source": [ + "## Set up the plotting environment\n", + "# matplotlib.rcParams.update(matplotlib.rcParamsDefault)\n", + "plt.rc('text', usetex=True)\n", + "plt.rc('font', family='cmr10', size=12)\n", + "plt.rcParams[\"axes.formatter.use_mathtext\"] = True" + ] + }, + { + "cell_type": "code", + "execution_count": 8, + "metadata": {}, + "outputs": [], + "source": [ + "## Set the plotting parameters\n", + "seed = 0\n", + "identifier1 = \"\"\n", + "# identifier2 = \"3\"\n", + "# min_energy = -3.6635127# -3.7717605425" + ] + }, + { + "cell_type": "code", + "execution_count": 9, + "metadata": {}, + "outputs": [], + "source": [ + "## Set the descriptors\n", + "from agox.models.descriptors import SOAP, Voronoi\n", + "local_descriptor = local_descriptor = SOAP.from_species([\"Si\", \"Ge\"], r_cut=5.0)\n", + "\n", + "graph_descriptor = Voronoi(\n", + " covalent_bond_scale_factor=1.3, n_points=8, angle_from_central_atom=20, environment=None\n", + ")" + ] + }, + { + "cell_type": "code", + "execution_count": 10, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Using float32 for MACECalculator, which is faster but less accurate. Recommended for MD. Use float64 for geometry optimization.\n", + "Default dtype float32 does not match model dtype float64, converting models to float32.\n" + ] + }, + { + "name": "stderr", + "output_type": "stream", + "text": [ + "/opt/homebrew/Caskroom/miniconda/base/envs/raffle_env/lib/python3.12/site-packages/mace/calculators/mace.py:135: FutureWarning: You are using `torch.load` with `weights_only=False` (the current default value), which uses the default pickle module implicitly. It is possible to construct malicious pickle data which will execute arbitrary code during unpickling (See https://github.com/pytorch/pytorch/blob/main/SECURITY.md#untrusted-models for more details). In a future release, the default value for `weights_only` will be flipped to `True`. This limits the functions that could be executed during unpickling. Arbitrary objects will no longer be allowed to be loaded via this mode unless they are explicitly allowlisted by the user via `torch.serialization.add_safe_globals`. We recommend you start setting `weights_only=True` for any use case where you don't have full control of the loaded file. Please open an issue on GitHub for any issues related to this experimental feature.\n", + " torch.load(f=model_path, map_location=device)\n" + ] + } + ], + "source": [ + "## Set the calculators\n", + "# from chgnet.model import CHGNetCalculator\n", + "from mace.calculators import mace_mp\n", + "from ase.calculators.singlepoint import SinglePointCalculator\n", + "# calc = CHGNetCalculator()\n", + "calc = mace_mp(model=\"mace-mpa-0-medium.model\")" + ] + }, + { + "cell_type": "code", + "execution_count": 11, + "metadata": {}, + "outputs": [], + "source": [ + "## Load the unrelaxed structures\n", + "unrlxd_structures1 = read(\"DOutput\"+identifier1+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "for structure in unrlxd_structures1:\n", + " structure.calc = calc\n", + "\n", + "# ## Load the additional relaxed structures\n", + "# unrlxd_structures2 = read(\"DOutput\"+identifier2+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n" + ] + }, + { + "cell_type": "code", + "execution_count": 12, + "metadata": {}, + "outputs": [], + "source": [ + "## Load the relaxed structures\n", + "rlxd_structures1 = read(\"DOutput\"+identifier1+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", + "for structure in rlxd_structures1:\n", + " structure.calc = calc\n", + "\n", + "# ## Load the additional relaxed structures\n", + "# rlxd_structures2 = read(\"DOutput\"+identifier2+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")" + ] + }, + { + "cell_type": "code", + "execution_count": 13, + "metadata": {}, + "outputs": [], + "source": [ + "## Read energies from energies_unrlxd_seed0.txt and add to the respective structures using a SinglePointCalculator\n", + "## The file has the form \"index energy\"\n", + "## This is done because there seem to be issues with storing the energy in the ASE trajectory file for some setups\n", + "filename = \"DOutput\"+identifier1+\"/energies_unrlxd_seed\"+str(seed)+\".txt\"\n", + "with open(filename) as f:\n", + " for line in f:\n", + " index, energy = line.split()\n", + " index = int(index)\n", + " energy = float(energy)\n", + " unrlxd_structures1[index].calc = SinglePointCalculator(unrlxd_structures1[index], energy=energy * len(unrlxd_structures1[index]))\n", + "\n", + "\n", + "filename = \"DOutput\"+identifier1+\"/energies_rlxd_seed\"+str(seed)+\".txt\"\n", + "with open(filename) as f:\n", + " for line in f:\n", + " index, energy = line.split()\n", + " index = int(index)\n", + " energy = float(energy)\n", + " rlxd_structures1[index].calc = SinglePointCalculator(rlxd_structures1[index], energy=energy * len(rlxd_structures1[index]))\n", + "\n", + "# filename = \"DOutput\"+identifier2+\"/energies_unrlxd_seed\"+str(seed)+\".txt\"\n", + "# with open(filename) as f:\n", + "# for line in f:\n", + "# index, energy = line.split()\n", + "# index = int(index)\n", + "# energy = float(energy)\n", + "# unrlxd_structures2[index].calc = SinglePointCalculator(unrlxd_structures2[index], energy=energy * len(unrlxd_structures2[index]))\n", + "\n", + "\n", + "# filename = \"DOutput\"+identifier2+\"/energies_rlxd_seed\"+str(seed)+\".txt\"\n", + "# with open(filename) as f:\n", + "# for line in f:\n", + "# index, energy = line.split()\n", + "# index = int(index)\n", + "# energy = float(energy)\n", + "# rlxd_structures2[index].calc = SinglePointCalculator(rlxd_structures2[index], energy=energy * len(rlxd_structures2[index]))" + ] + }, + { + "cell_type": "code", + "execution_count": 14, + "metadata": {}, + "outputs": [], + "source": [ + "unrlxd_structures = unrlxd_structures1 #+ unrlxd_structures2\n", + "rlxd_structures = rlxd_structures1 #+ rlxd_structures2" + ] + }, + { + "cell_type": "code", + "execution_count": 15, + "metadata": {}, + "outputs": [], + "source": [ + "## Get bulk reference energies\n", + "Si_bulk = build.bulk(\"Si\", crystalstructure=\"diamond\", a=5.43)\n", + "Si_bulk.calc = calc\n", + "Si_reference_energy = Si_bulk.get_potential_energy() / len(Si_bulk)\n", + "Si_cubic = build.make_supercell(Si_bulk, [[-1, 1, 1], [1, -1, 1], [1, 1, -1]])\n", + "\n", + "Ge_bulk = build.bulk(\"Ge\", crystalstructure=\"diamond\", a=5.65)\n", + "Ge_bulk.calc = calc\n", + "Ge_reference_energy = Ge_bulk.get_potential_energy() / len(Ge_bulk)\n", + "Ge_cubic = build.make_supercell(Ge_bulk, [[-1, 1, 1], [1, -1, 1], [1, 1, -1]])\n" + ] + }, + { + "cell_type": "code", + "execution_count": 16, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + " Step Time Energy fmax\n", + "FIRE: 0 09:37:36 -404.223419 0.308327\n", + "FIRE: 1 09:37:36 -404.241852 0.287606\n", + "FIRE: 2 09:37:36 -404.272003 0.248617\n", + "FIRE: 3 09:37:37 -404.303772 0.195892\n", + "FIRE: 4 09:37:37 -404.329620 0.135901\n", + "FIRE: 5 09:37:37 -404.347687 0.144643\n", + "FIRE: 6 09:37:37 -404.362213 0.175805\n", + "FIRE: 7 09:37:38 -404.376984 0.175536\n", + "FIRE: 8 09:37:38 -404.394958 0.142853\n", + "FIRE: 9 09:37:38 -404.413055 0.100423\n", + "FIRE: 10 09:37:39 -404.429321 0.129503\n", + "FIRE: 11 09:37:39 -404.447083 0.121735\n", + "FIRE: 12 09:37:39 -404.468445 0.077042\n", + "FIRE: 13 09:37:40 -404.486176 0.055705\n", + "FIRE: 14 09:37:40 -404.490448 0.068701\n", + "FIRE: 15 09:37:40 -404.491455 0.059911\n", + "FIRE: 16 09:37:40 -404.493134 0.043550\n", + " Step Time Energy fmax\n", + "FIRE: 0 09:37:41 -346.881958 0.666953\n", + "FIRE: 1 09:37:41 -346.957520 0.634437\n", + "FIRE: 2 09:37:41 -347.092957 0.572620\n", + "FIRE: 3 09:37:41 -347.262268 0.487324\n", + "FIRE: 4 09:37:42 -347.436462 0.385976\n", + "FIRE: 5 09:37:42 -347.591003 0.276925\n", + "FIRE: 6 09:37:42 -347.711609 0.213073\n", + "FIRE: 7 09:37:42 -347.796143 0.225150\n", + "FIRE: 8 09:37:43 -347.859192 0.209056\n", + "FIRE: 9 09:37:43 -347.912292 0.221024\n", + "FIRE: 10 09:37:43 -347.974304 0.227086\n", + "FIRE: 11 09:37:43 -348.062683 0.211165\n", + "FIRE: 12 09:37:43 -348.180664 0.205920\n", + "FIRE: 13 09:37:44 -348.289246 0.142311\n", + "FIRE: 14 09:37:44 -348.345886 0.030842\n" + ] + }, + { + "data": { + "text/plain": [ + "True" + ] + }, + "execution_count": 16, + "metadata": {}, + "output_type": "execute_result" + } + ], + "source": [ + "## Get slab energetics\n", + "Si_slab_vac = read(\"../Si_slab.vasp\")\n", + "Ge_slab_vac = read(\"../Ge_slab.vasp\")\n", + "Si_slab_vac.calc = calc\n", + "Ge_slab_vac.calc = calc\n", + "optimizer = FIRE(Si_slab_vac)\n", + "optimizer.run(fmax=0.05, steps=100)\n", + "optimizer = FIRE(Ge_slab_vac)\n", + "optimizer.run(fmax=0.05, steps=100)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [ + { + "ename": "FileNotFoundError", + "evalue": "[Errno 2] No such file or directory: 'SiGe_abrupt_interface.vasp'", + "output_type": "error", + "traceback": [ + "\u001b[0;31m---------------------------------------------------------------------------\u001b[0m", + "\u001b[0;31mFileNotFoundError\u001b[0m Traceback (most recent call last)", + "Cell \u001b[0;32mIn[17], line 2\u001b[0m\n\u001b[1;32m 1\u001b[0m \u001b[38;5;66;03m## Get abrupt interface energetics\u001b[39;00m\n\u001b[0;32m----> 2\u001b[0m SiGe_abrupt \u001b[38;5;241m=\u001b[39m \u001b[43mread\u001b[49m\u001b[43m(\u001b[49m\u001b[38;5;124;43m\"\u001b[39;49m\u001b[38;5;124;43mSiGe_abrupt_interface.vasp\u001b[39;49m\u001b[38;5;124;43m\"\u001b[39;49m\u001b[43m)\u001b[49m\n\u001b[1;32m 3\u001b[0m SiGe_abrupt\u001b[38;5;241m.\u001b[39mcalc \u001b[38;5;241m=\u001b[39m calc\n\u001b[1;32m 4\u001b[0m SiGe_abrupt\u001b[38;5;241m.\u001b[39mset_cell(rlxd_structures[\u001b[38;5;241m0\u001b[39m]\u001b[38;5;241m.\u001b[39mget_cell(), scale_atoms\u001b[38;5;241m=\u001b[39m\u001b[38;5;28;01mTrue\u001b[39;00m)\n", + "File \u001b[0;32m/opt/homebrew/Caskroom/miniconda/base/envs/raffle_env/lib/python3.12/site-packages/ase/io/formats.py:793\u001b[0m, in \u001b[0;36mread\u001b[0;34m(filename, index, format, parallel, do_not_split_by_at_sign, **kwargs)\u001b[0m\n\u001b[1;32m 791\u001b[0m \u001b[38;5;28;01mif\u001b[39;00m index \u001b[38;5;129;01mis\u001b[39;00m \u001b[38;5;28;01mNone\u001b[39;00m:\n\u001b[1;32m 792\u001b[0m index \u001b[38;5;241m=\u001b[39m \u001b[38;5;241m-\u001b[39m\u001b[38;5;241m1\u001b[39m\n\u001b[0;32m--> 793\u001b[0m \u001b[38;5;28mformat\u001b[39m \u001b[38;5;241m=\u001b[39m \u001b[38;5;28mformat\u001b[39m \u001b[38;5;129;01mor\u001b[39;00m \u001b[43mfiletype\u001b[49m\u001b[43m(\u001b[49m\u001b[43mfilename\u001b[49m\u001b[43m,\u001b[49m\u001b[43m \u001b[49m\u001b[43mread\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[38;5;28;43misinstance\u001b[39;49m\u001b[43m(\u001b[49m\u001b[43mfilename\u001b[49m\u001b[43m,\u001b[49m\u001b[43m \u001b[49m\u001b[38;5;28;43mstr\u001b[39;49m\u001b[43m)\u001b[49m\u001b[43m)\u001b[49m\n\u001b[1;32m 795\u001b[0m io \u001b[38;5;241m=\u001b[39m get_ioformat(\u001b[38;5;28mformat\u001b[39m)\n\u001b[1;32m 796\u001b[0m \u001b[38;5;28;01mif\u001b[39;00m \u001b[38;5;28misinstance\u001b[39m(index, (\u001b[38;5;28mslice\u001b[39m, \u001b[38;5;28mstr\u001b[39m)):\n", + "File \u001b[0;32m/opt/homebrew/Caskroom/miniconda/base/envs/raffle_env/lib/python3.12/site-packages/ase/io/formats.py:965\u001b[0m, in \u001b[0;36mfiletype\u001b[0;34m(filename, read, guess)\u001b[0m\n\u001b[1;32m 962\u001b[0m \u001b[38;5;28;01mreturn\u001b[39;00m ext\n\u001b[1;32m 964\u001b[0m \u001b[38;5;28;01mif\u001b[39;00m orig_filename \u001b[38;5;241m==\u001b[39m filename:\n\u001b[0;32m--> 965\u001b[0m fd \u001b[38;5;241m=\u001b[39m \u001b[43mopen_with_compression\u001b[49m\u001b[43m(\u001b[49m\u001b[43mfilename\u001b[49m\u001b[43m,\u001b[49m\u001b[43m \u001b[49m\u001b[38;5;124;43m'\u001b[39;49m\u001b[38;5;124;43mrb\u001b[39;49m\u001b[38;5;124;43m'\u001b[39;49m\u001b[43m)\u001b[49m\n\u001b[1;32m 966\u001b[0m \u001b[38;5;28;01melse\u001b[39;00m:\n\u001b[1;32m 967\u001b[0m fd \u001b[38;5;241m=\u001b[39m orig_filename \u001b[38;5;66;03m# type: ignore[assignment]\u001b[39;00m\n", + "File \u001b[0;32m/opt/homebrew/Caskroom/miniconda/base/envs/raffle_env/lib/python3.12/site-packages/ase/io/formats.py:597\u001b[0m, in \u001b[0;36mopen_with_compression\u001b[0;34m(filename, mode)\u001b[0m\n\u001b[1;32m 594\u001b[0m \u001b[38;5;28;01mreturn\u001b[39;00m lzma\u001b[38;5;241m.\u001b[39mopen(filename, mode)\n\u001b[1;32m 595\u001b[0m \u001b[38;5;28;01melse\u001b[39;00m:\n\u001b[1;32m 596\u001b[0m \u001b[38;5;66;03m# Either None or unknown string\u001b[39;00m\n\u001b[0;32m--> 597\u001b[0m \u001b[38;5;28;01mreturn\u001b[39;00m \u001b[38;5;28;43mopen\u001b[39;49m\u001b[43m(\u001b[49m\u001b[43mfilename\u001b[49m\u001b[43m,\u001b[49m\u001b[43m \u001b[49m\u001b[43mmode\u001b[49m\u001b[43m)\u001b[49m\n", + "\u001b[0;31mFileNotFoundError\u001b[0m: [Errno 2] No such file or directory: 'SiGe_abrupt_interface.vasp'" + ] + } + ], + "source": [ + "## Get abrupt interface energetics\n", + "SiGe_abrupt = read(\"../SiGe_abrupt_interface.vasp\")\n", + "SiGe_abrupt.calc = calc\n", + "SiGe_abrupt.set_cell(rlxd_structures[0].get_cell(), scale_atoms=True)\n", + "optimizer = FIRE(SiGe_abrupt)\n", + "optimizer.run(fmax=0.05, steps=100)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Interface area: 122.76639830932618\n" + ] + } + ], + "source": [ + "## Get abrupt interface area\n", + "area = np.linalg.norm(np.cross(SiGe_abrupt.get_cell()[0], SiGe_abrupt.get_cell()[1]))\n", + "print(\"Interface area: \", area)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Function to get the interface formation energy\n", + "def get_interface_energy(struc, Si_slab, Ge_slab, extra=False):\n", + " energy = struc.get_potential_energy()\n", + " cell = struc.get_cell()\n", + " area = np.linalg.norm(np.cross(cell[0], cell[1]))\n", + " Si_energy = Si_slab.get_potential_energy()\n", + " Ge_energy = Ge_slab.get_potential_energy()\n", + " ## need to subtract remaining silicon and germanium energies also\n", + " if extra:\n", + " return (energy - Si_energy - Ge_energy - 16*(Si_reference_energy + Ge_reference_energy)) / (2.0 * area)\n", + " else:\n", + " return (energy - Si_energy - Ge_energy) / (2.0 * area)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "# print(\"abrupt match 2 layers energy: \", get_interface_energy(abrupt, Si_slab, Ge_slab))\n", + "# print(\"abrupt match 3 layers energy: \", get_interface_energy(abrupt_3, Si_slab_3, Ge_slab_3))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Abrupt min energy: -0.15245676545796508\n" + ] + } + ], + "source": [ + "abrupt_en_per_area = get_interface_energy(SiGe_abrupt, Si_slab_vac, Ge_slab_vac, False)\n", + "print(\"Abrupt min energy: \", abrupt_en_per_area)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Unrelaxed min energy: 0.029598842486012463\n" + ] + } + ], + "source": [ + "## Calculate energies per atom for each unrelaxed structure\n", + "unrlxd_en_per_area = [get_interface_energy(structure, Si_slab_vac, Ge_slab_vac, False) for structure in unrlxd_structures]\n", + "print(\"Unrelaxed min energy: \", np.min(unrlxd_en_per_area))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Relaxed min energy: -0.15207966580648735\n" + ] + } + ], + "source": [ + "## Calculate energies per atom for each relaxed structure\n", + "rlxd_en_per_area = [get_interface_energy(structure, Si_slab_vac, Ge_slab_vac, False) for structure in rlxd_structures]\n", + "print(\"Relaxed min energy: \", np.min(rlxd_en_per_area))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Set up the PCA\n", + "pca = PCA(n_components=2)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the 'super atom' descriptors for the unrelaxed structures\n", + "unrlxd_super_atoms = []\n", + "for structure in unrlxd_structures:\n", + " unrlxd_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Get the 'super atom' descriptors for the relaxed structures\n", + "rlxd_super_atoms = []\n", + "for structure in rlxd_structures:\n", + " rlxd_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Fit the PCA model to the unrelaxed or relaxed structures\n", + "rlxd_string = \"rlxd\"" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Save pca model\n", + "import pickle\n", + "if True:\n", + " pca.fit(np.squeeze([arr for arr in rlxd_super_atoms]))\n", + " with open(\"pca_model_all_rlxd_\"+str(seed)+\".pkl\", \"wb\") as f:\n", + " pickle.dump(pca, f)\n", + "\n", + "## Load pca model\n", + "with open(\"pca_model_all_\"+rlxd_string+\"_0.pkl\", \"rb\") as f:\n", + " pca = pickle.load(f)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "abrupt_super_atom = []\n", + "abrupt_super_atom.append(np.mean(local_descriptor.get_features(SiGe_abrupt), axis=0))\n", + "abrupt_super_atom.append(np.mean(local_descriptor.get_features(SiGe_abrupt), axis=0))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [ + "## Transform the unrelaxed and relaxed structures to the reduced space\n", + "unrlxd_X_reduced = pca.transform(np.squeeze([arr for arr in unrlxd_super_atoms]))\n", + "rlxd_X_reduced = pca.transform(np.squeeze([arr for arr in rlxd_super_atoms]))\n", + "abrupt_X_reduced = pca.transform(np.squeeze([arr for arr in abrupt_super_atom]))" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "186\n" + ] + } + ], + "source": [ + "## Get the index of the structure with the minimum energy\n", + "min_energy_index = np.argmin(rlxd_en_per_area)\n", + "print(min_energy_index)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [ + { + "data": { + "image/png": "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", + "text/plain": [ + "
" + ] + }, + "metadata": {}, + "output_type": "display_data" + } + ], + "source": [ + "## Plot the PCA\n", + "fig, axes = plt.subplots(nrows=1, ncols=2, figsize=(8, 6))\n", + "\n", + "plt.subplots_adjust(wspace=0.05, hspace=0)\n", + "\n", + "## Get the maximum energy for the colourbar\n", + "scaled_unrlxd_ens = [x * 1000 for x in unrlxd_en_per_area]\n", + "scaled_rlxd_ens = [x * 1000 for x in rlxd_en_per_area]\n", + "scaled_abrupt_en = abrupt_en_per_area * 1000\n", + "min_en = max(scaled_abrupt_en, min(np.min(scaled_unrlxd_ens), np.min(scaled_rlxd_ens)))\n", + "max_en = min(max(np.max(scaled_unrlxd_ens), np.max(scaled_rlxd_ens)), -0.1*1000)\n", + "\n", + "## Plot the PCA\n", + "axes[0].scatter(unrlxd_X_reduced[:, 0], unrlxd_X_reduced[:, 1], c=scaled_unrlxd_ens, cmap=\"viridis\", vmin = min_en, vmax = max_en)\n", + "axes[1].scatter(rlxd_X_reduced[:, 0], rlxd_X_reduced[:, 1], c=scaled_rlxd_ens, cmap=\"viridis\", vmin = min_en, vmax = max_en)\n", + "\n", + "## Add the minimum energy structures to the plot\n", + "for ax in axes:\n", + " ax.scatter(abrupt_X_reduced[0, 0], abrupt_X_reduced[0, 1], s=200, edgecolor='red', facecolor='none', linewidth=2, label=\"Abrupt interface\")\n", + " ax.scatter(abrupt_X_reduced[0, 0], abrupt_X_reduced[0, 1], c=scaled_abrupt_en, cmap=\"viridis\", vmin = min_en, vmax = max_en)\n", + " if ax == axes[1]:\n", + " handles, labels = ax.get_legend_handles_labels()\n", + " ax.legend(handles[::-1], labels[::-1], facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, bbox_to_anchor=(1.0, 1.0), fontsize=20, handletextpad=0.2, borderpad=0.3, handlelength=1)\n", + " \n", + "## Add labels\n", + "fig.text(0.5, 0.0, 'Principal component 1', ha='center', fontsize=20)\n", + "axes[0].set_ylabel('Principal component 2', fontsize=20)\n", + "axes[0].set_title('Unrelaxed', fontsize=20)\n", + "axes[1].set_title('Relaxed', fontsize=20)\n", + "if rlxd_string == \"rlxd\":\n", + " xlims = [-3, 3.5]\n", + " ylims = [-1, 4]\n", + "else:\n", + " xlims = [-42, 55]\n", + " ylims = [-12, 30]\n", + "\n", + "for ax in axes:\n", + " ax.tick_params(axis='both', direction='in', length=6, labelsize=20)\n", + " ax.yaxis.set_major_locator(MultipleLocator(1))\n", + " ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.xaxis.set_minor_locator(AutoMinorLocator(2))\n", + " ax.tick_params(axis='both', which='minor', length=3, direction='in')\n", + " ax.set_xlim(xlims)\n", + " ax.set_ylim(ylims)\n", + "\n", + "## Unify tick labels\n", + "xticks = axes[0].get_xticks()\n", + "xticks = xticks[(xticks >= xlims[0]) & (xticks <= xlims[1])]\n", + "\n", + "axes[1].set_xticks(xticks)\n", + "axes[1].set_yticklabels([])\n", + "axes[0].tick_params(axis='x', labelbottom=True, top=True)\n", + "axes[1].tick_params(axis='x', labelbottom=True, top=True)\n", + "axes[0].tick_params(axis='y', labelbottom=True, right=True)\n", + "axes[1].tick_params(axis='y', labelbottom=True, right=True)\n", + "\n", + "## Make axes[0] and axes[1] the same width\n", + "axes[0].set_box_aspect(1.7)\n", + "axes[1].set_box_aspect(1.7)\n", + "\n", + "## Add colorbar next to the axes\n", + "cbar = fig.colorbar(axes[1].collections[0], ax=axes, orientation='vertical', fraction=0.085, pad=0.02)\n", + "cbar.ax.tick_params(labelsize=20)\n", + "# cbar.ax.yaxis.set_major_locator(plt.FixedLocator([-61, -59, -57, -55, -53, -51]))\n", + "cbar.ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", + "cbar.set_label('Formation energy (meV/Å$^2$)', fontsize=20)\n", + "\n", + "## Save the figure\n", + "plt.savefig('Si-Ge_RAFFLE'+identifier1+'_pca_'+rlxd_string+'_fit_seed'+str(seed)+'.pdf', bbox_inches='tight', pad_inches=0, facecolor=fig.get_facecolor(), edgecolor='none')" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [] + } + ], + "metadata": { + "kernelspec": { + "display_name": "raffle_env", + "language": "python", + "name": "python3" + }, + "language_info": { + "codemirror_mode": { + "name": "ipython", + "version": 3 + }, + "file_extension": ".py", + "mimetype": "text/x-python", + "name": "python", + "nbconvert_exporter": "python", + "pygments_lexer": "ipython3", + "version": "3.12.8" + } + }, + "nbformat": 4, + "nbformat_minor": 2 +} diff --git a/example/python_pkg/Si-Ge_learn/learn.py b/example/python_pkg/Si-Ge_learn/learn.py index af20687a..4697fdd8 100644 --- a/example/python_pkg/Si-Ge_learn/learn.py +++ b/example/python_pkg/Si-Ge_learn/learn.py @@ -1,4 +1,4 @@ -from chgnet.model import CHGNetCalculator +from mace.calculators import mace_mp from raffle.generator import raffle_generator from ase import build from ase.optimize import FIRE @@ -57,8 +57,8 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct if __name__ == "__main__": # set up the calculator - calc_params = {} - calc = CHGNetCalculator() + calc_params = { 'model': "../mace-mpa-0-medium.model" } + calc = mace_mp(**calc_params) # set up the hosts hosts = [] @@ -136,7 +136,7 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct num_structures_old = 0 optimise_structure = True # start the iterations, loop over the hosts, then repeat the process X times - for ival in range(20): + for ival in range(40): for host in hosts: print("setting host") generator.set_host(host) @@ -150,7 +150,7 @@ def process_structure(i, atoms, num_structures_old, calc_params, optimise_struct num_structures = 5, stoichiometry = { 'Si': 16, 'Ge': 16 }, seed = seed*1000+iter, - method_probab = {"void": 0.3, "rand": 0.01, "walk": 0.3, "grow": 0.0, "min": 1.0}, + method_ratio = {"void": 0.1, "rand": 0.01, "walk": 0.25, "grow": 0.25, "min": 1.0}, verbose = 0, ) diff --git a/example/python_pkg/Si-Ge_learn/pca.ipynb b/example/python_pkg/Si-Ge_learn/pca.ipynb deleted file mode 100644 index 53cb3d9b..00000000 --- a/example/python_pkg/Si-Ge_learn/pca.ipynb +++ /dev/null @@ -1,620 +0,0 @@ -{ - "cells": [ - { - "cell_type": "code", - "execution_count": 1, - "metadata": {}, - "outputs": [ - { - "name": "stderr", - "output_type": "stream", - "text": [ - "/home/ntt203/.conda/envs/raffle_env/lib/python3.12/site-packages/tqdm/auto.py:21: TqdmWarning: IProgress not found. Please update jupyter and ipywidgets. See https://ipywidgets.readthedocs.io/en/stable/user_install.html\n", - " from .autonotebook import tqdm as notebook_tqdm\n", - "2025-02-14 14:06:37,323\tINFO util.py:154 -- Missing packages: ['ipywidgets']. Run `pip install -U ipywidgets`, then restart the notebook server for rich notebook output.\n" - ] - } - ], - "source": [ - "import matplotlib.pyplot as plt\n", - "%matplotlib inline\n", - "\n", - "# matplotlib.use(\"Agg\")\n", - "\n", - "from ase import build\n", - "from ase.optimize import FIRE\n", - "from ase.io import read\n", - "from agox.databases import Database\n", - "from agox.environments import Environment\n", - "from agox.utils.graph_sorting import Analysis\n", - "\n", - "import numpy as np\n", - "from sklearn.decomposition import PCA" - ] - }, - { - "cell_type": "code", - "execution_count": 2, - "metadata": {}, - "outputs": [], - "source": [ - "## Set up the plotting environment\n", - "# matplotlib.rcParams.update(matplotlib.rcParamsDefault)\n", - "plt.rc('text', usetex=True)\n", - "plt.rc('font', family='cmr10', size=12)\n", - "plt.rcParams[\"axes.formatter.use_mathtext\"] = True" - ] - }, - { - "cell_type": "code", - "execution_count": 3, - "metadata": {}, - "outputs": [], - "source": [ - "## Set the plotting parameters\n", - "seed = 0\n", - "identifier1 = \"2\"\n", - "identifier2 = \"3\"\n", - "# min_energy = -3.6635127# -3.7717605425" - ] - }, - { - "cell_type": "code", - "execution_count": 4, - "metadata": {}, - "outputs": [], - "source": [ - "## Set the descriptors\n", - "from agox.models.descriptors import SOAP, Voronoi\n", - "local_descriptor = local_descriptor = SOAP.from_species([\"Si\", \"Ge\"], r_cut=5.0)\n", - "\n", - "graph_descriptor = Voronoi(\n", - " covalent_bond_scale_factor=1.3, n_points=8, angle_from_central_atom=20, environment=None\n", - ")" - ] - }, - { - "cell_type": "code", - "execution_count": 5, - "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "CHGNet v0.3.0 initialized with 412,525 parameters\n", - "CHGNet will run on cuda\n" - ] - } - ], - "source": [ - "## Set the calculators\n", - "from chgnet.model import CHGNetCalculator\n", - "from ase.calculators.singlepoint import SinglePointCalculator\n", - "calc = CHGNetCalculator()" - ] - }, - { - "cell_type": "code", - "execution_count": 6, - "metadata": {}, - "outputs": [], - "source": [ - "## Load the unrelaxed structures\n", - "unrlxd_structures1 = read(\"DTMP\"+identifier1+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", - "for structure in unrlxd_structures1:\n", - " structure.calc = calc\n", - "\n", - "## Load the additional relaxed structures\n", - "unrlxd_structures2 = read(\"DTMP\"+identifier2+\"/unrlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n" - ] - }, - { - "cell_type": "code", - "execution_count": 7, - "metadata": {}, - "outputs": [], - "source": [ - "## Load the relaxed structures\n", - "rlxd_structures1 = read(\"DTMP\"+identifier1+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")\n", - "for structure in rlxd_structures1:\n", - " structure.calc = calc\n", - "\n", - "## Load the additional relaxed structures\n", - "rlxd_structures2 = read(\"DTMP\"+identifier2+\"/rlxd_structures_seed\"+str(seed)+\".traj\", index=\":\")" - ] - }, - { - "cell_type": "code", - "execution_count": 8, - "metadata": {}, - "outputs": [], - "source": [ - "## Read energies from energies_unrlxd_seed0.txt and add to the respective structures using a SinglePointCalculator\n", - "## The file has the form \"index energy\"\n", - "## This is done because there seem to be issues with storing the energy in the ASE trajectory file for some setups\n", - "filename = \"DTMP\"+identifier1+\"/energies_unrlxd_seed\"+str(seed)+\".txt\"\n", - "with open(filename) as f:\n", - " for line in f:\n", - " index, energy = line.split()\n", - " index = int(index)\n", - " energy = float(energy)\n", - " unrlxd_structures1[index].calc = SinglePointCalculator(unrlxd_structures1[index], energy=energy * len(unrlxd_structures1[index]))\n", - "\n", - "\n", - "filename = \"DTMP\"+identifier1+\"/energies_rlxd_seed\"+str(seed)+\".txt\"\n", - "with open(filename) as f:\n", - " for line in f:\n", - " index, energy = line.split()\n", - " index = int(index)\n", - " energy = float(energy)\n", - " rlxd_structures1[index].calc = SinglePointCalculator(rlxd_structures1[index], energy=energy * len(rlxd_structures1[index]))\n", - "\n", - "filename = \"DTMP\"+identifier2+\"/energies_unrlxd_seed\"+str(seed)+\".txt\"\n", - "with open(filename) as f:\n", - " for line in f:\n", - " index, energy = line.split()\n", - " index = int(index)\n", - " energy = float(energy)\n", - " unrlxd_structures2[index].calc = SinglePointCalculator(unrlxd_structures2[index], energy=energy * len(unrlxd_structures2[index]))\n", - "\n", - "\n", - "filename = \"DTMP\"+identifier2+\"/energies_rlxd_seed\"+str(seed)+\".txt\"\n", - "with open(filename) as f:\n", - " for line in f:\n", - " index, energy = line.split()\n", - " index = int(index)\n", - " energy = float(energy)\n", - " rlxd_structures2[index].calc = SinglePointCalculator(rlxd_structures2[index], energy=energy * len(rlxd_structures2[index]))" - ] - }, - { - "cell_type": "code", - "execution_count": 9, - "metadata": {}, - "outputs": [], - "source": [ - "unrlxd_structures = unrlxd_structures1 + unrlxd_structures2\n", - "rlxd_structures = rlxd_structures1 + rlxd_structures2" - ] - }, - { - "cell_type": "code", - "execution_count": 10, - "metadata": {}, - "outputs": [], - "source": [ - "## Get bulk reference energies\n", - "Si_bulk = build.bulk(\"Si\", crystalstructure=\"diamond\", a=5.43)\n", - "Si_bulk.calc = calc\n", - "Si_reference_energy = Si_bulk.get_potential_energy() / len(Si_bulk)\n", - "Si_cubic = build.make_supercell(Si_bulk, [[-1, 1, 1], [1, -1, 1], [1, 1, -1]])\n", - "\n", - "Ge_bulk = build.bulk(\"Ge\", crystalstructure=\"diamond\", a=5.65)\n", - "Ge_bulk.calc = calc\n", - "Ge_reference_energy = Ge_bulk.get_potential_energy() / len(Ge_bulk)\n", - "Ge_cubic = build.make_supercell(Ge_bulk, [[-1, 1, 1], [1, -1, 1], [1, 1, -1]])\n" - ] - }, - { - "cell_type": "code", - "execution_count": 11, - "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - " Step Time Energy fmax\n", - "FIRE: 0 14:06:39 -409.767609 0.108492\n", - "FIRE: 1 14:06:39 -409.770844 0.094166\n", - "FIRE: 2 14:06:39 -409.775543 0.067695\n", - "FIRE: 3 14:06:39 -409.779114 0.040967\n", - " Step Time Energy fmax\n", - "FIRE: 0 14:06:39 -345.926086 0.255276\n", - "FIRE: 1 14:06:39 -345.937805 0.245573\n", - "FIRE: 2 14:06:39 -345.959961 0.230154\n", - "FIRE: 3 14:06:39 -345.990173 0.200196\n", - "FIRE: 4 14:06:39 -346.024353 0.149001\n", - "FIRE: 5 14:06:39 -346.059906 0.150136\n", - "FIRE: 6 14:06:39 -346.098694 0.165835\n", - "FIRE: 7 14:06:39 -346.141357 0.170946\n", - "FIRE: 8 14:06:40 -346.193115 0.155803\n", - "FIRE: 9 14:06:40 -346.253418 0.119264\n", - "FIRE: 10 14:06:40 -346.319122 0.101087\n", - "FIRE: 11 14:06:40 -346.387390 0.098366\n", - "FIRE: 12 14:06:40 -346.457947 0.077963\n", - "FIRE: 13 14:06:40 -346.520935 0.059486\n", - "FIRE: 14 14:06:40 -346.565826 0.042929\n" - ] - }, - { - "data": { - "text/plain": [ - "np.True_" - ] - }, - "execution_count": 11, - "metadata": {}, - "output_type": "execute_result" - } - ], - "source": [ - "## Get slab energetics\n", - "Si_slab_vac = read(\"Si_slab.vasp\")\n", - "Ge_slab_vac = read(\"Ge_slab.vasp\")\n", - "Si_slab_vac.calc = calc\n", - "Ge_slab_vac.calc = calc\n", - "optimizer = FIRE(Si_slab_vac)\n", - "optimizer.run(fmax=0.05, steps=100)\n", - "optimizer = FIRE(Ge_slab_vac)\n", - "optimizer.run(fmax=0.05, steps=100)" - ] - }, - { - "cell_type": "code", - "execution_count": 12, - "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - " Step Time Energy fmax\n", - "FIRE: 0 14:06:40 -767.812805 0.584523\n", - "FIRE: 1 14:06:40 -767.876831 0.536846\n", - "FIRE: 2 14:06:40 -767.992432 0.464278\n", - "FIRE: 3 14:06:40 -768.138123 0.352445\n", - "FIRE: 4 14:06:40 -768.299438 0.250566\n", - "FIRE: 5 14:06:40 -768.467773 0.243208\n", - "FIRE: 6 14:06:40 -768.639587 0.254611\n", - "FIRE: 7 14:06:40 -768.819458 0.240592\n", - "FIRE: 8 14:06:40 -769.025574 0.200278\n", - "FIRE: 9 14:06:40 -769.251343 0.200775\n", - "FIRE: 10 14:06:40 -769.463135 0.211234\n", - "FIRE: 11 14:06:40 -769.657715 0.196226\n", - "FIRE: 12 14:06:40 -769.832764 0.177386\n", - "FIRE: 13 14:06:40 -769.973999 0.155502\n", - "FIRE: 14 14:06:41 -770.089355 0.136756\n", - "FIRE: 15 14:06:41 -770.179504 0.091195\n", - "FIRE: 16 14:06:41 -770.231201 0.065348\n", - "FIRE: 17 14:06:41 -770.248657 0.110161\n", - "FIRE: 18 14:06:41 -770.253174 0.094120\n", - "FIRE: 19 14:06:41 -770.259644 0.059759\n", - "FIRE: 20 14:06:41 -770.264160 0.033225\n" - ] - }, - { - "data": { - "text/plain": [ - "np.True_" - ] - }, - "execution_count": 12, - "metadata": {}, - "output_type": "execute_result" - } - ], - "source": [ - "## Get abrupt interface energetics\n", - "SiGe_abrupt = read(\"SiGe_abrupt_interface.vasp\")\n", - "SiGe_abrupt.calc = calc\n", - "SiGe_abrupt.set_cell(rlxd_structures[0].get_cell(), scale_atoms=True)\n", - "optimizer = FIRE(SiGe_abrupt)\n", - "optimizer.run(fmax=0.05, steps=100)" - ] - }, - { - "cell_type": "code", - "execution_count": 13, - "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "Interface area: 122.76639830932618\n" - ] - } - ], - "source": [ - "## Get abrupt interface area\n", - "area = np.linalg.norm(np.cross(SiGe_abrupt.get_cell()[0], SiGe_abrupt.get_cell()[1]))\n", - "print(\"Interface area: \", area)" - ] - }, - { - "cell_type": "code", - "execution_count": 14, - "metadata": {}, - "outputs": [], - "source": [ - "## Function to get the interface formation energy\n", - "def get_interface_energy(struc, Si_slab, Ge_slab, extra=False):\n", - " energy = struc.get_potential_energy()\n", - " cell = struc.get_cell()\n", - " area = np.linalg.norm(np.cross(cell[0], cell[1]))\n", - " Si_energy = Si_slab.get_potential_energy()\n", - " Ge_energy = Ge_slab.get_potential_energy()\n", - " ## need to subtract remaining silicon and germanium energies also\n", - " if extra:\n", - " return (energy - Si_energy - Ge_energy - 16*(Si_reference_energy + Ge_reference_energy)) / (2.0 * area)\n", - " else:\n", - " return (energy - Si_energy - Ge_energy) / (2.0 * area)" - ] - }, - { - "cell_type": "code", - "execution_count": 15, - "metadata": {}, - "outputs": [], - "source": [ - "# print(\"abrupt match 2 layers energy: \", get_interface_energy(abrupt, Si_slab, Ge_slab))\n", - "# print(\"abrupt match 3 layers energy: \", get_interface_energy(abrupt_3, Si_slab_3, Ge_slab_3))" - ] - }, - { - "cell_type": "code", - "execution_count": 16, - "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "Abrupt min energy: -0.05668986042757322\n" - ] - } - ], - "source": [ - "abrupt_en_per_area = get_interface_energy(SiGe_abrupt, Si_slab_vac, Ge_slab_vac, False)\n", - "print(\"Abrupt min energy: \", abrupt_en_per_area)" - ] - }, - { - "cell_type": "code", - "execution_count": 17, - "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "Unrelaxed min energy: 0.04692777709653661\n" - ] - } - ], - "source": [ - "## Calculate energies per atom for each unrelaxed structure\n", - "unrlxd_en_per_area = [get_interface_energy(structure, Si_slab_vac, Ge_slab_vac, False) for structure in unrlxd_structures]\n", - "print(\"Unrelaxed min energy: \", np.min(unrlxd_en_per_area))" - ] - }, - { - "cell_type": "code", - "execution_count": 18, - "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "Relaxed min energy: -0.06195806933579199\n" - ] - } - ], - "source": [ - "## Calculate energies per atom for each relaxed structure\n", - "rlxd_en_per_area = [get_interface_energy(structure, Si_slab_vac, Ge_slab_vac, False) for structure in rlxd_structures]\n", - "print(\"Relaxed min energy: \", np.min(rlxd_en_per_area))" - ] - }, - { - "cell_type": "code", - "execution_count": 19, - "metadata": {}, - "outputs": [], - "source": [ - "## Set up the PCA\n", - "pca = PCA(n_components=2)" - ] - }, - { - "cell_type": "code", - "execution_count": 20, - "metadata": {}, - "outputs": [], - "source": [ - "## Get the 'super atom' descriptors for the unrelaxed structures\n", - "unrlxd_super_atoms = []\n", - "for structure in unrlxd_structures:\n", - " unrlxd_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" - ] - }, - { - "cell_type": "code", - "execution_count": 21, - "metadata": {}, - "outputs": [], - "source": [ - "## Get the 'super atom' descriptors for the relaxed structures\n", - "rlxd_super_atoms = []\n", - "for structure in rlxd_structures:\n", - " rlxd_super_atoms.append( np.mean(local_descriptor.get_features(structure), axis=0) )" - ] - }, - { - "cell_type": "code", - "execution_count": 22, - "metadata": {}, - "outputs": [], - "source": [ - "## Fit the PCA model to the unrelaxed or relaxed structures\n", - "rlxd_string = \"rlxd\"" - ] - }, - { - "cell_type": "code", - "execution_count": 23, - "metadata": {}, - "outputs": [], - "source": [ - "## Save pca model\n", - "import pickle\n", - "if True:\n", - " pca.fit(np.squeeze([arr for arr in rlxd_super_atoms]))\n", - " with open(\"pca_model_all_rlxd_\"+str(seed)+\".pkl\", \"wb\") as f:\n", - " pickle.dump(pca, f)\n", - "\n", - "## Load pca model\n", - "with open(\"pca_model_all_\"+rlxd_string+\"_0.pkl\", \"rb\") as f:\n", - " pca = pickle.load(f)" - ] - }, - { - "cell_type": "code", - "execution_count": 24, - "metadata": {}, - "outputs": [], - "source": [ - "abrupt_super_atom = []\n", - "abrupt_super_atom.append(np.mean(local_descriptor.get_features(SiGe_abrupt), axis=0))\n", - "abrupt_super_atom.append(np.mean(local_descriptor.get_features(SiGe_abrupt), axis=0))" - ] - }, - { - "cell_type": "code", - "execution_count": 25, - "metadata": {}, - "outputs": [], - "source": [ - "## Transform the unrelaxed and relaxed structures to the reduced space\n", - "unrlxd_X_reduced = pca.transform(np.squeeze([arr for arr in unrlxd_super_atoms]))\n", - "rlxd_X_reduced = pca.transform(np.squeeze([arr for arr in rlxd_super_atoms]))\n", - "abrupt_X_reduced = pca.transform(np.squeeze([arr for arr in abrupt_super_atom]))" - ] - }, - { - "cell_type": "code", - "execution_count": 26, - "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "147\n" - ] - } - ], - "source": [ - "## Get the index of the structure with the minimum energy\n", - "min_energy_index = np.argmin(rlxd_en_per_area)\n", - "print(min_energy_index)" - ] - }, - { - "cell_type": "code", - "execution_count": 27, - "metadata": {}, - "outputs": [ - { - "data": { - "image/png": "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", - "text/plain": [ - "
" - ] - }, - "metadata": {}, - "output_type": "display_data" - } - ], - "source": [ - "## Plot the PCA\n", - "fig, axes = plt.subplots(nrows=1, ncols=2, figsize=(8, 6))\n", - "\n", - "plt.subplots_adjust(wspace=0.05, hspace=0)\n", - "\n", - "## Get the maximum energy for the colourbar\n", - "scaled_unrlxd_ens = [x * 1000 for x in unrlxd_en_per_area]\n", - "scaled_rlxd_ens = [x * 1000 for x in rlxd_en_per_area]\n", - "scaled_abrupt_en = abrupt_en_per_area * 1000\n", - "min_en = max(-0.08*1000, min(np.max(scaled_unrlxd_ens), np.min(scaled_rlxd_ens)))\n", - "max_en = min(max(np.max(scaled_unrlxd_ens), np.max(scaled_rlxd_ens)), scaled_abrupt_en)\n", - "\n", - "## Plot the PCA\n", - "axes[0].scatter(unrlxd_X_reduced[:, 0], unrlxd_X_reduced[:, 1], c=scaled_unrlxd_ens, cmap=\"viridis\", vmin = min_en, vmax = max_en)\n", - "axes[1].scatter(rlxd_X_reduced[:, 0], rlxd_X_reduced[:, 1], c=scaled_rlxd_ens, cmap=\"viridis\", vmin = min_en, vmax = max_en)\n", - "\n", - "## Add the minimum energy structures to the plot\n", - "for ax in axes:\n", - " ax.scatter(abrupt_X_reduced[0, 0], abrupt_X_reduced[0, 1], s=200, edgecolor='red', facecolor='none', linewidth=2, label=\"Abrupt interface\")\n", - " ax.scatter(abrupt_X_reduced[0, 0], abrupt_X_reduced[0, 1], c=abrupt_en_per_area, cmap=\"viridis\", vmin = min_en, vmax = max_en)\n", - " if ax == axes[1]:\n", - " ax.legend(fontsize=10)\n", - " handles, labels = ax.get_legend_handles_labels()\n", - " ax.legend(handles[::-1], labels[::-1], facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, loc='upper right')\n", - "\n", - "## Add labels\n", - "fig.text(0.5, 0.04, 'Principal Component 1', ha='center', fontsize=15)\n", - "axes[0].set_ylabel('Principal Component 2', fontsize=15)\n", - "axes[0].set_title('Unrelaxed')\n", - "axes[1].set_title('Relaxed')\n", - "if rlxd_string == \"rlxd\":\n", - " xlims = [-2, 5.8]\n", - " ylims = [-1, 2]\n", - "else:\n", - " xlims = [-42, 55]\n", - " ylims = [-12, 30]\n", - "\n", - "for ax in axes:\n", - " ax.tick_params(axis='both', direction='in')\n", - " ax.set_xlim(xlims)\n", - " ax.set_ylim(ylims)\n", - "\n", - "## Unify tick labels\n", - "xticks = axes[0].get_xticks()\n", - "xticks = xticks[(xticks >= xlims[0]) & (xticks <= xlims[1])]\n", - "\n", - "axes[1].set_xticks(xticks)\n", - "axes[1].set_yticklabels([])\n", - "axes[0].tick_params(axis='x', labelbottom=True, top=True)\n", - "axes[1].tick_params(axis='x', labelbottom=True, top=True)\n", - "axes[0].tick_params(axis='y', labelbottom=True, right=True)\n", - "axes[1].tick_params(axis='y', labelbottom=True, right=True)\n", - "\n", - "## Make axes[0] and axes[1] the same width\n", - "axes[0].set_box_aspect(1.7)\n", - "axes[1].set_box_aspect(1.7)\n", - "\n", - "## Add colorbar next to the axes\n", - "cbar = fig.colorbar(axes[1].collections[0], ax=axes, orientation='vertical', fraction=0.085, pad=0.02)\n", - "cbar.set_label('Formation energy (meV/Å$^2$)', fontsize=15)\n", - "\n", - "## Save the figure\n", - "plt.savefig('Si-Ge_RAFFLE'+identifier1+'_pca_'+rlxd_string+'_fit_seed'+str(seed)+'.pdf', bbox_inches='tight', pad_inches=0, facecolor=fig.get_facecolor(), edgecolor='none')" - ] - } - ], - "metadata": { - "kernelspec": { - "display_name": "Python 3", - "language": "python", - "name": "python3" - }, - "language_info": { - "codemirror_mode": { - "name": "ipython", - "version": 3 - }, - "file_extension": ".py", - "mimetype": "text/x-python", - "name": "python", - "nbconvert_exporter": "python", - "pygments_lexer": "ipython3", - "version": "3.12.2" - } - }, - "nbformat": 4, - "nbformat_minor": 2 -} diff --git a/example/python_pkg/benchmarks/cutoff_max.py b/example/python_pkg/benchmarks/cutoff_max.py index 74c86992..fa2aa35b 100644 --- a/example/python_pkg/benchmarks/cutoff_max.py +++ b/example/python_pkg/benchmarks/cutoff_max.py @@ -13,7 +13,7 @@ [0.025, np.pi/200.0, np.pi/200.0] ]) @pytest.mark.parametrize("grid_spacing", [0.1]) -@pytest.mark.parametrize("method_probab", [ +@pytest.mark.parametrize("method_ratio", [ {'void': 0.0, 'rand': 0.0, 'walk': 0.0, 'grow': 0.0, 'min': 1.0} ]) @pytest.mark.parametrize("cutoff_max", [4.0, 4.5, 5.0, 5.5, 6.0, 6.5, 7.0]) @@ -24,7 +24,7 @@ disable_gc=True, warmup=False ) -def test_cutoff_in_evaluator(benchmark, grid_spacing, kBT, width, method_probab, cutoff_max): +def test_cutoff_in_evaluator(benchmark, grid_spacing, kBT, width, method_ratio, cutoff_max): calc = CHGNetCalculator() current_dir = os.path.dirname(os.path.abspath(__file__)) @@ -61,7 +61,7 @@ def test_cutoff_in_evaluator(benchmark, grid_spacing, kBT, width, method_probab, "kBT": kBT, "width": width, "grid_spacing": grid_spacing, - "method_probab": method_probab, + "method_ratio": method_ratio, "cutoff_max": cutoff_max } @@ -76,7 +76,7 @@ def test_cutoff_in_evaluator(benchmark, grid_spacing, kBT, width, method_probab, [0.025, np.pi/200.0, np.pi/200.0] ]) @pytest.mark.parametrize("grid_spacing", [0.1]) -@pytest.mark.parametrize("method_probab", [ +@pytest.mark.parametrize("method_ratio", [ {'void': 0.0, 'rand': 0.0, 'walk': 0.0, 'grow': 0.0, 'min': 1.0} ]) @pytest.mark.parametrize("cutoff_max", [4.0, 4.5, 5.0, 5.5, 6.0, 6.5, 7.0]) @@ -87,7 +87,7 @@ def test_cutoff_in_evaluator(benchmark, grid_spacing, kBT, width, method_probab, disable_gc=True, warmup=False ) -def test_cutoff_in_database(benchmark, grid_spacing, kBT, width, method_probab, cutoff_max): +def test_cutoff_in_database(benchmark, grid_spacing, kBT, width, method_ratio, cutoff_max): calc = CHGNetCalculator() current_dir = os.path.dirname(os.path.abspath(__file__)) @@ -122,7 +122,7 @@ def test_cutoff_in_database(benchmark, grid_spacing, kBT, width, method_probab, "kBT": kBT, "width": width, "grid_spacing": grid_spacing, - "method_probab": method_probab, + "method_ratio": method_ratio, "cutoff_max": cutoff_max } diff --git a/example/python_pkg/benchmarks/min_placement.py b/example/python_pkg/benchmarks/min_placement.py index 29588fec..29beefcd 100644 --- a/example/python_pkg/benchmarks/min_placement.py +++ b/example/python_pkg/benchmarks/min_placement.py @@ -54,7 +54,7 @@ def test_min_placement(benchmark, grid_spacing, kBT, width): num_structures = 1, stoichiometry = {'C': 1}, seed = 0, - method_probab = { + method_ratio = { 'void': 0.0, 'rand': 0.0, 'walk': 0.0, diff --git a/example/python_pkg/benchmarks/placement_methods.py b/example/python_pkg/benchmarks/placement_methods.py index 40af62a7..34bb4631 100644 --- a/example/python_pkg/benchmarks/placement_methods.py +++ b/example/python_pkg/benchmarks/placement_methods.py @@ -11,7 +11,7 @@ [0.025, np.pi/200.0, np.pi/200.0] ]) @pytest.mark.parametrize("grid_spacing", [0.5, 0.25, 0.1, 0.075, 0.05]) -@pytest.mark.parametrize("method_probab", [ +@pytest.mark.parametrize("method_ratio", [ {'void': 0.0, 'rand': 0.0, 'walk': 0.0, 'grow': 0.0, 'min': 1.0}, {'void': 0.0, 'rand': 0.0, 'walk': 0.0, 'grow': 1.0, 'min': 0.0}, {'void': 0.0, 'rand': 0.0, 'walk': 1.0, 'grow': 0.0, 'min': 0.0}, @@ -25,7 +25,7 @@ disable_gc=True, warmup=False ) -def test_placement_methods(benchmark, grid_spacing, kBT, width, method_probab): +def test_placement_methods(benchmark, grid_spacing, kBT, width, method_ratio): calc = CHGNetCalculator() host = Atoms('C', positions=[(0, 0, 0)], cell=[3.567, 3.567, 3.567], pbc=True, calculator=calc) @@ -53,7 +53,7 @@ def test_placement_methods(benchmark, grid_spacing, kBT, width, method_probab): "kBT": kBT, "width": width, "grid_spacing": grid_spacing, - "method_probab": method_probab + "method_ratio": method_ratio } # Measure time for distributions.create() @@ -61,7 +61,7 @@ def test_placement_methods(benchmark, grid_spacing, kBT, width, method_probab): num_structures = 1, stoichiometry = {'C': 1}, seed = 0, - method_probab = method_probab, + method_ratio = method_ratio, verbose = 0 ) diff --git a/example/python_pkg/benchmarks/plot_benchmarks.ipynb b/example/python_pkg/benchmarks/plot_benchmarks.ipynb index 76408ae3..a6fcbd16 100644 --- a/example/python_pkg/benchmarks/plot_benchmarks.ipynb +++ b/example/python_pkg/benchmarks/plot_benchmarks.ipynb @@ -189,14 +189,23 @@ " x, y = zip(*time_data)\n", " plt.plot(x, [val * 1000 for val in y], marker='o', linestyle='--', label=brand)\n", "\n", - "plt.tick_params(axis='x', labelbottom=True, top=True)\n", - "plt.tick_params(axis='y', labelbottom=True, right=True)\n", + "plt.tick_params(axis='x', labelbottom=True, top=True, labelsize=20)\n", + "plt.tick_params(axis='y', labelbottom=True, right=True, labelsize=20)\n", "plt.tick_params(axis='both', which=\"both\", direction='in')\n", - "\n", - "plt.ylabel(\"Median Execution Time (ms)\", fontsize=15)\n", - "plt.xlabel(\"Upper bondlength cutoff (Å)\", fontsize=15)\n", - "plt.legend(facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False)\n", - "plt.grid(axis=\"y\", linestyle=\"--\", alpha=0.7)\n", + "# set major ticks to every 50\n", + "plt.gca().yaxis.set_major_locator(MultipleLocator(50))\n", + "# add one minor tick for each major tick\n", + "plt.gca().yaxis.set_minor_locator(AutoMinorLocator(2))\n", + "# make major and minor ticks longer\n", + "plt.tick_params(which='both', width=1, length=6)\n", + "plt.tick_params(which='minor', width=1, length=3)\n", + "\n", + "plt.ylabel(\"Median execution time (ms)\", fontsize=25)\n", + "plt.xlabel(\"Upper bond length cutoff (Å)\", fontsize=25)\n", + "# set aspet ratio so that the output is a square\n", + "plt.legend(facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, fontsize=16)\n", + "# plt.grid(axis=\"y\", linestyle=\"--\", alpha=0.7)\n", + "plt.gca().set_aspect(1.0/plt.gca().get_data_ratio(), adjustable='box')\n", "fig.show()\n", "\n", "plt.savefig('benchmark_cutoff_max_database.pdf', bbox_inches='tight', pad_inches=0, facecolor=fig.get_facecolor(), edgecolor='none')" @@ -231,14 +240,23 @@ " x, y = zip(*time_data)\n", " plt.plot(x, [val * 1000 for val in y], marker='o', linestyle='--', label=brand)\n", "\n", - "plt.tick_params(axis='x', labelbottom=True, top=True)\n", - "plt.tick_params(axis='y', labelbottom=True, right=True)\n", - "plt.tick_params(axis='both', which=\"both\", direction='in')\n", "\n", - "plt.ylabel(\"Median Execution Time (ms)\", fontsize=15)\n", - "plt.xlabel(\"Upper bondlength cutoff (Å)\", fontsize=15)\n", - "plt.legend(facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False)\n", - "plt.grid(axis=\"y\", linestyle=\"--\", alpha=0.7)\n", + "plt.tick_params(axis='x', labelbottom=True, top=True, labelsize=20)\n", + "plt.tick_params(axis='y', labelbottom=True, right=True, labelsize=20)\n", + "plt.tick_params(axis='both', which=\"both\", direction='in')\n", + "# set major ticks to every 0.2\n", + "plt.gca().yaxis.set_major_locator(MultipleLocator(0.2))\n", + "# add one minor tick for each major tick\n", + "plt.gca().yaxis.set_minor_locator(AutoMinorLocator(2))\n", + "# make major and minor ticks longer\n", + "plt.tick_params(which='both', width=1, length=6)\n", + "plt.tick_params(which='minor', width=1, length=3)\n", + "\n", + "plt.ylabel(\"Median execution time (ms)\", fontsize=25)\n", + "plt.xlabel(\"Upper bond length cutoff (Å)\", fontsize=25)\n", + "plt.legend(facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, loc='lower right', fontsize=16)\n", + "# plt.grid(axis=\"y\", linestyle=\"--\", alpha=0.7)\n", + "plt.gca().set_aspect(1.0/plt.gca().get_data_ratio(), adjustable='box')\n", "fig.show()\n", "\n", "plt.savefig('benchmark_cutoff_max_evaluator.pdf', bbox_inches='tight', pad_inches=0, facecolor=fig.get_facecolor(), edgecolor='none')" @@ -252,7 +270,7 @@ "source": [ "column = \"grid_spacing\"\n", "tmp_df = grouped_dfs['placement_methods']\n", - "filtered_df = tmp_df[tmp_df['method_probab.rand'] == 1.0]\n", + "filtered_df = tmp_df[tmp_df['method_ratio.rand'] == 1.0]\n", "times = {}\n", "for idx, row in filtered_df.iterrows():\n", "\tif row['brand'] not in times:\n", @@ -274,10 +292,18 @@ " time_data = sorted(time_data, key=lambda x: x[0])\n", " x, y = zip(*time_data)\n", " plt.plot(x, [val * 1000 for val in y], marker='o', linestyle='--', label=brand)\n", - " \n", - "plt.tick_params(axis='x', labelbottom=True, top=True)\n", - "plt.tick_params(axis='y', labelbottom=True, right=True)\n", + "\n", + "\n", + "plt.tick_params(axis='x', labelbottom=True, top=True, labelsize=20)\n", + "plt.tick_params(axis='y', labelbottom=True, right=True, labelsize=20)\n", "plt.tick_params(axis='both', which=\"both\", direction='in')\n", + "# set major ticks to every 0.2\n", + "plt.gca().yaxis.set_major_locator(MultipleLocator(0.2))\n", + "# add one minor tick for each major tick\n", + "plt.gca().yaxis.set_minor_locator(AutoMinorLocator(2))\n", + "# make major and minor ticks longer\n", + "plt.tick_params(which='both', width=1, length=6)\n", + "plt.tick_params(which='minor', width=1, length=3)\n", "\n", "ymin, ymax = ax.get_ylim()\n", "yrange = ymax - ymin\n", @@ -291,10 +317,11 @@ "ax.yaxis.set_major_locator(MultipleLocator(tick_spacing))\n", "ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", "\n", - "plt.ylabel(\"Median Execution Time (ms)\", fontsize=15)\n", - "plt.xlabel(\"Grid spacing (Å)\", fontsize=15)\n", - "plt.legend(facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False)\n", - "plt.grid(axis=\"y\", linestyle=\"--\", alpha=0.7)\n", + "plt.ylabel(\"Median execution time (ms)\", fontsize=25)\n", + "plt.xlabel(\"Grid spacing (Å)\", fontsize=25)\n", + "plt.legend(facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, loc='center right', fontsize=16)\n", + "# plt.grid(axis=\"y\", linestyle=\"--\", alpha=0.7)\n", + "plt.gca().set_aspect(1.0/plt.gca().get_data_ratio(), adjustable='box')\n", "fig.show()\n", "\n", "plt.savefig('benchmark_min_placement.pdf', bbox_inches='tight', pad_inches=0, facecolor=fig.get_facecolor(), edgecolor='none')" @@ -310,7 +337,7 @@ "tmp_df = grouped_dfs['placement_methods']\n", "\n", "for method in ['void', 'rand', 'walk', 'grow', 'min']:\n", - " filtered_df = tmp_df[tmp_df['method_probab.'+method] == 1.0]\n", + " filtered_df = tmp_df[tmp_df['method_ratio.'+method] == 1.0]\n", " times = {}\n", " for idx, row in filtered_df.iterrows():\n", " if row['brand'] not in times:\n", @@ -340,15 +367,30 @@ " ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", "\n", "\n", - " plt.tick_params(axis='x', labelbottom=True, top=True)\n", - " plt.tick_params(axis='y', labelbottom=True, right=True)\n", + " plt.tick_params(axis='x', labelbottom=True, top=True, labelsize=20)\n", + " plt.tick_params(axis='y', labelbottom=True, right=True, labelsize=20)\n", " plt.tick_params(axis='both', which=\"both\", direction='in')\n", - "\n", - " # plt.yscale('log')\n", - " plt.ylabel(\"Median Execution Time (ms)\", fontsize=15)\n", - " plt.xlabel(\"Grid spacing (Å)\", fontsize=15)\n", - " plt.legend(facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False)\n", - " plt.grid(axis=\"y\", linestyle=\"--\", alpha=0.7)\n", + " # make major and minor ticks longer\n", + " plt.tick_params(which='both', width=1, length=6)\n", + " plt.tick_params(which='minor', width=1, length=3)\n", + "\n", + " if method in ['void', 'min']:\n", + " # plt.yscale('log')\n", + " loc = 'upper right'\n", + " elif method in ['rand', 'walk', 'grow']:\n", + " loc = 'center right'\n", + " plt.ylim(0.3, 0.52)\n", + " plt.gca().yaxis.set_major_locator(MultipleLocator(0.05))\n", + " plt.gca().yaxis.set_minor_locator(AutoMinorLocator(2))\n", + " if method == 'void':\n", + " plt.ylim(0.1, 10)\n", + "\n", + "\n", + " plt.ylabel(\"Median execution time (ms)\", fontsize=25)\n", + " plt.xlabel(\"Grid spacing (Å)\", fontsize=25)\n", + " plt.legend(facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, loc='upper right', fontsize=16)\n", + " # plt.grid(axis=\"y\", linestyle=\"--\", alpha=0.7)\n", + " plt.gca().set_aspect(1.0/plt.gca().get_data_ratio(), adjustable='box')\n", " fig.show()\n", "\n", " plt.savefig('benchmark_placement_method_'+method+'.pdf', bbox_inches='tight', pad_inches=0, facecolor=fig.get_facecolor(), edgecolor='none')" @@ -426,14 +468,22 @@ " if column == \"avg_num_atoms\":\n", " ax.set_ylim([-1,32])\n", "\n", - " plt.tick_params(axis='x', labelbottom=True, top=True)\n", - " plt.tick_params(axis='y', labelbottom=True, right=True)\n", + " plt.tick_params(axis='x', labelbottom=True, top=True, labelsize=20)\n", + " plt.tick_params(axis='y', labelbottom=True, right=True, labelsize=20)\n", " plt.tick_params(axis='both', which=\"both\", direction='in')\n", - "\n", - " plt.ylabel(\"Median Execution Time (s)\", fontsize=15)\n", - " plt.xlabel(label, fontsize=15)\n", - " plt.legend(facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, loc='upper left')\n", - " plt.grid(axis=\"y\", linestyle=\"--\", alpha=0.7)\n", + " # set major ticks to every 0.2\n", + " plt.gca().yaxis.set_major_locator(MultipleLocator(10))\n", + " # add one minor tick for each major tick\n", + " plt.gca().yaxis.set_minor_locator(AutoMinorLocator(2))\n", + " # make major and minor ticks longer\n", + " plt.tick_params(which='both', width=1, length=6)\n", + " plt.tick_params(which='minor', width=1, length=3)\n", + "\n", + " plt.ylabel(\"Median execution time (s)\", fontsize=25)\n", + " plt.xlabel(label, fontsize=25)\n", + " plt.legend(facecolor='white', framealpha=1.0, edgecolor='black', fancybox=False, loc='upper left', fontsize=16)\n", + " # plt.grid(axis=\"y\", linestyle=\"--\", alpha=0.7)\n", + " plt.gca().set_aspect(1.0/plt.gca().get_data_ratio(), adjustable='box')\n", "\n", " plt.savefig(f'benchmark_distributions_{column}.pdf', bbox_inches='tight', pad_inches=0, facecolor=fig.get_facecolor(), edgecolor='none')\n", " print(row['kBT'], row['width_2-body'], row['width_3-body'], row['width_4-body'], row['avg_num_atoms'])" diff --git a/example/python_pkg/diamond/POSCAR_host b/example/python_pkg/diamond/POSCAR_host new file mode 100644 index 00000000..11242071 --- /dev/null +++ b/example/python_pkg/diamond/POSCAR_host @@ -0,0 +1,16 @@ +C8 + 1.000000000 + 3.560745109 0.000000000 0.000000000 + 0.000000000 3.560745109 0.000000000 + 0.000000000 0.000000000 7.121490218 +C +8 +Direct + 0.000000000 0.000000000 0.000000000 + 0.500000000 0.500000000 0.000000000 + 0.500000000 0.000000000 0.250000000 + 0.000000000 0.500000000 0.250000000 + 0.250000000 0.250000000 0.125000000 + 0.750000000 0.750000000 0.125000000 + 0.750000000 0.250000000 0.375000000 + 0.250000000 0.750000000 0.375000000 diff --git a/example/python_pkg/diamond/POSCAR_host_3x3 b/example/python_pkg/diamond/POSCAR_host_3x3 new file mode 100644 index 00000000..72b5deab --- /dev/null +++ b/example/python_pkg/diamond/POSCAR_host_3x3 @@ -0,0 +1,80 @@ +C8 + 1.000000000 + 14.242980436 0.000000000 0.000000000 + 0.000000000 14.242980436 0.000000000 + 0.000000000 0.000000000 7.121490218 +C +72 +Direct + 0.000000000 0.000000000 0.000000000 + 0.333333333 0.000000000 0.000000000 + 0.666666667 0.000000000 0.000000000 + 0.000000000 0.333333333 0.000000000 + 0.333333333 0.333333333 0.000000000 + 0.666666667 0.333333333 0.000000000 + 0.000000000 0.666666667 0.000000000 + 0.333333333 0.666666667 0.000000000 + 0.666666667 0.666666667 0.000000000 + 0.166666667 0.166666667 0.000000000 + 0.500000000 0.166666667 0.000000000 + 0.833333333 0.166666667 0.000000000 + 0.166666667 0.500000000 0.000000000 + 0.500000000 0.500000000 0.000000000 + 0.833333333 0.500000000 0.000000000 + 0.166666667 0.833333333 0.000000000 + 0.500000000 0.833333333 0.000000000 + 0.833333333 0.833333333 0.000000000 + 0.166666667 0.000000000 0.250000000 + 0.500000000 0.000000000 0.250000000 + 0.833333333 0.000000000 0.250000000 + 0.166666667 0.333333333 0.250000000 + 0.500000000 0.333333333 0.250000000 + 0.833333333 0.333333333 0.250000000 + 0.166666667 0.666666667 0.250000000 + 0.500000000 0.666666667 0.250000000 + 0.833333333 0.666666667 0.250000000 + 0.000000000 0.166666667 0.250000000 + 0.333333333 0.166666667 0.250000000 + 0.666666667 0.166666667 0.250000000 + 0.000000000 0.500000000 0.250000000 + 0.333333333 0.500000000 0.250000000 + 0.666666667 0.500000000 0.250000000 + 0.000000000 0.833333333 0.250000000 + 0.333333333 0.833333333 0.250000000 + 0.666666667 0.833333333 0.250000000 + 0.083333333 0.083333333 0.125000000 + 0.416666667 0.083333333 0.125000000 + 0.750000000 0.083333333 0.125000000 + 0.083333333 0.416666667 0.125000000 + 0.416666667 0.416666667 0.125000000 + 0.750000000 0.416666667 0.125000000 + 0.083333333 0.750000000 0.125000000 + 0.416666667 0.750000000 0.125000000 + 0.750000000 0.750000000 0.125000000 + 0.250000000 0.250000000 0.125000000 + 0.583333333 0.250000000 0.125000000 + 0.916666667 0.250000000 0.125000000 + 0.250000000 0.583333333 0.125000000 + 0.583333333 0.583333333 0.125000000 + 0.916666667 0.583333333 0.125000000 + 0.250000000 0.916666667 0.125000000 + 0.583333333 0.916666667 0.125000000 + 0.916666667 0.916666667 0.125000000 + 0.250000000 0.083333333 0.375000000 + 0.583333333 0.083333333 0.375000000 + 0.916666667 0.083333333 0.375000000 + 0.250000000 0.416666667 0.375000000 + 0.583333333 0.416666667 0.375000000 + 0.916666667 0.416666667 0.375000000 + 0.250000000 0.750000000 0.375000000 + 0.583333333 0.750000000 0.375000000 + 0.916666667 0.750000000 0.375000000 + 0.083333333 0.250000000 0.375000000 + 0.416666667 0.250000000 0.375000000 + 0.750000000 0.250000000 0.375000000 + 0.083333333 0.583333333 0.375000000 + 0.416666667 0.583333333 0.375000000 + 0.750000000 0.583333333 0.375000000 + 0.083333333 0.916666667 0.375000000 + 0.416666667 0.916666667 0.375000000 + 0.750000000 0.916666667 0.375000000 diff --git a/example/python_pkg/diamond/run.py b/example/python_pkg/diamond/run.py index 3cc6f3e0..2f19e492 100644 --- a/example/python_pkg/diamond/run.py +++ b/example/python_pkg/diamond/run.py @@ -155,7 +155,7 @@ print(f"Iteration {iter}") print("Generating...") # this is the main function to generate structures - generator.generate(num_structures=1, stoichiometry=stoich_dict, seed=0+iter, verbose=1, method_probab={"void":0.0001, "walk":0.0, "min":1.0}) + generator.generate(num_structures=1, stoichiometry=stoich_dict, seed=0+iter, verbose=1, method_ratio={"void":0.0001, "walk":0.0, "min":1.0}) print("Generated") print("Getting structures") diff --git a/example/python_pkg/graphite/POSCAR_host_graphene b/example/python_pkg/graphite/POSCAR_host_graphene new file mode 100644 index 00000000..f5d05414 --- /dev/null +++ b/example/python_pkg/graphite/POSCAR_host_graphene @@ -0,0 +1,26 @@ +C4 + 1.000000000 + 3.700936892 -6.410210733 0.000000000 + 3.700936892 6.410210733 0.000000000 + 0.000000000 0.000000000 7.803073000 +C +18 +Direct + 0.000000000 0.000000000 0.250000000 + 0.333333333 0.000000000 0.250000000 + 0.666666667 0.000000000 0.250000000 + 0.000000000 0.333333333 0.250000000 + 0.333333333 0.333333333 0.250000000 + 0.666666667 0.333333333 0.250000000 + 0.000000000 0.666666667 0.250000000 + 0.333333333 0.666666667 0.250000000 + 0.666666667 0.666666667 0.250000000 + 0.111111111 0.222222222 0.250000000 + 0.444444444 0.222222222 0.250000000 + 0.777777778 0.222222222 0.250000000 + 0.111111111 0.555555556 0.250000000 + 0.444444444 0.555555556 0.250000000 + 0.777777778 0.555555556 0.250000000 + 0.111111111 0.888888889 0.250000000 + 0.444444444 0.888888889 0.250000000 + 0.777777778 0.888888889 0.250000000 \ No newline at end of file diff --git a/example/python_pkg/graphite/POSCAR_host_graphite_vacancy b/example/python_pkg/graphite/POSCAR_host_graphite_vacancy new file mode 100644 index 00000000..4fb28784 --- /dev/null +++ b/example/python_pkg/graphite/POSCAR_host_graphite_vacancy @@ -0,0 +1,44 @@ +C4 + 1.000000000 + 3.700936892 -6.410210733 0.000000000 + 3.700936892 6.410210733 0.000000000 + 0.000000000 0.000000000 7.803073000 +C +35 +Direct + 0.000000000 0.000000000 0.250000000 + 0.333333333 0.000000000 0.250000000 + 0.666666667 0.000000000 0.250000000 + 0.000000000 0.333333333 0.250000000 + 0.333333333 0.333333333 0.250000000 + 0.666666667 0.333333333 0.250000000 + 0.000000000 0.666666667 0.250000000 + 0.333333333 0.666666667 0.250000000 + 0.666666667 0.666666667 0.250000000 + 0.000000000 0.000000000 0.750000000 + 0.333333333 0.000000000 0.750000000 + 0.666666667 0.000000000 0.750000000 + 0.000000000 0.333333333 0.750000000 + 0.333333333 0.333333333 0.750000000 + 0.666666667 0.333333333 0.750000000 + 0.000000000 0.666666667 0.750000000 + 0.333333333 0.666666667 0.750000000 + 0.666666667 0.666666667 0.750000000 + 0.111111111 0.222222222 0.250000000 + 0.444444444 0.222222222 0.250000000 + 0.777777778 0.222222222 0.250000000 + 0.111111111 0.555555556 0.250000000 + 0.444444444 0.555555556 0.250000000 + 0.777777778 0.555555556 0.250000000 + 0.111111111 0.888888889 0.250000000 + 0.444444444 0.888888889 0.250000000 + 0.777777778 0.888888889 0.250000000 + 0.222222222 0.111111111 0.750000000 + 0.555555556 0.111111111 0.750000000 + 0.888888889 0.111111111 0.750000000 + 0.222222222 0.444444444 0.750000000 + 0.555555556 0.444444444 0.750000000 + 0.888888889 0.444444444 0.750000000 + 0.222222222 0.777777778 0.750000000 + 0.555555556 0.777777778 0.750000000 + diff --git a/example/python_pkg/graphite/POSCAR_host_missing_layer b/example/python_pkg/graphite/POSCAR_host_missing_layer new file mode 100644 index 00000000..024e65f9 --- /dev/null +++ b/example/python_pkg/graphite/POSCAR_host_missing_layer @@ -0,0 +1,15 @@ +C + 1.000000000 + 1.233645631 -2.136736911 0.000000000 + 1.233645631 2.136736911 0.000000000 + 0.000000000 0.000000000 15.606146000 +C +6 +Direct + 0.000000000 0.000000000 0.125000000 + 0.000000000 0.000000000 0.375000000 + 0.000000000 0.000000000 0.875000000 + 0.333333333 0.666666667 0.125000000 + 0.666666667 0.333333333 0.375000000 + 0.666666667 0.333333333 0.875000000 + diff --git a/example/python_pkg/graphite/run.py b/example/python_pkg/graphite/run.py index d52fbe00..effef2c0 100644 --- a/example/python_pkg/graphite/run.py +++ b/example/python_pkg/graphite/run.py @@ -158,7 +158,7 @@ print(f"Iteration {iter}") print("Generating...") # this is the main function to generate structures - generator.generate(num_structures=1, stoichiometry=stoich_dict, seed=0+iter, verbose=1, method_probab={"void":0.0001, "walk":0.0, "min":1.0}) + generator.generate(num_structures=1, stoichiometry=stoich_dict, seed=0+iter, verbose=1, method_ratio={"void":0.0001, "walk":0.0, "min":1.0}) print("Generated") print("Getting structures") diff --git a/example/python_pkg/perovskites/run.py b/example/python_pkg/perovskites/run.py index e464a73d..517e5613 100644 --- a/example/python_pkg/perovskites/run.py +++ b/example/python_pkg/perovskites/run.py @@ -84,7 +84,7 @@ print(f"Iteration {iter}") print("Generating...") # this is the main function to generate structures - generator.generate(num_structures=1, stoichiometry=stoich_dict, seed=0+iter, verbose=0, method_probab={"void":0.001, "walk":0.0, "min":1.0}) + generator.generate(num_structures=1, stoichiometry=stoich_dict, seed=0+iter, verbose=0, method_ratio={"void":0.001, "walk":0.0, "min":1.0}) print("Generated") print("Getting structures") diff --git a/fpm.toml b/fpm.toml index 22d1b082..8160bee7 100644 --- a/fpm.toml +++ b/fpm.toml @@ -1,5 +1,5 @@ name = "raffle" -version = "0.5.1" +version = "1.0.0" author = "Ned Thaddeus Taylor" maintainer = "n.t.taylor@exeter.ac.uk" description = "A Fortran library and executable for structure prediction at material interfaces" diff --git a/src/fortran/lib/mod_dist_calcs.f90 b/src/fortran/lib/mod_dist_calcs.f90 index c92621f9..9bade3df 100644 --- a/src/fortran/lib/mod_dist_calcs.f90 +++ b/src/fortran/lib/mod_dist_calcs.f90 @@ -84,8 +84,8 @@ function get_min_dist(basis,loc,lignore_close,axis,labove,lreal,tol, & do js = 1, basis%nspec atmloop: do ja = 1, basis%spec(js)%num if(present(ignore_list))then - do i = 1, size(ignore_list,1), 1 - if(all(ignore_list(i,:).eq.[js,ja])) cycle atmloop + do i = 1, size(ignore_list,2), 1 + if(all(ignore_list(:,i).eq.[js,ja])) cycle atmloop end do end if vdtmp1 = basis%spec(js)%atom(ja,:3) - loc @@ -181,8 +181,8 @@ pure function get_min_dist_between_point_and_species( & dist = huge(0._real32) atom_loop: do ia = 1,basis%spec(species)%num if(present(ignore_list))then - do i = 1, size(ignore_list,1), 1 - if(all(ignore_list(i,:).eq.[species,ia])) cycle atom_loop + do i = 1, size(ignore_list,2), 1 + if(all(ignore_list(:,i).eq.[species,ia])) cycle atom_loop end do end if vec = loc - basis%spec(species)%atom(ia,:3) diff --git a/src/fortran/lib/mod_distribs.f90 b/src/fortran/lib/mod_distribs.f90 index ed7732c4..ca21f1a9 100644 --- a/src/fortran/lib/mod_distribs.f90 +++ b/src/fortran/lib/mod_distribs.f90 @@ -671,7 +671,7 @@ function get_distrib(value_list, nbins, eta, width, cutoff_min, & loop_limits(:,1) = & [ min(nbins, bin), min(nbins, bin + max_num_steps), 1 ] loop_limits(:,2) = & - [ max(1, bin - 1), max(1, bin - max_num_steps), -1 ] + [ max(0, bin - 1), max(1, bin - max_num_steps), -1 ] !------------------------------------------------------------------------ diff --git a/src/fortran/lib/mod_distribs_container.f90 b/src/fortran/lib/mod_distribs_container.f90 index e6b26119..4224751c 100644 --- a/src/fortran/lib/mod_distribs_container.f90 +++ b/src/fortran/lib/mod_distribs_container.f90 @@ -2209,6 +2209,8 @@ subroutine evolve(this, system) this%gdf%df_3body(:,i) * exp( & this%best_energy_per_species(i) / this%kBT & ) / exp( best_energy_per_species_old(i) / this%kBT ) + end do + do i = 1, size(this%gdf%df_4body,2) this%gdf%df_4body(:,i) = & this%gdf%df_4body(:,i) * exp( & this%best_energy_per_species(i) / this%kBT & diff --git a/src/fortran/lib/mod_evaluator.f90 b/src/fortran/lib/mod_evaluator.f90 index 6956b2e0..cb786b5c 100644 --- a/src/fortran/lib/mod_evaluator.f90 +++ b/src/fortran/lib/mod_evaluator.f90 @@ -107,8 +107,8 @@ function evaluate_point( distribs_container, & atom_loop: do ia = 1, basis%spec(is)%num ! Check if the atom is in the ignore list ! If it is, skip the atom. - do i = 1, size(atom_ignore_list,dim=1), 1 - if(all(atom_ignore_list(i,:).eq.[is,ia])) cycle atom_loop + do i = 1, size(atom_ignore_list,dim=2), 1 + if(all(atom_ignore_list(:,i).eq.[is,ia])) cycle atom_loop end do associate( position_store => [ basis%spec(is)%atom(ia,1:3) ] ) bondlength = modu( matmul(position - position_store, basis%lat) ) diff --git a/src/fortran/lib/mod_generator.f90 b/src/fortran/lib/mod_generator.f90 index 3c08e080..35f59968 100644 --- a/src/fortran/lib/mod_generator.f90 +++ b/src/fortran/lib/mod_generator.f90 @@ -70,8 +70,8 @@ module raffle__generator walk_step_size_coarse = 1._real32, & walk_step_size_fine = 0.1_real32 !! Step size for the walk and grow methods. - real(real32), dimension(5) :: method_probab - !! Probability of each placement method. + real(real32), dimension(5) :: method_ratio + !! Ratio of each placement method. type(basis_type), dimension(:), allocatable :: structures !! Generated structures. contains @@ -297,15 +297,15 @@ end subroutine reset_bounds !############################################################################### subroutine generate(this, num_structures, & - stoichiometry, method_probab, seed, settings_out_file, & - verbose & + stoichiometry, method_ratio, seed, settings_out_file, & + verbose, exit_code & ) !! Generate random structures. !! !! This procedure generates random structures from the contained host !! structure and the stoichiometry argument. The number of structures to !! generate is specified by the num_structures argument. - !! The ratio of placement methods to be sampled is defined by method_probab. + !! The ratio of placement methods to be sampled is defined by method_ratio. implicit none ! Arguments @@ -315,24 +315,28 @@ subroutine generate(this, num_structures, & !! Number of structures to generate. type(stoichiometry_type), dimension(:), intent(in) :: stoichiometry !! Stoichiometry of the structures to generate. - real(real32), dimension(5), intent(in), optional :: method_probab - !! Probability of each placement method. + real(real32), dimension(5), intent(in), optional :: method_ratio + !! Ratio of each placement method. integer, intent(in), optional :: seed !! Seed for the random number generator. character(*), intent(in), optional :: settings_out_file !! File to print the settings to. integer, intent(in), optional :: verbose !! Verbosity level. + integer, intent(out), optional :: exit_code + !! Exit code. ! Local variables integer :: i, j, k, istructure, num_structures_old, num_structures_new !! Loop counters. + integer :: exit_code_ + !! Exit code. integer :: num_seed !! Number of seeds for the random number generator. integer :: num_insert_atoms, num_insert_species !! Number of atoms and species to insert (from stoichiometry). - real(real32) :: total_probab - !! Total probability of the placement methods. + real(real32) :: ratio_norm + !! Normalisation factor for the method ratios. logical :: success !! Boolean comparison of element symbols. integer :: verbose_ @@ -340,9 +344,9 @@ subroutine generate(this, num_structures, & type(basis_type) :: basis_template !! Basis of the structure to generate (i.e. allocated species and atoms). real(real32), dimension(5) :: & - method_probab_ = & + method_rand_limit = & [1.0_real32, 0.1_real32, 0.5_real32, 0.5_real32, 1.0_real32] - !! Default probability of each placement method. + !! Default ratio of each placement method. integer, dimension(:), allocatable :: seed_arr !! Array of seeds for the random number generator. @@ -356,33 +360,34 @@ subroutine generate(this, num_structures, & !--------------------------------------------------------------------------- ! Set the verbosity level !--------------------------------------------------------------------------- + exit_code_ = 0 verbose_ = 0 if(present(verbose)) verbose_ = verbose if(verbose_ .eq. 0) suppress_warnings = .true. !--------------------------------------------------------------------------- - ! set the placement method probabilities + ! Set the placement method selection limit numbers !--------------------------------------------------------------------------- - if(verbose_.gt.0) write(*,*) "Setting method probabilities" - if(present(method_probab))then - method_probab_ = method_probab + if(verbose_.gt.0) write(*,*) "Setting method ratios" + if(present(method_ratio))then + method_rand_limit = method_ratio else - method_probab_ = this%method_probab + method_rand_limit = this%method_ratio end if - this%method_probab = method_probab_ - total_probab = real(sum(method_probab_), real32) - method_probab_ = method_probab_ / total_probab + this%method_ratio = method_rand_limit + ratio_norm = real(sum(method_rand_limit), real32) + method_rand_limit = method_rand_limit / ratio_norm do i = 2, 5, 1 - method_probab_(i) = method_probab_(i) + method_probab_(i-1) + method_rand_limit(i) = method_rand_limit(i) + method_rand_limit(i-1) end do if(verbose_.gt.0) write(*,*) & - "Method probabilities (void, rand, walk, grow, min): ", & - method_probab_ + "Method random limits (void, rand, walk, grow, min): ", & + method_rand_limit !--------------------------------------------------------------------------- - ! print the settings to a file + ! Print the settings to a file !--------------------------------------------------------------------------- if(present(settings_out_file))then if(trim(settings_out_file).ne."")then @@ -391,7 +396,7 @@ subroutine generate(this, num_structures, & end if !--------------------------------------------------------------------------- - ! set the random seed + ! Set the random seed !--------------------------------------------------------------------------- if(present(seed))then call random_seed(size=num_seed) @@ -467,7 +472,7 @@ subroutine generate(this, num_structures, & ! ... basis_template !--------------------------------------------------------------------------- if(verbose_.gt.0) write(*,*) "Generating placement list" - allocate(placement_list(num_insert_atoms,2)) + allocate(placement_list(2, num_insert_atoms)) k = 0 spec_loop1: do i = 1, basis_template%nspec success = .false. @@ -481,15 +486,15 @@ subroutine generate(this, num_structures, & if(i.gt.this%host%nspec)then do j = 1, basis_template%spec(i)%num k = k + 1 - placement_list(k,1) = i - placement_list(k,2) = j + placement_list(1,k) = i + placement_list(2,k) = j end do else do j = 1, basis_template%spec(i)%num if(j.le.this%host%spec(i)%num) cycle k = k + 1 - placement_list(k,1) = i - placement_list(k,2) = j + placement_list(1,k) = i + placement_list(2,k) = j end do end if end do spec_loop1 @@ -508,17 +513,25 @@ subroutine generate(this, num_structures, & this%generate_structure( & basis_template, & placement_list, & - method_probab_, & - verbose_ & + method_rand_limit, & + verbose_, & + exit_code_ & ) & ) this%num_structures = istructure end do structure_loop - if(verbose_ .gt. 0) write(*,*) "Finished generating structures" + if(verbose_ .gt. 0 .and. exit_code_ .eq. 0) & + write(*,*) "Finished generating structures" if(verbose_ .eq. 0) suppress_warnings = .true. + if(present(exit_code))then + exit_code = exit_code_ + elseif(exit_code_ .ne. 0)then + call stop_program("Error generating structures", exit_code_) + end if + end subroutine generate !############################################################################### @@ -527,7 +540,8 @@ end subroutine generate function generate_structure( & this, & basis_initial, & - placement_list, method_probab, verbose & + placement_list, method_rand_limit, verbose, & + exit_code & ) result(basis) !! Generate a single random structure. !! @@ -545,12 +559,14 @@ function generate_structure( & !! Initial basis to build upon. integer, dimension(:,:), intent(in) :: placement_list !! List of possible placements. - real(real32), dimension(5) :: method_probab - !! Probability of each placement method. + real(real32), dimension(5) :: method_rand_limit + !! Upper limit of the random number to call each placement method. type(extended_basis_type) :: basis !! Generated basis. integer, intent(in) :: verbose !! Verbosity level. + integer, intent(inout) :: exit_code + !! Exit code. ! Local variables integer :: iplaced, void_ticker @@ -561,14 +577,16 @@ function generate_structure( & !! Random number. logical :: viable !! Boolean for viable placement. + logical :: placement_aborted + !! Boolean for aborted placement. integer, dimension(size(placement_list,1),size(placement_list,2)) :: & placement_list_shuffled !! Shuffled placement list. real(real32), dimension(3) :: point !! Coordinate of the atom to place. - real(real32), dimension(5) :: method_probab_ - !! Temporary probability of each placement method. - !! This is used to update the probability of the global minimum method if + real(real32), dimension(5) :: method_rand_limit_ + !! Temporary random limit of each placement method. + !! This is used to update the contribution of the global minimum method if !! no viable gridpoints are found. integer, dimension(:), allocatable :: species_index_list !! List of species indices to add. @@ -593,21 +611,21 @@ function generate_structure( & ! shuffle the placement list !--------------------------------------------------------------------------- placement_list_shuffled = placement_list - call shuffle(placement_list_shuffled,1) + call shuffle(placement_list_shuffled,2) !--------------------------------------------------------------------------- ! generate species index list to add !--------------------------------------------------------------------------- - species_index_list = placement_list_shuffled(:,1) + species_index_list = placement_list_shuffled(1,:) call set(species_index_list) !--------------------------------------------------------------------------- ! check for viable gridpoints !--------------------------------------------------------------------------- - method_probab_ = method_probab - if(abs( method_probab_(5) - method_probab_(4) ) .gt. 1.E-3)then + method_rand_limit_ = method_rand_limit + if(abs( method_rand_limit(5) - method_rand_limit(4) ) .gt. 1.E-3)then gridpoint_viability = get_gridpoints_and_viability( & this%distributions, & this%grid, & @@ -622,11 +640,12 @@ function generate_structure( & !--------------------------------------------------------------------------- - ! place the atoms according to the method probabilities + ! place the atoms according to the method ratios !--------------------------------------------------------------------------- iplaced = 0 void_ticker = 0 viable = .false. + placement_aborted = .false. placement_loop: do while (iplaced.lt.num_insert_atoms) !------------------------------------------------------------------------ ! check if there are any viable gridpoints remaining @@ -638,78 +657,73 @@ function generate_structure( & this%distributions, & basis, & species_index_list, & - [ placement_list_shuffled(iplaced,:) ], & + [ placement_list_shuffled(:,iplaced) ], & [ this%distributions%bond_info(:)%radius_covalent ], & - placement_list_shuffled(iplaced+1:,:) & + placement_list_shuffled(:,iplaced+1:) & ) if(.not.allocated(gridpoint_viability))then - if(abs(method_probab_(4)).lt.1.E-6)then - call stop_program( & - "No viable gridpoints" // & - achar(13) // achar(10) // & - "No placement methods available" & - ) - return - else if( & - abs( method_probab_(5) - method_probab_(4) ) .gt. 1.E-6 & + if(abs(method_rand_limit(4)).lt.1.E-6)then + placement_aborted = .true. + exit placement_loop + elseif( & + abs( & + method_rand_limit(5) - method_rand_limit(4) & + ) .gt. 1.E-6 & ) then write(warn_msg, '("No more viable gridpoints")') warn_msg = trim(warn_msg) // & achar(13) // achar(10) // & "Suppressing global minimum method" call print_warning(warn_msg) - method_probab_ = method_probab_ / method_probab_(4) - method_probab_(5) = method_probab_(4) + method_rand_limit = method_rand_limit / method_rand_limit(4) + method_rand_limit(5) = method_rand_limit(4) end if end if end if viable = .false. !------------------------------------------------------------------------ - ! choose a placement method - ! call a random number and query the method probabilities + ! Choose a placement method + ! call a random number and query the method ratios !------------------------------------------------------------------------ call random_number(rtmp1) - if(rtmp1.le.method_probab_(1)) then + if(rtmp1.le.method_rand_limit(1)) then if(verbose.gt.0) write(*,*) "Add Atom Void" - point = place_method_void( this%grid, & - this%grid_offset, & - this%bounds, & + point = place_method_void( & + gridpoint_viability, & basis, & - placement_list_shuffled(iplaced+1:,:), viable & + placement_list_shuffled(:,iplaced+1:), viable & ) - else if(rtmp1.le.method_probab_(2)) then + elseif(rtmp1.le.method_rand_limit(2)) then if(verbose.gt.0) write(*,*) "Add Atom Random" point = place_method_rand( & this%distributions, & this%bounds, & basis, & - placement_list_shuffled(iplaced+1:,:), & + placement_list_shuffled(:,iplaced+1:), & [ this%distributions%bond_info(:)%radius_covalent ], & this%max_attempts, & viable & ) - if(.not. viable) cycle placement_loop - else if(rtmp1.le.method_probab_(3)) then + elseif(rtmp1.le.method_rand_limit(3)) then if(verbose.gt.0) write(*,*) "Add Atom Walk" point = place_method_walk( & this%distributions, & this%bounds, & basis, & - placement_list_shuffled(iplaced+1:,:), & + placement_list_shuffled(:,iplaced+1:), & [ this%distributions%bond_info(:)%radius_covalent ], & this%max_attempts, & this%walk_step_size_coarse, this%walk_step_size_fine, & viable & ) - if(.not. viable) void_ticker = void_ticker + 1 - else if(rtmp1.le.method_probab_(4)) then + elseif(rtmp1.le.method_rand_limit(4)) then if(iplaced.eq.0)then if(verbose.gt.0) write(*,*) "Add Atom Random (growth seed)" point = place_method_rand( & this%distributions, & this%bounds, & basis, & - placement_list_shuffled(iplaced+1:,:), & + placement_list_shuffled(:,iplaced+1:), & [ this%distributions%bond_info(:)%radius_covalent ], & this%max_attempts, & viable & @@ -718,38 +732,29 @@ function generate_structure( & if(verbose.gt.0) write(*,*) "Add Atom Growth" point = place_method_growth( & this%distributions, & - basis%spec(placement_list_shuffled(iplaced,1))%atom( & - placement_list_shuffled(iplaced,2),:3 & + basis%spec(placement_list_shuffled(1,iplaced))%atom( & + placement_list_shuffled(2,iplaced),:3 & ), & - placement_list_shuffled(iplaced,1), & + placement_list_shuffled(1,iplaced), & this%bounds, & basis, & - placement_list_shuffled(iplaced+1:,:), & + placement_list_shuffled(:,iplaced+1:), & [ this%distributions%bond_info(:)%radius_covalent ], & this%max_attempts, & this%walk_step_size_coarse, this%walk_step_size_fine, & viable & ) end if - if(.not. viable) void_ticker = void_ticker + 1 - else if(rtmp1.le.method_probab_(5)) then + elseif(rtmp1.le.method_rand_limit(5)) then if(verbose.gt.0) write(*,*) "Add Atom Minimum" point = place_method_min( gridpoint_viability, & - placement_list_shuffled(iplaced+1,1), & + placement_list_shuffled(1,iplaced+1), & species_index_list, & viable & ) - if(.not. viable .and. abs(method_probab_(4)).lt.1.E-6)then - write(stop_msg,*) & - "No viable gridpoints" // & - achar(13) // achar(10) // & - "Min method is the only method, but cannot place another & - &atom" // & - achar(13) // achar(10) // & - "Species to place now: ", & - basis%spec(placement_list_shuffled(iplaced+1,1))%name - call stop_program(stop_msg) - return + if(.not. viable .and. abs(method_rand_limit(4)).lt.1.E-6)then + placement_aborted = .true. + exit placement_loop elseif(.not. viable)then deallocate(gridpoint_viability) write(warn_msg, '("No more viable gridpoints")') @@ -757,33 +762,38 @@ function generate_structure( & achar(13) // achar(10) // & "Suppressing global minimum method" call print_warning(warn_msg) - method_probab_ = method_probab_ / method_probab_(4) - method_probab_(5) = method_probab_(4) + method_rand_limit = method_rand_limit / method_rand_limit(4) + method_rand_limit(5) = method_rand_limit(4) end if end if !------------------------------------------------------------------------ ! check if the placement method returned a viable point ! if not, cycle the loop !------------------------------------------------------------------------ - if(.not. viable) then - if(void_ticker.gt.10) & - point = place_method_void( & - this%grid, this%grid_offset, this%bounds, basis, & - placement_list_shuffled(iplaced+1:,:), viable & - ) - void_ticker = 0 + if(.not. viable)then + void_ticker = void_ticker + 1 + if(void_ticker.gt.10.and..not.allocated(gridpoint_viability))then + placement_aborted = .true. + exit placement_loop + elseif(void_ticker.gt.10)then + point = place_method_void( & + gridpoint_viability, basis, & + placement_list_shuffled(:,iplaced+1:), viable & + ) + void_ticker = 0 + end if if(.not.viable) cycle placement_loop end if !------------------------------------------------------------------------ ! place the atom and update the image atoms in the basis !------------------------------------------------------------------------ iplaced = iplaced + 1 - basis%spec(placement_list_shuffled(iplaced,1))%atom( & - placement_list_shuffled(iplaced,2),:3) = point(:3) + basis%spec(placement_list_shuffled(1,iplaced))%atom( & + placement_list_shuffled(2,iplaced),:3) = point(:3) call basis%update_images( & max_bondlength = this%distributions%cutoff_max(1), & - is = placement_list_shuffled(iplaced,1), & - ia = placement_list_shuffled(iplaced,2) & + is = placement_list_shuffled(1,iplaced), & + ia = placement_list_shuffled(2,iplaced) & ) if(verbose.gt.0)then write(*,'(A)',ADVANCE='NO') achar(13) @@ -791,6 +801,16 @@ function generate_structure( & end if end do placement_loop + + if(placement_aborted)then + call stop_program( & + "Placement routine aborted, not all atoms placed", & + block_stop = .true. & + ) + exit_code = 1 + call basis%remove_atoms(placement_list_shuffled(:,iplaced+1:)) + end if + if(allocated(gridpoint_viability)) deallocate(gridpoint_viability) end function generate_structure @@ -920,7 +940,7 @@ function evaluate(this, basis) result(viability) ! Local variables integer :: is, ia, species !! Loop indices. - integer, dimension(1,2) :: atom_ignore + integer, dimension(2,1) :: atom_ignore !! Atom to ignore. type(extended_basis_type) :: basis_extd !! Extended basis for the structure to evaluate. @@ -947,10 +967,10 @@ function evaluate(this, basis) result(viability) return end if do ia = 1, basis%spec(is)%num - atom_ignore(1,:) = [is,ia] + atom_ignore(:,1) = [is,ia] viability = viability + & evaluate_point( this%distributions, & - basis%spec(is)%atom(ia,1:3), & + [ basis%spec(is)%atom(ia,1:3) ], & species, basis_extd, & atom_ignore, & [ this%distributions%bond_info(:)%radius_covalent ] & @@ -1000,11 +1020,11 @@ subroutine print_generator_settings(this, file) write(unit,'("MAX_ATTEMPTS =",I0)') this%max_attempts write(unit,'("WALK_STEP_SIZE_COARSE = ",F15.9)') this%walk_step_size_coarse write(unit,'("WALK_STEP_SIZE_FINE = ",F15.9)') this%walk_step_size_fine - write(unit,'("METHOD_VOID = ",F15.9)') this%method_probab(1) - write(unit,'("METHOD_RANDOM = ",F15.9)') this%method_probab(2) - write(unit,'("METHOD_WALK = ",F15.9)') this%method_probab(3) - write(unit,'("METHOD_GROW = ",F15.9)') this%method_probab(4) - write(unit,'("METHOD_MIN = ",F15.9)') this%method_probab(5) + write(unit,'("METHOD_VOID = ",F15.9)') this%method_ratio(1) + write(unit,'("METHOD_RANDOM = ",F15.9)') this%method_ratio(2) + write(unit,'("METHOD_WALK = ",F15.9)') this%method_ratio(3) + write(unit,'("METHOD_GROW = ",F15.9)') this%method_ratio(4) + write(unit,'("METHOD_MIN = ",F15.9)') this%method_ratio(5) write(unit,'("# DISTRIBUTION SETTINGS")') write(unit,'("KBT = ",F5.2)') this%distributions%kbt @@ -1112,15 +1132,15 @@ subroutine read_generator_settings(this, file) case("WALK_STEP_SIZE_FINE") call assign_val(line, this%walk_step_size_fine, itmp1) case("METHOD_VOID") - call assign_val(line, this%method_probab(1), itmp1) + call assign_val(line, this%method_ratio(1), itmp1) case("METHOD_RANDOM") - call assign_val(line, this%method_probab(2), itmp1) + call assign_val(line, this%method_ratio(2), itmp1) case("METHOD_WALK") - call assign_val(line, this%method_probab(3), itmp1) + call assign_val(line, this%method_ratio(3), itmp1) case("METHOD_GROW") - call assign_val(line, this%method_probab(4), itmp1) + call assign_val(line, this%method_ratio(4), itmp1) case("METHOD_MIN") - call assign_val(line, this%method_probab(5), itmp1) + call assign_val(line, this%method_ratio(5), itmp1) case("KBT") call assign_val(line, this%distributions%kbt, itmp1) case("SIGMA") diff --git a/src/fortran/lib/mod_geom_extd.f90 b/src/fortran/lib/mod_geom_extd.f90 index 3c27f13d..3b1d4dd0 100644 --- a/src/fortran/lib/mod_geom_extd.f90 +++ b/src/fortran/lib/mod_geom_extd.f90 @@ -92,8 +92,8 @@ subroutine create_images(this, max_bondlength, atom_ignore_list) image_species(is)%radius = this%spec(is)%radius image_species(is)%name = this%spec(is)%name atom_loop: do ia = 1, this%spec(is)%num - do i = 1, size(atom_ignore_list_,1), 1 - if(all(atom_ignore_list_(i,:).eq.[is,ia])) cycle atom_loop + do i = 1, size(atom_ignore_list_,2), 1 + if(all(atom_ignore_list_(:,i).eq.[is,ia])) cycle atom_loop end do do i=-amax,amax+1,1 vtmp1(1) = this%spec(is)%atom(ia,1) + real(i, real32) diff --git a/src/fortran/lib/mod_geom_rw.f90 b/src/fortran/lib/mod_geom_rw.f90 index 720630d9..f4eecf3f 100644 --- a/src/fortran/lib/mod_geom_rw.f90 +++ b/src/fortran/lib/mod_geom_rw.f90 @@ -71,6 +71,10 @@ module raffle__geom_rw !! Procedure to copy the basis. procedure, pass(this) :: get_lattice_constants !! Procedure to get the lattice constants of the basis. + procedure, pass(this) :: remove_atom + !! Procedure to remove an atom from the basis. + procedure, pass(this) :: remove_atoms + !! Procedure to remove atoms from the basis. end type basis_type @@ -1406,6 +1410,137 @@ end subroutine copy !############################################################################### +!############################################################################### + subroutine remove_atom(this, ispec, iatom) + !! Remove an atom from the basis. + implicit none + + ! Arguments + class(basis_type), intent(inout) :: this + !! Parent. The basis. + integer, intent(in) :: ispec, iatom + !! The species and atom to remove. + + ! Local variables + integer :: i + !! Loop index. + real(real32), dimension(:,:), allocatable :: atom + !! Temporary array to store the atomic positions. + + + !--------------------------------------------------------------------------- + ! remove atom from basis + !--------------------------------------------------------------------------- + do i = 1, this%nspec + if(i.eq.ispec)then + if(iatom.gt.this%spec(i)%num)then + call stop_program("Atom to remove does not exist") + return + end if + allocate(atom(this%spec(i)%num-1,size(this%spec(i)%atom,2))) + atom(1:iatom-1:1,:) = this%spec(i)%atom(1:iatom-1:1,:) + atom(iatom:this%spec(i)%num-1:1,:) = & + this%spec(i)%atom(iatom+1:this%spec(i)%num:1,:) + this%spec(i)%atom = atom + deallocate(atom) + this%spec(i)%num = this%spec(i)%num - 1 + this%natom = this%natom - 1 + if(this%spec(i)%num.eq.0)then + deallocate(this%spec(i)%atom) + if(this%nspec.eq.0)then + deallocate(this%spec) + this%lcart = .true. + this%sysname = "" + this%energy = 0._real32 + this%lat = 0._real32 + this%pbc = .true. + end if + end if + end if + end do + + end subroutine remove_atom +!############################################################################### + + +!############################################################################### + subroutine remove_atoms(this, atoms) + !! Remove atoms from the basis. + use raffle__misc, only: swap + implicit none + + ! Arguments + class(basis_type), intent(inout) :: this + !! Parent. The basis. + integer, dimension(:,:), intent(in) :: atoms + !! The atoms to remove (2, number of atoms to remove) + !! 1st value of 1st dimension is the species number + !! 2nd value of 1st dimension is the atom number + !! 2nd dimension is the number of atoms to remove + + ! Local variables + integer :: is, ia, i + !! Loop index. + integer :: n, m, start_idx, end_idx, loc + !! Index variables. + integer :: num_species + !! The number of species. + integer, dimension(:,:), allocatable :: atoms_ordered + !! The atoms to remove ordered by species and atom + real(real32), dimension(:,:), allocatable :: atom + !! Temporary array to store the atomic positions. + + + !--------------------------------------------------------------------------- + ! reorder atoms to remove + !--------------------------------------------------------------------------- + allocate(atoms_ordered, source=atoms) + n = size(atoms_ordered, 1) + m = size(atoms_ordered, 2) + + do i = 1, m + loc = maxloc(atoms_ordered(1, i:n), dim=1) + i - 1 + if (loc .ne. i) then + call swap(atoms_ordered(1, i), atoms_ordered(1, loc)) + call swap(atoms_ordered(2, i), atoms_ordered(2, loc)) + end if + end do + num_species = this%nspec + do is = 1, num_species + start_idx = findloc(atoms_ordered(1, :), is, dim=1) + end_idx = findloc(atoms_ordered(1, :), is, dim=1, back=.true.) + if (start_idx .eq. 0) cycle + do ia = start_idx, end_idx, 1 + loc = maxloc( & + atoms_ordered(2, ia:end_idx), & + dim=1 & + ) + ia - 1 + if (loc .ne. ia) then + call swap(atoms_ordered(1, ia), atoms_ordered(1, loc)) + call swap(atoms_ordered(2, ia), atoms_ordered(2, loc)) + end if + end do + end do + + + !--------------------------------------------------------------------------- + ! remove atoms from basis + !--------------------------------------------------------------------------- + do i = 1, size(atoms_ordered, 2) + call this%remove_atom(atoms_ordered(1, i), atoms_ordered(2, i)) + end do + + do is = 1, this%nspec + if (this%spec(is)%num .eq. 0) then + this%spec = [ this%spec(1:is-1), this%spec(is+1:) ] + this%nspec = this%nspec - 1 + end if + end do + + end subroutine remove_atoms +!############################################################################### + + !############################################################################### subroutine get_element_properties(element, charge, mass, radius) !! Set the mass and charge of the element diff --git a/src/fortran/lib/mod_io_utils.F90 b/src/fortran/lib/mod_io_utils.F90 index 64c724f2..48ff6c7b 100644 --- a/src/fortran/lib/mod_io_utils.F90 +++ b/src/fortran/lib/mod_io_utils.F90 @@ -7,8 +7,8 @@ module raffle__io_utils logical :: test_error_handling = .false. logical :: suppress_warnings = .false. - character(len=*), parameter :: raffle__version__ = "0.5.1" - + character(len=*), parameter :: raffle__version__ = "1.0.0" + private public :: raffle__version__ @@ -20,23 +20,32 @@ module raffle__io_utils contains !############################################################################### - subroutine stop_program(message, exit_code) + subroutine stop_program(message, exit_code, block_stop) !! Stop the program and print an error message. implicit none character(len=*), intent(in) :: message integer, intent(in), optional :: exit_code + logical, intent(in), optional :: block_stop integer :: exit_code_ + logical :: block_stop_ if(present(exit_code)) then exit_code_ = exit_code else exit_code_ = 1 end if + if(present(block_stop)) then + block_stop_ = block_stop + else + block_stop_ = .false. + end if write(0,*) 'ERROR: ', trim(message) - if(.not.test_error_handling)then - stop exit_code_ + if(.not.block_stop_)then + if(.not.test_error_handling) then + stop exit_code_ + end if end if end subroutine stop_program !############################################################################### @@ -64,17 +73,17 @@ subroutine print_version() end subroutine print_version !############################################################################### - + !############################################################################### subroutine print_build_info() !! Print the build information of the program. implicit none write(*,'("RAFFLE: pseudoRandom Approach For Finding Local Energy minima")') - write(*,'(" version: ",A)') raffle__version__ + call print_version() write(*,'(" (build ",A,1X,A,")")') __DATE__, __TIME__ end subroutine print_build_info !############################################################################### -end module raffle__io_utils \ No newline at end of file +end module raffle__io_utils diff --git a/src/fortran/lib/mod_misc.f90 b/src/fortran/lib/mod_misc.f90 index e0d6405b..83a3ec69 100644 --- a/src/fortran/lib/mod_misc.f90 +++ b/src/fortran/lib/mod_misc.f90 @@ -620,13 +620,14 @@ subroutine ishuffle(arr,dim,seed) iother = 2 i2s=1;i2e=size(arr,dim=iother) j2s=1;j2e=size(arr,dim=iother) + allocate(tlist(1,size(arr,dim=iother))) else iother = 1 i1s=1;i1e=size(arr,dim=iother) j1s=1;j1e=size(arr,dim=iother) + allocate(tlist(size(arr,dim=iother),1)) end if istart=1 - allocate(tlist(1,size(arr,dim=iother))) do k = 1, 2 do i = 1, n_data call random_number(r) @@ -638,9 +639,9 @@ subroutine ishuffle(arr,dim,seed) i2s=i;i2e=i j2s=j;j2e=j end if - tlist(1:1,:) = arr(i1s:i1e,i2s:i2e) + tlist(:,:) = arr(i1s:i1e,i2s:i2e) arr(i1s:i1e,i2s:i2e) = arr(j1s:j1e,j2s:j2e) - arr(j1s:j1e,j2s:j2e) = tlist(1:1,:) + arr(j1s:j1e,j2s:j2e) = tlist(:,:) end do end do diff --git a/src/fortran/lib/mod_place_methods.f90 b/src/fortran/lib/mod_place_methods.f90 index cb704429..bb3e17ab 100644 --- a/src/fortran/lib/mod_place_methods.f90 +++ b/src/fortran/lib/mod_place_methods.f90 @@ -32,7 +32,7 @@ module raffle__place_methods !############################################################################### function place_method_void( & - grid, grid_offset, bounds, basis, atom_ignore_list, viable & + points, basis, atom_ignore_list, viable & ) result(point) !! VOID placement method. !! @@ -41,14 +41,10 @@ function place_method_void( & implicit none ! Arguments + real(real32), dimension(:,:), intent(in) :: points + !! List of gridpoints to consider. type(extended_basis_type), intent(inout) :: basis !! Structure to add atom to. - integer, dimension(3), intent(in) :: grid - !! Number of gridpoints in each direction. - real(real32), dimension(3), intent(in) :: grid_offset - !! Offset for gridpoints. - real(real32), dimension(2,3), intent(in) :: bounds - !! Bounds of the unit cell. integer, dimension(:,:), intent(in) :: atom_ignore_list !! List of atoms to ignore (i.e. indices of atoms not yet placed). logical, intent(out) :: viable @@ -75,21 +71,14 @@ function place_method_void( & !--------------------------------------------------------------------------- best_location = 0._real32 best_location_bond = -huge(1._real32) - do i = 0, grid(1) - 1, 1 - do j = 0, grid(2) - 1, 1 - do k = 0, grid(3) - 1, 1 - tmpvector = bounds(1,:) + & - ( bounds(2,:) - bounds(1,:) ) * & - ( [ i, j, k ] + grid_offset ) / real(grid,real32) - smallest_bond = modu(get_min_dist(& - basis, tmpvector, .false., & - ignore_list = atom_ignore_list)) - if( smallest_bond .gt. best_location_bond ) then - best_location_bond = smallest_bond - best_location = tmpvector - end if - end do - end do + do i = 1, size(points,2) + smallest_bond = modu(get_min_dist(& + basis, [ points(1:3,i) ], .false., & + ignore_list = atom_ignore_list)) + if( smallest_bond .gt. best_location_bond ) then + best_location_bond = smallest_bond + best_location = points(1:3,i) + end if end do diff --git a/src/fortran/lib/mod_viability.f90 b/src/fortran/lib/mod_viability.f90 index b3526123..c4685d5d 100644 --- a/src/fortran/lib/mod_viability.f90 +++ b/src/fortran/lib/mod_viability.f90 @@ -78,8 +78,8 @@ function get_gridpoints_and_viability(distribs_container, grid, bounds, & ( [ i, j, k ] + grid_offset ) / real(grid,real32) do is = 1, basis%nspec atom_loop: do ia = 1, basis%spec(is)%num - do l = 1, size(atom_ignore_list,dim=1), 1 - if(all(atom_ignore_list(l,:).eq.[is,ia])) cycle atom_loop + do l = 1, size(atom_ignore_list,dim=2), 1 + if(all(atom_ignore_list(:,l).eq.[is,ia])) cycle atom_loop end do if( & get_min_dist_between_point_and_atom( & diff --git a/src/raffle/raffle.py b/src/raffle/raffle.py index bb82ad43..bb0f57a7 100644 --- a/src/raffle/raffle.py +++ b/src/raffle/raffle.py @@ -3,6 +3,8 @@ import f90wrap.runtime import logging import numpy +import warnings + class Geom_Rw(f90wrap.runtime.FortranModule): """ @@ -12,7 +14,7 @@ class Geom_Rw(f90wrap.runtime.FortranModule): store atomic geometries. In this module, and all of the codebase, element and species are used interchangeably. - + Defined in ../src/lib/mod_geom_rw.f90 .. note:: @@ -26,7 +28,7 @@ class species_type(f90wrap.runtime.FortranDerivedType): def __init__(self, handle=None): """ Create a ``species_type`` object. - + Returns: species (species_type): Object to be constructed @@ -34,26 +36,26 @@ def __init__(self, handle=None): f90wrap.runtime.FortranDerivedType.__init__(self) result = _raffle.f90wrap_geom_rw__species_type_initialise() self._handle = result[0] if isinstance(result, tuple) else result - + def __del__(self): """ Destructor for class species_type - - + + Defined at ../src/lib/mod_geom_rw.f90 lines \ 26-32 - + Parameters ---------- this : species_type Object to be destructed - - + + Automatically generated destructor for species_type """ if self._alloc: _raffle.f90wrap_geom_rw__species_type_finalise(this=self._handle) - + @property def atom(self): """ @@ -69,36 +71,36 @@ def atom(self): _raffle.f90wrap_species_type__array__atom) self._arrays[array_handle] = atom return atom - + @atom.setter def atom(self, atom): self.atom[...] = atom - + @property def mass(self): """ The mass of the element. """ return _raffle.f90wrap_species_type__get__mass(self._handle) - + @mass.setter def mass(self, mass): _raffle.f90wrap_species_type__set__mass(self._handle, mass) - + @property def charge(self): """ - The charge of the element. + The charge of the element. """ return _raffle.f90wrap_species_type__get__charge(self._handle) - + @property def radius(self): """ The radius of the element. """ return _raffle.f90wrap_species_type__get__radius(self._handle) - + @radius.setter def radius(self, radius): _raffle.f90wrap_species_type__set__radius(self._handle, radius) @@ -106,29 +108,29 @@ def radius(self, radius): @charge.setter def charge(self, charge): _raffle.f90wrap_species_type__set__charge(self._handle, charge) - + @property def name(self): """ The symbol of the element. """ return _raffle.f90wrap_species_type__get__name(self._handle) - + @name.setter def name(self, name): _raffle.f90wrap_species_type__set__name(self._handle, name) - + @property def num(self): """ The number of atoms of this species/element. """ return _raffle.f90wrap_species_type__get__num(self._handle) - + @num.setter def num(self, num): _raffle.f90wrap_species_type__set__num(self._handle, num) - + def __str__(self): ret = ['{\n'] ret.append(' atom : ') @@ -143,10 +145,10 @@ def __str__(self): ret.append(repr(self.num)) ret.append('}') return ''.join(ret) - + _dt_array_initialisers = [] - - + + @f90wrap.runtime.register_class("raffle.basis") class basis(f90wrap.runtime.FortranDerivedType): def __init__(self, atoms=None, handle=None): @@ -156,7 +158,7 @@ def __init__(self, atoms=None, handle=None): This object is used to store the atomic information of a crystal, including lattice and basis information. This is confusingly named as a crystal = lattice + basis. - + Returns: basis (basis): Object to be constructed @@ -167,31 +169,31 @@ def __init__(self, atoms=None, handle=None): if atoms is not None: self.fromase(atoms) - + def __del__(self): """ Destructor for class basis - - + + Defined at ../src/lib/mod_geom_rw.f90 lines \ 34-42 - + Parameters ---------- this : basis Object to be destructed - - + + Automatically generated destructor for basis """ if self._alloc: _raffle.f90wrap_geom_rw__basis_type_finalise(this=self._handle) - + def allocate_species(self, num_species=None, species_symbols=None, species_count=None, \ positions=None): """ Allocate memory for the species list. - + Parameters: num_species (int): Number of species @@ -205,7 +207,7 @@ def allocate_species(self, num_species=None, species_symbols=None, species_count _raffle.f90wrap_geom_rw__allocate_species__binding__basis_type(this=self._handle, \ num_species=num_species, species_symbols=species_symbols, species_count=species_count, \ atoms=positions) - + def _init_array_spec(self): """ Initialise the species array. @@ -216,13 +218,13 @@ def _init_array_spec(self): _raffle.f90wrap_basis_type__array_len__spec, """ Element spec ftype=type(species_type) pytype=species_type - - + + Defined at ../src/lib/mod_geom_rw.f90 line 35 - + """, Geom_Rw.species_type) return self.spec - + def toase(self, calculator=None): """ Convert the basis object to an ASE Atoms object. @@ -240,7 +242,7 @@ def toase(self, calculator=None): for j in range(self.spec[i].num): species_string += str(self.spec[i].name.decode()).strip() positions.append(self.spec[i].atom[j]) - + # Set the atoms if(self.lcart): atoms = Atoms(species_string, positions=positions, cell=self.lat, pbc=self.pbc) @@ -250,7 +252,7 @@ def toase(self, calculator=None): if calculator is not None: atoms.calc = calculator return atoms - + def fromase(self, atoms, verbose=False): """ Convert the ASE Atoms object to a basis object. @@ -262,14 +264,14 @@ def fromase(self, atoms, verbose=False): Boolean whether to print warnings. """ from ase.calculators.singlepoint import SinglePointCalculator - + # Get the species symbols species_symbols = atoms.get_chemical_symbols() species_symbols_unique = sorted(set(species_symbols)) # Set the number of species self.nspec = len(species_symbols_unique) - + # Set the number of atoms self.natom = len(atoms) @@ -279,14 +281,14 @@ def fromase(self, atoms, verbose=False): print("WARNING: No calculator present, setting energy to 0.0") atoms.calc = SinglePointCalculator(atoms, energy=0.0) self.energy = atoms.get_potential_energy() - + # # Set the lattice vectors self.lat = numpy.reshape(atoms.get_cell().flatten(), [3,3], order='A') self.pbc = atoms.pbc - + # Set the system name self.sysname = atoms.get_chemical_formula() - + # Set the species list species_count = [] atom_positions = [] @@ -296,7 +298,7 @@ def fromase(self, atoms, verbose=False): for j, symbol in enumerate(species_symbols): if symbol == species: atom_positions.append(positions[j]) - + # Allocate memory for the atom list self.lcart = False self.allocate_species(species_symbols=species_symbols_unique, species_count=species_count, positions=atom_positions) @@ -307,33 +309,33 @@ def nspec(self): The number of species in the basis. """ return _raffle.f90wrap_basis_type__get__nspec(self._handle) - + @nspec.setter def nspec(self, nspec): _raffle.f90wrap_basis_type__set__nspec(self._handle, nspec) - + @property def natom(self): """ The number of atoms in the basis. """ return _raffle.f90wrap_basis_type__get__natom(self._handle) - + @natom.setter def natom(self, natom): _raffle.f90wrap_basis_type__set__natom(self._handle, natom) - + @property def energy(self): """ The energy associated with the basis (or crystal). """ return _raffle.f90wrap_basis_type__get__energy(self._handle) - + @energy.setter def energy(self, energy): _raffle.f90wrap_basis_type__set__energy(self._handle, energy) - + @property def lat(self): """ @@ -349,22 +351,22 @@ def lat(self): _raffle.f90wrap_basis_type__array__lat) self._arrays[array_handle] = lat return lat - + @lat.setter def lat(self, lat): self.lat[...] = lat - + @property def lcart(self): """ Boolean whether the atomic positions are in cartesian coordinates. """ return _raffle.f90wrap_basis_type__get__lcart(self._handle) - + @lcart.setter def lcart(self, lcart): _raffle.f90wrap_basis_type__set__lcart(self._handle, lcart) - + @property def pbc(self): """ @@ -380,11 +382,11 @@ def pbc(self): _raffle.f90wrap_basis_type__array__pbc) self._arrays[array_handle] = pbc return pbc - + @pbc.setter def pbc(self, pbc): self.pbc[...] = pbc - + @property def sysname(self): """ @@ -395,7 +397,7 @@ def sysname(self): @sysname.setter def sysname(self, sysname): _raffle.f90wrap_basis_type__set__sysname(self._handle, sysname) - + def __str__(self): ret = ['{\n'] ret.append(' nspec : ') @@ -414,9 +416,9 @@ def __str__(self): ret.append(repr(self.sysname)) ret.append('}') return ''.join(ret) - + _dt_array_initialisers = [_init_array_spec] - + @f90wrap.runtime.register_class("raffle.basis_array") @@ -424,8 +426,8 @@ class basis_array(f90wrap.runtime.FortranDerivedType): def __init__(self, atoms=None, handle=None): """ Create a ``basis_array`` object. - - + + Returns: basis_array (basis_array): Object to be constructed @@ -446,26 +448,26 @@ def __init__(self, atoms=None, handle=None): self.allocate(len(atoms)) for i, atom in enumerate(atoms): self.items[i].fromase(atom) - + def __del__(self): """ Destructor for class basis_array - - + + Defined at ../src/lib/mod_generator.f90 lines \ 19-21 - + Parameters ---------- this : basis_array Object to be destructed - - + + Automatically generated destructor for basis_array """ if self._alloc: _raffle.f90wrap_geom_rw__basis_type_xnum_array_finalise(this=self._handle) - + def _init_array_items(self): """ Initialise the items array. @@ -476,13 +478,13 @@ def _init_array_items(self): _raffle.f90wrap_basis_type_xnum_array__array_len__items, """ Element items ftype=type(basis_type) pytype=basis - - + + Defined at line 0 - + """, Geom_Rw.basis) return self.items - + def toase(self): """ Convert the basis_array object to a list of ASE Atoms objects. @@ -497,7 +499,7 @@ def toase(self): def allocate(self, size): """ Allocate the items array with the given size. - + Parameters: size (int): Size of the items array @@ -509,11 +511,11 @@ def deallocate(self): Deallocate the items array """ _raffle.f90wrap_basis_type_xnum_array__array_dealloc__items(self._handle) - + _dt_array_initialisers = [_init_array_items] - + _dt_array_initialisers = [] - + geom_rw = Geom_Rw() @@ -527,9 +529,9 @@ class Raffle__Distribs_Container(f90wrap.runtime.FortranModule): environments in a crystal. The generalised distribution function (GDF) is a generalised descriptor for the atomic configurations that each species can adopt. - + Defined in ../src/fortran/lib/mod_distribs_container.f90 - + """ @f90wrap.runtime.register_class("raffle.distribs_container_type") class distribs_container_type(f90wrap.runtime.FortranDerivedType): @@ -546,26 +548,26 @@ def __init__(self, handle=None): result = \ _raffle.f90wrap_raffle__dc__dc_type_initialise() self._handle = result[0] if isinstance(result, tuple) else result - + def __del__(self): """ Destructor for class Distribs_Container_Type - - + + Defined at ../fortran/lib/mod_distribs_container.f90 \ lines 25-162 - + Parameters ---------- this : Distribs_Container_Type Object to be destructed - - + + Automatically generated destructor for distribs_container_type """ if self._alloc: _raffle.f90wrap_raffle__dc__dc_type_finalise(this=self._handle) - + def set_kBT(self, kBT): """ Set the energy scale for the distribution functions. @@ -573,7 +575,7 @@ def set_kBT(self, kBT): Parameters: kBT (float): Energy scale for the distribution functions. - + """ self.kBT = kBT @@ -588,7 +590,7 @@ def set_weight_method(self, method): Allowed values are: - 'formation_energy' or 'formation' or 'form' or 'e_form' - 'energy_above_hull' or 'hull_distance' or 'hull' or 'distance' or 'convex_hull' - + """ if method in ['empirical', 'formation_energy', 'formation', 'form', 'e_form']: @@ -601,7 +603,7 @@ def set_weight_method(self, method): def set_width(self, width): """ Set the distribution function widths. - + Parameters: width (list of float): List of distribution function widths. @@ -611,7 +613,7 @@ def set_width(self, width): """ _raffle.f90wrap_raffle__dc__set_width__binding__dc_type(this=self._handle, \ width=width) - + def set_sigma(self, sigma): """ Set the sigma values of the Gaussians used to @@ -626,7 +628,7 @@ def set_sigma(self, sigma): """ _raffle.f90wrap_raffle__dc__set_sigma__binding__dc_type(this=self._handle, \ sigma=sigma) - + def set_cutoff_min(self, cutoff_min): """ Set the minimum cutoff values for the distribution functions. @@ -640,7 +642,7 @@ def set_cutoff_min(self, cutoff_min): """ _raffle.f90wrap_raffle__dc__set_cutoff_min__binding__dc_type(this=self._handle, \ cutoff_min=cutoff_min) - + def set_cutoff_max(self, cutoff_max): """ Set the maximum cutoff values for the distribution functions. @@ -654,14 +656,14 @@ def set_cutoff_max(self, cutoff_max): """ _raffle.f90wrap_raffle__dc__set_cutoff_max__binding__dc_type(this=self._handle, \ cutoff_max=cutoff_max) - + def set_radius_distance_tol(self, radius_distance_tol): """ Set the radius distance tolerance for the distribution functions. The radius distance tolerance represents a multiplier to the bond radii to determine the cutoff distance for the distribution functions. - + Parameters: radius_distance_tol (list of float): List of radius distance tolerance values. @@ -672,7 +674,7 @@ def set_radius_distance_tol(self, radius_distance_tol): """ _raffle.f90wrap_raffle__dc__set_radius_distance_tol__binding__dc_type(this=self._handle, \ radius_distance_tol=radius_distance_tol) - + def create(self, basis_list, energy_above_hull_list=None, deallocate_systems=True, verbose=None): """ Create the distribution functions. @@ -700,7 +702,7 @@ def create(self, basis_list, energy_above_hull_list=None, deallocate_systems=Tru deallocate_systems=deallocate_systems, \ verbose=verbose \ ) - + def update(self, basis_list, energy_above_hull_list=None, from_host=True, deallocate_systems=True, verbose=None): """ Update the distribution functions. @@ -723,7 +725,7 @@ def update(self, basis_list, energy_above_hull_list=None, from_host=True, deallo elif isinstance(basis_list, list): if all([isinstance(basis, Atoms) for basis in basis_list]): basis_list = geom_rw.basis_array(basis_list) - + _raffle.f90wrap_raffle__dc__update__binding__dc_type(this=self._handle, \ basis_list=basis_list._handle, \ @@ -732,35 +734,35 @@ def update(self, basis_list, energy_above_hull_list=None, from_host=True, deallo deallocate_systems=deallocate_systems, \ verbose=verbose \ ) - + def deallocate_systems(self): """ Deallocate the atomic configurations. """ _raffle.f90wrap_raffle__dc__deallocate_systems__binding__dc_type(this=self._handle) - + def add_basis(self, basis): """ Add a basis to the distribution functions. It is not recommended to use this function directly, but to use the create or update functions instead. - + Parameters: basis (geom_rw.basis): Basis object to be added to the distribution functions. - + """ _raffle.f90wrap_raffle__dc__add_basis__binding__dc_type(this=self._handle, \ basis=basis._handle) - + def set_element_energies(self, element_energies): """ Set the element reference energies for the distribution functions. These energies are used to calculate the formation energies of the atomic configurations. - + Parameters: element_energies (dict): Dictionary of element reference energies. @@ -771,11 +773,11 @@ def set_element_energies(self, element_energies): energies = [element_energies[element] for element in element_list] _raffle.f90wrap_raffle__dc__set_element_energies__binding__dc_type(this=self._handle, \ elements=element_list, energies=energies) - + def get_element_energies(self): """ Get the element reference energies for the distribution functions. - + Returns: element_energies (dict): Dictionary of element reference energies. @@ -788,7 +790,7 @@ def get_element_energies(self): _raffle.f90wrap_raffle__dc__get_element_energies_sm__binding__dc_type(this=self._handle, \ elements=elements, energies=energies) - + # convert the fortran array to a python dictionary element_energies = {} for i, element in enumerate(elements): @@ -805,17 +807,17 @@ def set_bond_info(self): set_bond_radius or set_bond_radii functions instead. """ _raffle.f90wrap_raffle__dc__set_bond_info__binding__dc_type(this=self._handle) - + def set_bond_radius(self, radius_dict): """ - Set the bond radius for the distribution functions. - + Set the bond radius for the distribution functions. + Parameters: radius_dict (dict): Dictionary of bond radii. The keys are a tuple of the two element symbols and the values are the bond radii. """ - + # convert radius_dict to elements and radius # radius_dict = {('C', 'C'): 1.5} elements = list(radius_dict.keys()[0]) @@ -823,11 +825,11 @@ def set_bond_radius(self, radius_dict): _raffle.f90wrap_raffle__dc__set_bond_radius__binding__dc_type(this=self._handle, \ elements=elements, radius=radius) - + def set_bond_radii(self, radius_dict): """ Set the bond radii for the distribution functions. - + Parameters: radius_dict (dict): Dictionary of bond radii. @@ -841,15 +843,15 @@ def set_bond_radii(self, radius_dict): for key, value in radius_dict.items(): elements.append(list(key)) radii.append(value) - + _raffle.f90wrap_raffle__dc__set_bond_radii__binding__dc_type(this=self._handle, \ elements=elements, radii=radii) - + def get_bond_radii(self): """ - Get the bond radii for the distribution functions. - + Get the bond radii for the distribution functions. + Returns: bond_radii (dict): Dictionary of bond radii. @@ -867,7 +869,7 @@ def get_bond_radii(self): elements=elements, radii=radii) # _raffle.f90wrap_raffle__dc__get_bond_radii_staticmem__binding__dc_type(this=self._handle, \ # elements=elements, energies=energies) - + # convert the fortran array to a python dictionary bond_radii = {} for i, element in enumerate(elements): @@ -875,7 +877,7 @@ def get_bond_radii(self): bond_radii[names] = radii[i] return bond_radii - + def initialise_gdfs(self): """ Initialise the generalised distribution functions (GDFs). @@ -884,7 +886,7 @@ def initialise_gdfs(self): create or update functions instead. """ _raffle.f90wrap_raffle__dc__initialise_gdfs__binding__dc_type(this=self._handle) - + def evolve(self): #, system=None): """ Evolve the distribution functions. @@ -895,18 +897,18 @@ def evolve(self): #, system=None): _raffle.f90wrap_raffle__dc__evolve__binding__dc_type(this=self._handle) # _raffle.f90wrap_raffle__dc__evolve__binding__dc_type(this=self._handle, \ # system=None if system is None else system._handle) - + def write_gdfs(self, file): """ Write the generalised distribution functions (GDFs) to a file. - + Parameters: file (str): Name of file to write the GDFs to. """ _raffle.f90wrap_raffle__dc__write_gdfs__binding__dc_type(this=self._handle, \ file=file) - + def read_gdfs(self, file): """ Read the generalised distribution functions (GDFs) from a file. @@ -929,10 +931,10 @@ def write_dfs(self, file): """ _raffle.f90wrap_raffle__dc__write_dfs__binding__dc_type(this=self._handle, \ file=file) - + def read_dfs(self, file): """ - Read the distribution functions (DFs) associated with a set of + Read the distribution functions (DFs) associated with a set of systems from a file. Parameters: @@ -941,52 +943,52 @@ def read_dfs(self, file): """ _raffle.f90wrap_raffle__dc__read_dfs__binding__dc_type(this=self._handle, \ file=file) - + def write_2body(self, file): """ Write the 2-body generalised distribution functions (GDFs) to a file. - + Parameters: file (str): Name of file to write the 2-body GDFs to. """ _raffle.f90wrap_raffle__dc__write_2body__binding__dc_type(this=self._handle, \ file=file) - + def write_3body(self, file): """ Write the 3-body generalised distribution functions (GDFs) to a file. - + Parameters: file (str): Name of file to write the 3-body GDFs to. """ _raffle.f90wrap_raffle__dc__write_3body__binding__dc_type(this=self._handle, \ file=file) - + def write_4body(self, file): """ Write the 4-body generalised distribution functions (GDFs) to a file. - + Parameters: file (str): Name of file to write the 4-body GDFs to. """ _raffle.f90wrap_raffle__dc__write_4body__binding__dc_type(this=self._handle, \ file=file) - + def _get_pair_index(self, species1, species2): """ Get the index of the pair of species in the distribution functions. This is meant as an internal function and not likely to be used directly. - + Parameters: species1 (str): Name of the first species species2 (str): Name of the second species - + Returns: idx (int): Index of the pair of species in the distribution functions. @@ -995,7 +997,7 @@ def _get_pair_index(self, species1, species2): _raffle.f90wrap_raffle__dc__get_pair_index__binding__dc_type(this=self._handle, \ species1=species1, species2=species2) return idx - + def _get_bin(self, value, dim): """ Get the bin index for a value in the distribution functions. @@ -1008,30 +1010,30 @@ def _get_bin(self, value, dim): dim (int): Dimension of the distribution function. 1 for 2-body, 2 for 3-body, and 3 for 4-body. - + Returns ------- bin (int): Bin index for the value in the distribution functions. - + """ bin = \ _raffle.f90wrap_raffle__dc__get_bin__binding__dc_type(this=self._handle, \ value=value, dim=dim) return bin - + @property def num_evaluated(self): """ Number of evaluated distribution functions. """ return _raffle.f90wrap_distribs_container_type__get__num_evaluated(self._handle) - + @num_evaluated.setter def num_evaluated(self, num_evaluated): _raffle.f90wrap_distribs_container_type__set__num_evaluated(self._handle, \ num_evaluated) - + @property def num_evaluated_allocated(self): """ @@ -1039,23 +1041,23 @@ def num_evaluated_allocated(self): """ return \ _raffle.f90wrap_distribs_container_type__get__num_evaluated_allocated(self._handle) - + @num_evaluated_allocated.setter def num_evaluated_allocated(self, num_evaluated_allocated): _raffle.f90wrap_distribs_container_type__set__num_evaluated_allocated(self._handle, \ num_evaluated_allocated) - + @property def kBT(self): """ Energy scale for the distribution functions. """ return _raffle.f90wrap_distribs_container_type__get__kbt(self._handle) - + @kBT.setter def kBT(self, kBT): _raffle.f90wrap_distribs_container_type__set__kbt(self._handle, kBT) - + @property def weight_by_hull(self): """ @@ -1063,16 +1065,16 @@ def weight_by_hull(self): """ return \ _raffle.f90wrap_distribs_container_type__get__weight_by_hull(self._handle) - + @weight_by_hull.setter def weight_by_hull(self, weight_by_hull): _raffle.f90wrap_distribs_container_type__set__weight_by_hull(self._handle, \ weight_by_hull) - + @property def nbins(self): """ - Number of bins in the distribution functions. + Number of bins in the distribution functions. """ array_ndim, array_type, array_shape, array_handle = \ _raffle.f90wrap_distribs_container_type__array__nbins(self._handle) @@ -1084,11 +1086,11 @@ def nbins(self): _raffle.f90wrap_distribs_container_type__array__nbins) self._arrays[array_handle] = nbins return nbins - + @nbins.setter def nbins(self, nbins): self.nbins[...] = nbins - + @property def sigma(self): """ @@ -1105,11 +1107,11 @@ def sigma(self): _raffle.f90wrap_distribs_container_type__array__sigma) self._arrays[array_handle] = sigma return sigma - + @sigma.setter def sigma(self, sigma): self.sigma[...] = sigma - + @property def width(self): """ @@ -1125,11 +1127,11 @@ def width(self): _raffle.f90wrap_distribs_container_type__array__width) self._arrays[array_handle] = width return width - + @width.setter def width(self, width): self.width[...] = width - + @property def cutoff_min(self): """ @@ -1145,11 +1147,11 @@ def cutoff_min(self): _raffle.f90wrap_distribs_container_type__array__cutoff_min) self._arrays[array_handle] = cutoff_min return cutoff_min - + @cutoff_min.setter def cutoff_min(self, cutoff_min): self.cutoff_min[...] = cutoff_min - + @property def cutoff_max(self): """ @@ -1165,11 +1167,11 @@ def cutoff_max(self): _raffle.f90wrap_distribs_container_type__array__cutoff_max) self._arrays[array_handle] = cutoff_max return cutoff_max - + @cutoff_max.setter def cutoff_max(self, cutoff_max): self.cutoff_max[...] = cutoff_max - + @property def radius_distance_tol(self): """ @@ -1177,7 +1179,7 @@ def radius_distance_tol(self): The radius distance tolerance represents a multiplier to the bond radii to determine the cutoff distance for the distribution functions. - + The first two values are the lower and upper bounds for the 3-body distribution function radius distance tolerance. The third and fourth values are the lower and upper bounds for the @@ -1194,11 +1196,11 @@ def radius_distance_tol(self): _raffle.f90wrap_distribs_container_type__array__radius_distance_tol) self._arrays[array_handle] = radius_distance_tol return radius_distance_tol - + @radius_distance_tol.setter def radius_distance_tol(self, radius_distance_tol): self.radius_distance_tol[...] = radius_distance_tol - + def __str__(self): ret = ['{\n'] ret.append(' num_evaluated : ') @@ -1223,12 +1225,12 @@ def __str__(self): ret.append(repr(self.radius_distance_tol)) ret.append('}') return ''.join(ret) - + _dt_array_initialisers = []#_init_array_system] - - + + _dt_array_initialisers = [] - + raffle__distribs_container = Raffle__Distribs_Container() @@ -1239,16 +1241,16 @@ class Generator(f90wrap.runtime.FortranModule): The module handles converting Python objects to Fortran objects and vice versa. These include converting between dictionaries and Fortran derived types, and between ASE Atoms objects and Fortran derived types. - + Defined in ../src/lib/mod_generator.f90 - + """ @f90wrap.runtime.register_class("raffle.stoichiometry_type") class stoichiometry_type(f90wrap.runtime.FortranDerivedType): def __init__(self, dict=None, element=None, num=None, handle=None): """ - Object to store the stoichiometry of a structure. - + Object to store the stoichiometry of a structure. + Returns: stoichiometry (stoichiometry_type): Stoichiometry object @@ -1262,42 +1264,42 @@ def __init__(self, dict=None, element=None, num=None, handle=None): if num: self.num = num - + def __del__(self): """ Destructor for class Stoichiometry_Type - - + + Defined at ../src/lib/mod_generator.f90 lines \ 19-21 - + Automatically generated destructor for stoichiometry_type """ if self._alloc: _raffle.f90wrap_stoichiometry_type_finalise(this=self._handle) - + @property def element(self): """ String representing an element symbol. """ return _raffle.f90wrap_stoichiometry_type__get__element(self._handle) - + @element.setter def element(self, element): _raffle.f90wrap_stoichiometry_type__set__element(self._handle, element) - + @property def num(self): """ Integer representing the number of atoms of the element. """ return _raffle.f90wrap_stoichiometry_type__get__num(self._handle) - + @num.setter def num(self, num): _raffle.f90wrap_stoichiometry_type__set__num(self._handle, num) - + def __str__(self): ret = ['{\n'] ret.append(' element : ') @@ -1306,16 +1308,16 @@ def __str__(self): ret.append(repr(self.num)) ret.append('}') return ''.join(ret) - + _dt_array_initialisers = [] - - + + @f90wrap.runtime.register_class("raffle.stoichiometry_array") class stoichiometry_array(f90wrap.runtime.FortranDerivedType): def __init__(self, dict=None, handle=None): """ Array or list of stoichiometry objects. - + Returns: stoichiometry_array (stoichiometry_array): Stoichiometry array object @@ -1332,26 +1334,26 @@ def __init__(self, dict=None, handle=None): for i in range(num_elements): self.items[i].element = elements[i] self.items[i].num = nums[i] - + def __del__(self): """ Destructor for class Stoichiometry_Type - - + + Defined at ../src/lib/mod_generator.f90 lines \ 19-21 - + Parameters ---------- this : Stoichiometry_Type Object to be destructed - - + + Automatically generated destructor for stoichiometry_type """ if self._alloc: _raffle.f90wrap_generator__stoich_type_xnum_array_finalise(this=self._handle) - + def _init_array_items(self): self.items = f90wrap.runtime.FortranDerivedTypeArray(self, _raffle.f90wrap_stoich_type_xnum_array__array_getitem__items, @@ -1359,17 +1361,17 @@ def _init_array_items(self): _raffle.f90wrap_stoich_type_xnum_array__array_len__items, """ Element items ftype=type(stoichiometry_type) pytype=stoichiometry_type - - + + Defined at line 0 - + """, Generator.stoichiometry_type) return self.items - + def allocate(self, size): """ Allocate the items array with the given size. - + Parameters: size (int): Size of the items array @@ -1382,11 +1384,11 @@ def deallocate(self): """ _raffle.f90wrap_stoich_type_xnum_array__array_dealloc__items(self._handle) - + _dt_array_initialisers = [_init_array_items] - - + + @f90wrap.runtime.register_class("raffle.raffle_generator") class raffle_generator(f90wrap.runtime.FortranDerivedType): @@ -1401,15 +1403,15 @@ def __init__(self, handle=None): f90wrap.runtime.FortranDerivedType.__init__(self) result = _raffle.f90wrap_generator__raffle_generator_type_initialise() self._handle = result[0] if isinstance(result, tuple) else result - + def __del__(self): """ Destructor for class raffle_generator - - + + Defined at ../src/lib/mod_generator.f90 lines \ 23-34 - + """ if self._alloc: _raffle.f90wrap_generator__raffle_generator_type_finalise(this=self._handle) @@ -1440,11 +1442,11 @@ def set_walk_step_size(self, coarse=None, fine=None): self.walk_step_size_coarse = coarse if fine is not None: self.walk_step_size_fine = fine - + def set_host(self, host): """ Set the host structure for the generation. - + Parameters: host (ase.Atoms or geom_rw.basis): The host structure for the generation. @@ -1456,7 +1458,7 @@ def set_host(self, host): _raffle.f90wrap_generator__set_host__binding__rgt(this=self._handle, \ host=host._handle) - + def set_grid(self, grid=None, grid_spacing=None, grid_offset=None): """ Set the grid parameters for the generation. @@ -1471,13 +1473,13 @@ def set_grid(self, grid=None, grid_spacing=None, grid_offset=None): """ _raffle.f90wrap_generator__set_grid__binding__raffle_generator_type(this=self._handle, \ grid=grid, grid_spacing=grid_spacing, grid_offset=grid_offset) - + def reset_grid(self): """ Reset the grid parameters to their default values. """ _raffle.f90wrap_generator__reset_grid__binding__raffle_generator_type(this=self._handle) - + def set_bounds(self, bounds=None): """ Set the bounding box for the generation. @@ -1490,14 +1492,20 @@ def set_bounds(self, bounds=None): """ _raffle.f90wrap_generator__set_bounds__binding__rgt(this=self._handle, \ bounds=bounds) - + def reset_bounds(self): """ Reset the bounding box to the full host structure. """ _raffle.f90wrap_generator__reset_bounds__binding__rgt(this=self._handle) - def generate(self, num_structures, stoichiometry, method_probab={"void": 0.0, "rand": 0.0, "walk": 0.0, "grow": 0.0, "min": 0.0}, seed=None, settings_out_file=None, verbose=0): + def generate( + self, num_structures, stoichiometry, + method_ratio={"void": 0.0, "rand": 0.0, "walk": 0.0, "grow": 0.0, "min": 0.0}, + method_probab=None, + seed=None, settings_out_file=None, verbose=0, + calc=None + ): """ Generate structures using the RAFFLE method. @@ -1506,48 +1514,63 @@ def generate(self, num_structures, stoichiometry, method_probab={"void": 0.0, "r The number of structures to generate. stoichiometry (stoichiometry_array or dict): The stoichiometry of the structures to generate. + method_ratio (dict): + The ratio of using each method to generate a structure. method_probab (dict): - The probabilities of using each method to generate a structure. + DEPRECATED - The ratio of using each method to generate a structure. seed (int): The seed for the random number generator. - print_settings (bool): - Boolean whether to print the settings for the generation. + settings_out_file (str): + The file to write the settings to. verbose (int): The verbosity level for the generation. - """ - - method_probab_list = [] - method_probab_list.append(method_probab.get("void", 0.0)) - method_probab_list.append(method_probab.get("rand", 0.0)) # or method_probab.get("random", 0.0)) - method_probab_list.append(method_probab.get("walk", 0.0)) - method_probab_list.append(method_probab.get("grow", 0.0)) # or method_probab.get("growth", 0.0)) - method_probab_list.append(method_probab.get("min", 0.0)) # or method_probab.get("minimum", 0.0) or method_probab.get("global", 0.0)) - + calc (ASE calculator): + The calculator to use for the generated structures. + + Returns: + structures (geom_rw.basis_array): + The generated structures. + exit_code (int): + The exit code from the generation. + """ + + exit_code = 0 + structures = None + + # check if method_ratio is provided, if so, use it only if method_ratio is not provided + if method_probab is not None and method_ratio == {"void": 0.0, "rand": 0.0, "walk": 0.0, "grow": 0.0, "min": 0.0}: + method_ratio = method_probab + warnings.warn("method_probab is deprecated, use method_ratio instead", DeprecationWarning) + elif method_probab is not None: + warnings.warn("method_probab is deprecated, use method_ratio instead", DeprecationWarning) + # break if both method_ratio and method_probab are provided + raise ValueError("Both method_ratio and method_probab are provided, use only one (method_ratio)") + method_ratio_list = [] + method_ratio_list.append(method_ratio.get("void", 0.0)) + method_ratio_list.append(method_ratio.get("rand", 0.0)) # or method_ratio.get("random", 0.0)) + method_ratio_list.append(method_ratio.get("walk", 0.0)) + method_ratio_list.append(method_ratio.get("grow", 0.0)) # or method_ratio.get("growth", 0.0)) + method_ratio_list.append(method_ratio.get("min", 0.0)) # or method_ratio.get("minimum", 0.0) or method_ratio.get("global", 0.0)) + # check if all values are 0.0, if so, set them to the default of all 1.0 - if all([probab < 1E-6 for probab in method_probab_list]): - method_probab_list = [1.0, 0.1, 0.5, 0.5, 1.0] + if all([val < 1E-6 for val in method_ratio_list]): + method_ratio_list = [1.0, 0.1, 0.5, 0.5, 1.0] # if stoichiometry is a dictionary, convert it to a stoichiometry_array if isinstance(stoichiometry, dict): stoichiometry = Generator.stoichiometry_array(dict=stoichiometry) - if seed is not None: - _raffle.f90wrap_generator__generate__binding__rgt( - this=self._handle, - num_structures=num_structures, - stoichiometry=stoichiometry._handle, - method_probab=method_probab_list, - settings_out_file=settings_out_file, - seed=seed, verbose=verbose) - else: - _raffle.f90wrap_generator__generate__binding__rgt( - this=self._handle, - num_structures=num_structures, - stoichiometry=stoichiometry._handle, - method_probab=method_probab_list, - settings_out_file=settings_out_file, - verbose=verbose) - + exit_code = _raffle.f90wrap_generator__generate__binding__rgt( + this=self._handle, + num_structures=num_structures, + stoichiometry=stoichiometry._handle, + method_ratio=method_ratio_list, + settings_out_file=settings_out_file, + seed=seed, verbose=verbose) + + structures = self.get_structures(self, calc)[-num_structures:] + return structures, exit_code + def get_structures(self, calculator=None): """ Get the generated structures as a list of ASE Atoms objects. @@ -1560,7 +1583,7 @@ def get_structures(self, calculator=None): for structure in self.structures: atoms.append(structure.toase(calculator)) return atoms - + def set_structures(self, structures): """ Set the list of generated structures. @@ -1571,15 +1594,15 @@ def set_structures(self, structures): """ structures = geom_rw.basis_array(atoms=structures) _raffle.f90wrap_generator__set_structures__binding__rgt(this=self._handle, \ - structures=structures._handle) - + structures=structures._handle) + def remove_structure(self, index): """ Remove the structure at the given indices from the generator. - + Parameters: index (int or list of int): - The indices of the structure to remove. + The indices of the structure to remove. """ index_list = [index] if isinstance(index, int) else index index_list = [ i + 1 for i in index_list ] @@ -1591,11 +1614,11 @@ def evaluate(self, basis): Evaluate the viability of the structures. WARNING: This function is not implemented yet. - + Parameters: basis (geom_rw.basis or Atoms): The basis to use for the evaluation. - + Returns: viability (float): The viability of the structures. @@ -1608,7 +1631,7 @@ def evaluate(self, basis): _raffle.f90wrap_generator__evaluate__binding__rgt(this=self._handle, \ basis=basis._handle) return viability - + def print_settings(self, file): """ Print the settings for the generation to a file. @@ -1619,7 +1642,7 @@ def print_settings(self, file): """ _raffle.f90wrap_generator__print_settings__binding__rgt(this=self._handle, \ file=file) - + def read_settings(self, file): """ Read the settings for the generation from a file. @@ -1634,15 +1657,15 @@ def read_settings(self, file): @property def num_structures(self): """ - The number of generated structures currently stored in the generator. + The number of generated structures currently stored in the generator. """ return _raffle.f90wrap_raffle_generator_type__get__num_structures(self._handle) - + @num_structures.setter def num_structures(self, num_structures): _raffle.f90wrap_raffle_generator_type__set__num_structures(self._handle, \ num_structures) - + @property def host(self): """ @@ -1655,12 +1678,12 @@ def host(self): host = geom_rw.basis.from_handle(host_handle) self._objs[tuple(host_handle)] = host return host - + @host.setter def host(self, host): host = host._handle _raffle.f90wrap_raffle_generator_type__set__host(self._handle, host) - + @property def grid(self): """ @@ -1676,11 +1699,11 @@ def grid(self): _raffle.f90wrap_raffle_generator_type__array__grid) self._arrays[array_handle] = grid return grid - + @grid.setter def grid(self, grid): self.grid[...] = grid - + @property def grid_offset(self): """ @@ -1696,7 +1719,7 @@ def grid_offset(self): _raffle.f90wrap_raffle_generator_type__array__grid_offset) self._arrays[array_handle] = grid_offset return grid_offset - + @grid_offset.setter def grid_offset(self, grid_offset): self.grid_offset[...] = grid_offset @@ -1707,12 +1730,12 @@ def grid_spacing(self): The spacing between grid points. """ return _raffle.f90wrap_raffle_generator_type__get__grid_spacing(self._handle) - + @grid_spacing.setter def grid_spacing(self, grid_spacing): _raffle.f90wrap_raffle_generator_type__set__grid_spacing(self._handle, \ grid_spacing) - + @property def bounds(self): """ @@ -1728,7 +1751,7 @@ def bounds(self): _raffle.f90wrap_raffle_generator_type__array__bounds) self._arrays[array_handle] = bounds return bounds - + @bounds.setter def bounds(self, bounds): self.bounds[...] = bounds @@ -1747,20 +1770,20 @@ def distributions(self): raffle__distribs_container.distribs_container_type.from_handle(distributions_handle) self._objs[tuple(distributions_handle)] = distributions return distributions - + @distributions.setter def distributions(self, distributions): distributions = distributions._handle _raffle.f90wrap_raffle_generator_type__set__distributions(self._handle, \ distributions) - + @property def max_attempts(self): """ The maximum number of attempts to generate a structure using the walk method. """ return _raffle.f90wrap_raffle_generator_type__get__max_attempts(self._handle) - + @max_attempts.setter def max_attempts(self, max_attempts): _raffle.f90wrap_raffle_generator_type__set__max_attempts(self._handle, \ @@ -1773,12 +1796,12 @@ def walk_step_size_coarse(self): """ return \ _raffle.f90wrap_raffle_generator_type__get__walk_step_size_coarse(self._handle) - + @walk_step_size_coarse.setter def walk_step_size_coarse(self, walk_step_size_coarse): _raffle.f90wrap_raffle_generator_type__set__walk_step_size_coarse(self._handle, \ walk_step_size_coarse) - + @property def walk_step_size_fine(self): """ @@ -1786,32 +1809,32 @@ def walk_step_size_fine(self): """ return \ _raffle.f90wrap_raffle_generator_type__get__walk_step_size_fine(self._handle) - + @walk_step_size_fine.setter def walk_step_size_fine(self, walk_step_size_fine): _raffle.f90wrap_raffle_generator_type__set__walk_step_size_fine(self._handle, \ walk_step_size_fine) - + @property - def method_probab(self): + def method_ratio(self): """ - The probabilities of using each method to generate a structure. + The ratio of methods to employ to generate a structure. """ array_ndim, array_type, array_shape, array_handle = \ - _raffle.f90wrap_raffle_generator_type__array__method_probab(self._handle) + _raffle.f90wrap_raffle_generator_type__array__method_ratio(self._handle) if array_handle in self._arrays: - method_probab = self._arrays[array_handle] + method_ratio = self._arrays[array_handle] else: - method_probab = f90wrap.runtime.get_array(f90wrap.runtime.sizeof_fortran_t, + method_ratio = f90wrap.runtime.get_array(f90wrap.runtime.sizeof_fortran_t, self._handle, - _raffle.f90wrap_raffle_generator_type__array__method_probab) - self._arrays[array_handle] = method_probab - return method_probab - - @method_probab.setter - def method_probab(self, method_probab): - self.method_probab[...] = method_probab - + _raffle.f90wrap_raffle_generator_type__array__method_ratio) + self._arrays[array_handle] = method_ratio + return method_ratio + + @method_ratio.setter + def method_ratio(self, method_ratio): + self.method_ratio[...] = method_ratio + def _init_array_structures(self): """ Initialise the structures array. @@ -1824,11 +1847,11 @@ def _init_array_structures(self): _raffle.f90wrap_raffle_generator_type__array_len__structures, """ Element items ftype=type(basis_type) pytype=basis - - + + Defined at ../src/lib/mod_generator.f90 line \ 29 - + """, Geom_Rw.basis) return self.structures @@ -1850,32 +1873,31 @@ def __str__(self): ret.append(repr(self.distributions)) ret.append(',\n max_attempts : ') ret.append(repr(self.max_attempts)) - ret.append(',\n method_probab : ') - ret.append(repr(self.method_probab)) + ret.append(',\n method_ratio : ') + ret.append(repr(self.method_ratio)) ret.append(',\n structures : ') ret.append(repr(self.structures)) ret.append('}') return ''.join(ret) - + _dt_array_initialisers = [_init_array_structures] - - + + _dt_array_initialisers = [] - + generator = Generator() class Raffle(f90wrap.runtime.FortranModule): """ Module raffle - - + + Defined at ../src/raffle.f90 lines 1-4 - + """ pass _dt_array_initialisers = [] - -raffle = Raffle() +raffle = Raffle() diff --git a/src/wrapper/f90wrap_mod_generator.f90 b/src/wrapper/f90wrap_mod_generator.f90 index 689fade8..1a77ef17 100644 --- a/src/wrapper/f90wrap_mod_generator.f90 +++ b/src/wrapper/f90wrap_mod_generator.f90 @@ -584,7 +584,7 @@ end subroutine f90wrap_raffle_generator_type__set__walk_step_size_fine !############################################################################### ! placement method ratio !############################################################################### -subroutine f90wrap_raffle_generator_type__array__method_probab( & +subroutine f90wrap_raffle_generator_type__array__method_ratio( & this, nd, dtype, dshape, dloc & ) use raffle__generator, only: raffle_generator_type @@ -603,9 +603,9 @@ subroutine f90wrap_raffle_generator_type__array__method_probab( & nd = 1 dtype = 11 this_ptr = transfer(this, this_ptr) - dshape(1:1) = shape(this_ptr%p%method_probab) - dloc = loc(this_ptr%p%method_probab) -end subroutine f90wrap_raffle_generator_type__array__method_probab + dshape(1:1) = shape(this_ptr%p%method_ratio) + dloc = loc(this_ptr%p%method_ratio) +end subroutine f90wrap_raffle_generator_type__array__method_ratio !############################################################################### @@ -821,7 +821,9 @@ end subroutine f90wrap_generator__reset_bounds__binding__rgt subroutine f90wrap_generator__generate__binding__rgt( & this, num_structures, stoichiometry, & - method_probab, seed, settings_out_file, verbose) + method_ratio, seed, settings_out_file, verbose, exit_code & +) + use raffle__geom_rw, only: basis_type use raffle__generator, only: raffle_generator_type, stoichiometry_type implicit none @@ -842,20 +844,22 @@ subroutine f90wrap_generator__generate__binding__rgt( & integer, intent(in) :: num_structures type(stoichiometry_type_xnum_array_ptr_type) :: stoichiometry_ptr integer, intent(in), dimension(2) :: stoichiometry - real(4), intent(in), optional, dimension(5) :: method_probab + real(4), intent(in), optional, dimension(5) :: method_ratio character*(*), intent(in), optional :: settings_out_file integer, intent(in), optional :: seed integer, intent(in), optional :: verbose + integer, intent(out), optional :: exit_code this_ptr = transfer(this, this_ptr) stoichiometry_ptr = transfer(stoichiometry, stoichiometry_ptr) call this_ptr%p%generate( & num_structures=num_structures, & stoichiometry=stoichiometry_ptr%p%items, & - method_probab=method_probab, & + method_ratio=method_ratio, & seed=seed, & settings_out_file=settings_out_file, & - verbose=verbose & + verbose=verbose, & + exit_code=exit_code & ) end subroutine f90wrap_generator__generate__binding__rgt diff --git a/test/test_evaluator_BTO.f90 b/test/test_evaluator_BTO.f90 index 73660213..f5988409 100644 --- a/test/test_evaluator_BTO.f90 +++ b/test/test_evaluator_BTO.f90 @@ -164,12 +164,12 @@ program test_evaluator_BTO basis_host%lat(3,:) = [0.0, 0.0, 8.00] ! set up atom_ignore_list - allocate(atom_ignore_list(5,2)) - atom_ignore_list(1,:) = [1, 2] - atom_ignore_list(2,:) = [3, 4] - atom_ignore_list(3,:) = [3, 5] - atom_ignore_list(4,:) = [3, 6] - atom_ignore_list(5,:) = [2, 2] + allocate(atom_ignore_list(2,5)) + atom_ignore_list(:,1) = [1, 2] + atom_ignore_list(:,2) = [3, 4] + atom_ignore_list(:,3) = [3, 5] + atom_ignore_list(:,4) = [3, 6] + atom_ignore_list(:,5) = [2, 2] call basis_host%create_images( & max_bondlength = max_bondlength, & @@ -215,7 +215,7 @@ program test_evaluator_BTO grid_offset = generator%grid_offset & ) do i = 1, 3 - tolerance(i) = 1._real32 / real(generator%grid(i),real32) / 2._real32 + tolerance(i) = 1._real32 / real(generator%grid(i),real32) !/ 2._real32 end do @@ -236,8 +236,8 @@ program test_evaluator_BTO write(unit,fmt) basis_host%spec(:)%name do is = 1, basis_host%nspec atom_loop: do ia = 1, basis_host%spec(is)%num - do i = 1, size(atom_ignore_list,1) - if( all(atom_ignore_list(i,:).eq.[is,ia]) ) cycle atom_loop + do i = 1, size(atom_ignore_list,2) + if( all(atom_ignore_list(:,i).eq.[is,ia]) ) cycle atom_loop end do write(unit,*) basis_host%spec(is)%atom(ia,:3) end do atom_loop @@ -257,29 +257,29 @@ program test_evaluator_BTO ! call evaluator !----------------------------------------------------------------------------- allocate(viability_grid(basis_host%nspec,size(gridpoints,2))) - do ia = 1, size(atom_ignore_list,1) + do ia = 1, size(atom_ignore_list,2) viability_grid(:,:) = 0._real32 do is = 1, basis_host%nspec do i = 1, size(gridpoints,dim=2) viability_grid(is,i) = evaluate_point( generator%distributions, & gridpoints(1:3,i), is, & basis_host, & - atom_ignore_list(ia:,:), & + atom_ignore_list(:,ia:), & [ generator%distributions%bond_info(:)%radius_covalent ] & ) end do end do - best_loc = maxloc(viability_grid(atom_ignore_list(ia,1),:),dim=1) + best_loc = maxloc(viability_grid(atom_ignore_list(1,ia),:),dim=1) ltmp1 = .false. - if(any(viability_grid(atom_ignore_list(ia,1),:) .gt. 0._real32) )then - do ja = ia, size(atom_ignore_list,1), 1 - if( atom_ignore_list(ja,1) .ne. atom_ignore_list(ia,1) ) cycle + if(any(viability_grid(atom_ignore_list(1,ia),:) .gt. 0._real32) )then + do ja = ia, size(atom_ignore_list,2), 1 + if( atom_ignore_list(1,ja) .ne. atom_ignore_list(1,ia) ) cycle if( & all( & abs( & gridpoints(1:3,best_loc) - & - basis_host%spec(atom_ignore_list(ja,1))%atom( & - atom_ignore_list(ja,2),:3 & + basis_host%spec(atom_ignore_list(1,ja))%atom( & + atom_ignore_list(2,ja),:3 & ) & ) .lt. tolerance + 1.E-6_real32 & ) & @@ -292,15 +292,15 @@ program test_evaluator_BTO success & ) if( .not. ltmp1 ) then - write(*,*) "species: ", atom_ignore_list(ia,1) + write(*,*) "species: ", atom_ignore_list(1,ia) write(*,*) "Best location: ", best_loc write(*,*) "viability: ", & - viability_grid(atom_ignore_list(ia,1),best_loc) + viability_grid(atom_ignore_list(1,ia),best_loc) write(*,*) "Gridpoint: ", gridpoints(1:3,best_loc) end if call basis_host%update_images( & max_bondlength = max_bondlength, & - is = atom_ignore_list(ia,1), ia = atom_ignore_list(ia,2) & + is = atom_ignore_list(1,ia), ia = atom_ignore_list(2,ia) & ) end do close(unit) diff --git a/test/test_evaluator_C.f90 b/test/test_evaluator_C.f90 index c46093f8..5b510ae3 100644 --- a/test/test_evaluator_C.f90 +++ b/test/test_evaluator_C.f90 @@ -149,11 +149,11 @@ program test_evaluator basis_host%lat(3,:) = [0.0, 0.0, 7.121490218] ! set up atom_ignore_list - allocate(atom_ignore_list(8,2)) - do i = 1, size(atom_ignore_list,1) - atom_ignore_list(i,1) = 1 - atom_ignore_list(i,2) = & - basis_host%spec(1)%num - size(atom_ignore_list,1) + i + allocate(atom_ignore_list(2,8)) + do i = 1, size(atom_ignore_list,2) + atom_ignore_list(1,i) = 1 + atom_ignore_list(2,i) = & + basis_host%spec(1)%num - size(atom_ignore_list,2) + i end do call basis_host%create_images( & @@ -165,7 +165,7 @@ program test_evaluator generator%distributions%kBT = 0.2 call generator%set_host(basis_host) call generator%set_grid( grid_spacing = 0.2, grid_offset = [0.0, 0.0, 0.0] ) - generator%distributions%radius_distance_tol = [1.5, 2.5, 3.0, 6.0] + generator%distributions%radius_distance_tol = [1.5, 2.5, 3.0, 5.0] call generator%distributions%set_width([0.025, pi/200.0, pi/200.0]) @@ -220,8 +220,8 @@ program test_evaluator write(unit,fmt) basis_host%spec(:)%name do is = 1, basis_host%nspec atom_loop: do ia = 1, basis_host%spec(is)%num - do i = 1, size(atom_ignore_list,1) - if( all(atom_ignore_list(i,:).eq.[is,ia]) ) cycle atom_loop + do i = 1, size(atom_ignore_list,2) + if( all(atom_ignore_list(:,i).eq.[is,ia]) ) cycle atom_loop end do write(unit,*) basis_host%spec(is)%atom(ia,:3) end do atom_loop @@ -241,24 +241,24 @@ program test_evaluator ! call evaluator !----------------------------------------------------------------------------- allocate(viability_grid(basis_host%nspec,size(gridpoints,2))) - do ia = 1, size(atom_ignore_list,1) + do ia = 1, size(atom_ignore_list,2) viability_grid(:,:) = 0._real32 do i = 1, size(gridpoints,dim=2) viability_grid(1,i) = evaluate_point( generator%distributions, & - gridpoints(1:3,i), atom_ignore_list(ia,1), basis_host, & - atom_ignore_list(ia:,:), & + gridpoints(1:3,i), atom_ignore_list(1,ia), basis_host, & + atom_ignore_list(:,ia:), & [ generator%distributions%bond_info(:)%radius_covalent ] & ) end do - best_loc = maxloc(viability_grid(atom_ignore_list(ia,1),:),dim=1) + best_loc = maxloc(viability_grid(atom_ignore_list(1,ia),:),dim=1) ! Check point is correct ltmp1 = .false. - do ja = ia, size(atom_ignore_list,1), 1 + do ja = ia, size(atom_ignore_list,2), 1 if( & all( & abs( & gridpoints(1:3,best_loc) - & - basis_host%spec(1)%atom(atom_ignore_list(ja,2),:3) & + basis_host%spec(1)%atom(atom_ignore_list(2,ja),:3) & ) .lt. tolerance + 1.E-6_real32 & ) & ) ltmp1 = .true. @@ -270,7 +270,7 @@ program test_evaluator ) call basis_host%update_images( & max_bondlength = max_bondlength, & - is = 1, ia = atom_ignore_list(ia,2) & + is = 1, ia = atom_ignore_list(2,ia) & ) end do diff --git a/test/test_generator.f90 b/test/test_generator.f90 index d59be16d..3ab0da96 100644 --- a/test/test_generator.f90 +++ b/test/test_generator.f90 @@ -58,7 +58,7 @@ program test_generator write(*,*) "Testing generator missing host handling" call generator_var%generate( num_structures = 1, & stoichiometry = [ stoichiometry_type(element='C ', num = 8) ], & - method_probab = [0.0, 0.0, 0.0, 0.0, 1.0], & + method_ratio = [0.0, 0.0, 0.0, 0.0, 1.0], & seed = 0, & verbose = 1 & ) @@ -326,7 +326,7 @@ program test_generator !----------------------------------------------------------------------------- call generator%generate( num_structures = 0, & stoichiometry = [ stoichiometry_type(element='C ', num = 8) ], & - method_probab = [0.0, 0.0, 0.0, 0.0, 1.0] & + method_ratio = [0.0, 0.0, 0.0, 0.0, 1.0] & ) !----------------------------------------------------------------------------- @@ -334,7 +334,7 @@ program test_generator !----------------------------------------------------------------------------- call generator%generate( num_structures = 1, & stoichiometry = [ stoichiometry_type(element='C ', num = 8) ], & - method_probab = [0.0, 0.0, 0.0, 0.0, 1.0], & + method_ratio = [0.0, 0.0, 0.0, 0.0, 1.0], & seed = 0, & verbose = 1 & ) @@ -355,7 +355,7 @@ program test_generator !----------------------------------------------------------------------------- call generator%generate( num_structures = 2, & stoichiometry = [ stoichiometry_type(element='C ', num = 12) ], & - method_probab = [0.0, 0.0, 0.0, 0.0, 1.0], & + method_ratio = [0.0, 0.0, 0.0, 0.0, 1.0], & seed = 0, & verbose = 1 & ) diff --git a/test/test_geom_extd.f90 b/test/test_geom_extd.f90 index 831b50fc..f3e4319f 100644 --- a/test/test_geom_extd.f90 +++ b/test/test_geom_extd.f90 @@ -88,10 +88,10 @@ subroutine test_update_iamges(basis, success) logical, intent(inout) :: success type(extended_basis_type) :: basis_copy - integer, dimension(1,2) :: atom_ignore_list + integer, dimension(2,1) :: atom_ignore_list call basis_copy%copy(basis) - atom_ignore_list(1,:) = [1, 1] + atom_ignore_list(:,1) = [1, 1] ! Create images call basis_copy%create_images( & diff --git a/test/test_place_methods.f90 b/test/test_place_methods.f90 index f5d292f4..10987526 100644 --- a/test/test_place_methods.f90 +++ b/test/test_place_methods.f90 @@ -67,12 +67,6 @@ program test_place_methods basis%lat(3,3) = 5.0_real32 - !----------------------------------------------------------------------------- - ! test place_method_void - !----------------------------------------------------------------------------- - call test_place_method_void(basis, success) - - !----------------------------------------------------------------------------- ! set up distribution functions !----------------------------------------------------------------------------- @@ -95,8 +89,8 @@ program test_place_methods call generator%distributions%host_system%set_element_map( & generator%distributions%element_info & ) - allocate(atom_ignore_list(1, 2)) - atom_ignore_list(1,:) = [1,2] + allocate(atom_ignore_list(2,1)) + atom_ignore_list(:,1) = [1,2] seed = 0 call random_seed(size=num_seed) allocate(seed_arr(num_seed)) @@ -109,6 +103,12 @@ program test_place_methods ) + !----------------------------------------------------------------------------- + ! test place_method_void + !----------------------------------------------------------------------------- + call test_place_method_void(generator%distributions, basis, success) + + !----------------------------------------------------------------------------- ! test place_method_rand !----------------------------------------------------------------------------- @@ -199,10 +199,12 @@ program test_place_methods contains - subroutine test_place_method_void(basis, success) + subroutine test_place_method_void(distributions, basis, success) + use raffle__viability, only: get_gridpoints_and_viability implicit none logical, intent(inout) :: success type(basis_type), intent(in) :: basis + type(distribs_container_type), intent(in) :: distributions integer :: i type(extended_basis_type) :: basis_copy @@ -213,21 +215,40 @@ subroutine test_place_method_void(basis, success) integer, dimension(:,:), allocatable :: atom_ignore_list real(real32), dimension(3) :: tolerance real(real32), dimension(2,3) :: bounds + real(real32), dimension(:,:), allocatable :: gridpoints, viability_grid ! Initialise test data grid = [10, 10, 10] bounds(1,:) = 0.0_real32 bounds(2,:) = 1.0_real32 - allocate(atom_ignore_list(1, 2)) ! No atoms to ignore - atom_ignore_list(1,:) = [1,2] + allocate(atom_ignore_list(2,1)) ! No atoms to ignore + atom_ignore_list(:,1) = [1,2] grid_offset = [0.5_real32, 0.5_real32, 0.5_real32] ! Initialise basis call basis_copy%copy(basis) + call basis_copy%create_images( & + max_bondlength = 6._real32, & + atom_ignore_list = atom_ignore_list & + ) + + !--------------------------------------------------------------------------- + ! set up gridpoints + !--------------------------------------------------------------------------- + gridpoints = get_gridpoints_and_viability( & + distributions, & + grid, & + bounds, & + basis_copy, & + [ 1 ], & + [ distributions%bond_info(:)%radius_covalent ], & + atom_ignore_list, & + grid_offset = grid_offset & + ) ! Call the void subroutine point = place_method_void( & - grid, grid_offset, bounds, basis_copy, & + gridpoints, basis_copy, & atom_ignore_list, & viable & ) diff --git a/test/test_viability.f90 b/test/test_viability.f90 index f340ea9c..f49210d4 100644 --- a/test/test_viability.f90 +++ b/test/test_viability.f90 @@ -63,8 +63,8 @@ subroutine test_get_gridpoints_and_viability(basis, success) grid = [10, 10, 10] bounds(1,:) = 0.0_real32 bounds(2,:) = 1.0_real32 - allocate(atom_ignore_list(1, 2)) ! No atoms to ignore - atom_ignore_list(1,:) = [1,2] + allocate(atom_ignore_list(2,1)) ! No atoms to ignore + atom_ignore_list(:,1) = [1,2] allocate(radius_list(1)) radius_list = 1.0_real32 lowtol = 0.5_real32 @@ -133,8 +133,8 @@ subroutine test_update_gridpoints_and_viability(basis, success) grid = [10, 10, 10] bounds(1,:) = 0.0_real32 bounds(2,:) = 1.0_real32 - allocate(atom_ignore_list(1, 2)) ! No atoms to ignore - atom_ignore_list(1,:) = [1,2] + allocate(atom_ignore_list(2,1)) ! No atoms to ignore + atom_ignore_list(:,1) = [1,2] allocate(radius_list(1)) radius_list = 1.0_real32 !!! NO!!! USING CARBON RADIUS lowtol = 0.5_real32 diff --git a/tools/heatmap_2Dcut.ipynb b/tools/heatmap_2Dcut.ipynb index 1a166a28..d9d1f77e 100644 --- a/tools/heatmap_2Dcut.ipynb +++ b/tools/heatmap_2Dcut.ipynb @@ -10,6 +10,7 @@ "from mpl_toolkits.mplot3d.art3d import Poly3DCollection\n", "import numpy as np\n", "import matplotlib.pyplot as plt\n", + "from matplotlib import colors\n", "from scipy.interpolate import griddata\n", "from scipy.spatial import cKDTree\n", "from scipy.ndimage import gaussian_filter\n", @@ -282,25 +283,30 @@ "def plot_2d_slice(slice_level, species, axis):\n", " plt.clf() # Clear the current figure\n", "\n", + " norm = colors.PowerNorm(gamma=0.5)\n", + " plane_label = ''\n", " # Normalize slice level to the grid range\n", " if axis == 'c':\n", " slice_idx = int(slice_level * n_z)\n", " slice_data = grid_values[species-1][:, :, slice_idx]\n", - " plt.imshow(slice_data.T, extent=(x_min, x_max, y_min, y_max), origin='lower', cmap='viridis', aspect='auto')\n", + " plt.imshow(slice_data.T, extent=(x_min, x_max, y_min, y_max), origin='lower', cmap='viridis', norm=norm, aspect='auto')\n", " plt.xlabel('$x$ (\\AA)')\n", " plt.ylabel('$y$ (\\AA)')\n", + " plane_label = '$p_{3}$'\n", " elif axis == 'b':\n", " slice_idx = int(slice_level * n_y)\n", " slice_data = grid_values[species-1][:, slice_idx, :]\n", - " plt.imshow(slice_data.T, extent=(x_min, x_max, z_min, z_max), origin='lower', cmap='viridis', aspect='auto')\n", + " plt.imshow(slice_data.T, extent=(x_min, x_max, z_min, z_max), origin='lower', cmap='viridis', norm=norm, aspect='auto')\n", " plt.xlabel('$x$ (\\AA)')\n", " plt.ylabel('$z$ (\\AA)')\n", + " plane_label = '$p_{4}$'\n", " elif axis == 'a':\n", " slice_idx = int(slice_level * n_x)\n", " slice_data = grid_values[species-1][slice_idx, :, :]\n", - " plt.imshow(slice_data.T, extent=(y_min, y_max, z_min, z_max), origin='lower', cmap='viridis', aspect='auto')\n", + " plt.imshow(slice_data.T, extent=(y_min, y_max, z_min, z_max), origin='lower', cmap='viridis', norm=norm, aspect='auto')\n", " plt.xlabel('$y$ (\\AA)')\n", " plt.ylabel('$z$ (\\AA)')\n", + " plane_label = '$p_{1}$'\n", " elif axis == 'ab':\n", " # get diagonal list of idx\n", " slice_idx_xy = [\n", @@ -316,28 +322,36 @@ " slice_data = grid_values[species-1][slice_idx_x, slice_idx_y, :]\n", " min_loc = 0.0\n", " max_loc = np.sqrt( (len(slice_idx_x) * a / n_x)**2 + (len(slice_idx_y) * b / n_y)**2 )\n", - " plt.imshow(slice_data.T, extent=(min_loc, max_loc, z_min, z_max), origin='lower', cmap='viridis', aspect='auto')\n", + " plt.imshow(slice_data.T, extent=(min_loc, max_loc, z_min, z_max), origin='lower', cmap='viridis', norm=norm, aspect='auto')\n", " plt.xlabel(r'$xy$ (\\AA)')\n", " plt.ylabel('$z$ (\\AA)')\n", + " plane_label = '$p_{2}$'\n", "\n", - " plt.title(f'Slice through ${axis}$ = {slice_level:.2f}', fontsize=20)\n", + " plt.title(f'Plane {plane_label}', fontsize=25, y=1.0, pad=10)\n", " min_val = min(grid_value.min() for grid_value in grid_values)\n", " max_val = max(grid_value.max() for grid_value in grid_values)\n", " plt.clim(min_val, max_val)\n", - " cbar = plt.colorbar(label='Viability')\n", + " cbar = plt.colorbar(label='Viability', orientation='vertical', fraction=0.085, pad=0.02)\n", " ax = plt.gca()\n", - " ax.set_aspect('equal')\n", + " # ax.set_aspect('equal')\n", " # Set tick and label font size\n", - " ax.tick_params(axis='both', which='major', labelsize=16)\n", + " ax.tick_params(axis='both', which='major', labelsize=20)\n", + " \n", + " # Create a custom colormap where zero values are colored grey\n", + " cmap = plt.cm.viridis.copy()\n", + " cmap.set_bad('grey')\n", + " slice_data = np.ma.masked_where(slice_data == 0.0, slice_data)\n", + " plt.imshow(slice_data.T, extent=ax.get_images()[0].get_extent(), origin='lower', cmap=cmap, norm=norm, aspect='auto')\n", + " ax.set_aspect('equal')\n", " \n", - " plt.xlabel(plt.gca().get_xlabel(), fontsize=20)\n", - " plt.ylabel(plt.gca().get_ylabel(), fontsize=20)\n", + " plt.xlabel(plt.gca().get_xlabel(), fontsize=25)\n", + " plt.ylabel(plt.gca().get_ylabel(), fontsize=25)\n", " ax.xaxis.set_major_locator(plt.MaxNLocator(4))\n", " ax.yaxis.set_major_locator(plt.MaxNLocator(4))\n", " ax.xaxis.set_minor_locator(AutoMinorLocator(2))\n", " ax.yaxis.set_minor_locator(AutoMinorLocator(2))\n", - " cbar.ax.tick_params(labelsize=16)\n", - " cbar.set_label(r'$P_{'+species_name_list[species-1]+r'}$', fontsize=20)\n", + " cbar.ax.tick_params(labelsize=20)\n", + " cbar.set_label(r'$P_{\\mathrm{'+species_name_list[species-1]+r'}}$', fontsize=25)\n", " # cbar.set_ticks(np.linspace(min_val, max_val, 4))\n", " cbar.ax.yaxis.set_major_locator(plt.MaxNLocator(nbins=4))\n", " cbar.ax.minorticks_on()\n" @@ -390,11 +404,18 @@ "interactive_plot_2d = interactive(plot_2d_slice, slice_level=slice_slider_2d, axis=axis_selector_2d, species=species_selector_2d)\n", "interactive_plot_2d" ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [] } ], "metadata": { "kernelspec": { - "display_name": "py3.11", + "display_name": "raffle_env", "language": "python", "name": "python3" }, @@ -408,7 +429,7 @@ "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", - "version": "3.11.8" + "version": "3.12.8" } }, "nbformat": 4, diff --git a/tools/version_number.py b/tools/version_number.py index ef527028..79fdf6a7 100644 --- a/tools/version_number.py +++ b/tools/version_number.py @@ -4,14 +4,14 @@ def update_version(new_version): # Update fpm.toml with open('fpm.toml', 'r') as file: content = file.read() - content = re.sub(r'version = "\d+\.\d+\.\d+"', f'version = "{new_version}"', content) + content = re.sub(r'version = "\d+\.\d+\.\d+.*"', f'version = "{new_version}"', content) with open('fpm.toml', 'w') as file: file.write(content) # Update Fortran module with open('src/fortran/lib/mod_io_utils.F90', 'r') as file: content = file.read() - content = re.sub(r'character\(len=\*\), parameter :: raffle__version__ = "\d+\.\d+\.\d+"', f'character(len=*), parameter :: raffle__version__ = "{new_version}"', content) + content = re.sub(r'character\(len=\*\), parameter :: raffle__version__ = "\d+\.\d+\.\d+.*"', f'character(len=*), parameter :: raffle__version__ = "{new_version}"', content) with open('src/fortran/lib/mod_io_utils.F90', 'w') as file: file.write(content) @@ -19,7 +19,8 @@ def get_version(): # get the version number from fpm.toml with open('fpm.toml', 'r') as file: content = file.read() - match = re.search(r'version = "(\d+\.\d+\.\d+)"', content) + match = re.search(r'version = "(\d+\.\d+\.\d+.*)"', content) + print(match.group(1)) if match: return match.group(1)