Skip to content
Snippets Groups Projects
Commit d248dd95 authored by Marcin Kirsz's avatar Marcin Kirsz
Browse files

Merge branch 'develop' into 'main'

Develop

See merge request !16
parents 0b685b81 bc35f1ef
Branches
Tags
1 merge request!16Develop
Pipeline #50276 passed
Pipeline: Tadah.MLIP

#50280

    ......@@ -46,4 +46,5 @@ build_release_static:
    trigger_job:
    stage: trigger
    trigger:
    project: tadah/tadah.mlip
    \ No newline at end of file
    project: tadah/tadah.mlip
    branch: $CI_COMMIT_REF_NAME
    \ No newline at end of file
    ......@@ -15,11 +15,11 @@ public:
    /**
    * @brief Factory method to create specific DatasetReader objects.
    *
    * @param type The type of the dataset reader to create.
    * @param filepath File path to check the content.
    * @param db Reference to a StructureDB object to store parsed data.
    * @return A unique pointer to a DatasetReader object.
    */
    static std::unique_ptr<DatasetReader> get_reader(const std::string& type, StructureDB& db);
    static std::unique_ptr<DatasetReader> get_reader(const std::string& filepath, StructureDB& db);
    /**
    * @brief Determines the file type based on its content.
    ......
    #ifndef CASTEP_CELL_WRITER_H
    #define CASTEP_CELL_WRITER_H
    #include <tadah/mlip/structure.h>
    #include <tadah/mlip/structure_db.h>
    #include <tadah/mlip/dataset_writers/dataset_writer.h>
    #include <iostream>
    #include <fstream>
    #include <sstream>
    #include <vector>
    #include <stdexcept>
    class CastepCellWriter : public DatasetWriter {
    public:
    CastepCellWriter(StructureDB& db);
    virtual void write_data(const std::string& filename, const size_t i) override;
    };
    #endif // CASTEP_CELL_WRITER_H
    #ifndef DATASET_WRITER_H
    #define DATASET_WRITER_H
    #include <tadah/mlip/structure_db.h>
    #include <string>
    #include <vector>
    class DatasetWriter {
    public:
    virtual ~DatasetWriter() = default;
    virtual void write_data(const std::string& filename, const size_t i) = 0;
    DatasetWriter(StructureDB& db) : stdb(db) {};
    virtual void set_precision(const size_t _p) { p = _p; w = p+6; };
    protected:
    StructureDB& stdb;
    double p = 10; // output precision
    double w = p+6; // column width
    };
    #endif // DATASET_WRITER_H
    #ifndef DATASET_WRITER_SELECTOR_H
    #define DATASET_WRITER_SELECTOR_H
    #include <tadah/mlip/structure_db.h>
    #include <tadah/mlip/dataset_writers/dataset_writer.h>
    #include <string>
    #include <memory>
    class DatasetWriterSelector {
    public:
    static std::unique_ptr<DatasetWriter> get_writer(const std::string& type, StructureDB& db);
    };
    #endif // DATASET_WRITER_SELECTOR_H
    #ifndef LAMMPS_STRUCTURE_WRITER_H
    #define LAMMPS_STRUCTURE_WRITER_H
    #include <tadah/mlip/structure.h>
    #include <tadah/mlip/structure_db.h>
    #include <tadah/mlip/dataset_writers/dataset_writer.h>
    #include <iostream>
    #include <fstream>
    #include <sstream>
    #include <vector>
    #include <stdexcept>
    class LammpsStructureWriter : public DatasetWriter {
    public:
    LammpsStructureWriter(StructureDB& db);
    virtual void write_data(const std::string& filename, const size_t i) override;
    };
    #endif // LAMMPS_STRUCTURE_WRITER_H
    #ifndef VASP_POSCAR_WRITER_H
    #define VASP_POSCAR_WRITER_H
    #include <tadah/mlip/structure.h>
    #include <tadah/mlip/structure_db.h>
    #include <tadah/mlip/dataset_writers/dataset_writer.h>
    #include <iostream>
    #include <fstream>
    #include <sstream>
    #include <vector>
    #include <stdexcept>
    class VaspPoscarWriter : public DatasetWriter {
    public:
    VaspPoscarWriter(StructureDB& db);
    virtual void write_data(const std::string& filename, const size_t i) override;
    };
    #endif // VASP_POSCAR_WRITER_H
    #include <tadah/mlip/structure.h>
    #include <tadah/mlip/structure_db.h>
    #include <tadah/mlip/dataset_writers/castep_cell_writer.h>
    CastepCellWriter::CastepCellWriter(StructureDB& db) : DatasetWriter(db) {}
    void CastepCellWriter::write_data(const std::string& filename, const size_t i) {
    if (i >= stdb.size()) {
    throw std::out_of_range("Index i is out of range.");
    }
    std::ofstream file(filename);
    if (!file.is_open()) {
    throw std::runtime_error("Could not open the file: " + filename);
    }
    const Structure &st = stdb(i);
    // write label
    file << "# " << st.label << std::endl;
    // write cell
    file << "%BLOCK LATTICE_CART" << std::endl;
    file << "ANG" << std::endl;
    for (int i=0; i<3; ++i) {
    file << std::right << std::fixed << std::setw(w)
    << std::setprecision(p) << st.cell(i,0);
    file << std::right << std::fixed << std::setw(w)
    << std::setprecision(p) << st.cell(i,1);
    file << std::right << std::fixed << std::setw(w)
    << std::setprecision(p) << st.cell(i,2);
    file << std::endl;
    }
    file << "%ENDBLOCK LATTICE_CART" << std::endl;
    file << std::endl;
    file << "%BLOCK POSITIONS_ABS" << std::endl;
    for (const auto &atom : st) {
    file << std::right << std::fixed << std::setw(w)
    << atom.symbol;
    file << std::right << std::fixed << std::setw(w)
    << std::setprecision(p) << atom.position(0);
    file << std::right << std::fixed << std::setw(w)
    << std::setprecision(p) << atom.position(1);
    file << std::right << std::fixed << std::setw(w)
    << std::setprecision(p) << atom.position(2);
    file << std::endl;
    }
    file << "%ENDBLOCK POSITIONS_ABS " << std::endl;
    file.close();
    }
    #include <tadah/mlip/dataset_writers/dataset_writer_selector.h>
    #include <tadah/mlip/dataset_writers/castep_cell_writer.h>
    #include <tadah/mlip/dataset_writers/vasp_poscar_writer.h>
    #include <tadah/mlip/dataset_writers/lammps_structure_writer.h>
    // Factory method implementation
    std::unique_ptr<DatasetWriter> DatasetWriterSelector::get_writer(const std::string& type, StructureDB& db) {
    if (type == "CASTEP") {
    return std::make_unique<CastepCellWriter>(db);
    } else if (type == "VASP") {
    return std::make_unique<VaspPoscarWriter>(db);
    } else if (type == "LAMMPS") {
    return std::make_unique<LammpsStructureWriter>(db);
    } else {
    std::cerr << "Unknown type! Returning nullptr." << std::endl;
    return nullptr;
    }
    }
    #include <tadah/mlip/structure.h>
    #include <tadah/mlip/structure_db.h>
    #include <tadah/mlip/dataset_writers/lammps_structure_writer.h>
    LammpsStructureWriter::LammpsStructureWriter(StructureDB& db) : DatasetWriter(db) {}
    void LammpsStructureWriter::write_data(const std::string& filename, const size_t i) {
    if (i >= stdb.size()) {
    throw std::out_of_range("Index i is out of range.");
    }
    std::ofstream file(filename);
    if (!file.is_open()) {
    throw std::runtime_error("Could not open the file: " + filename);
    }
    const Structure &st = stdb(i);
    // compute number of atoms for a given element
    const auto &elements = st.get_unique_elements();
    std::map<std::string, size_t> nelements;
    std::map<std::string, size_t> type;
    // Initialize the count for each element
    for (const auto& element : elements) {
    nelements[element.symbol] = 0;
    }
    // then count...
    size_t t=0;
    for (const auto &atom : st) {
    nelements[atom.symbol]++;
    if (type.find(atom.symbol) == type.end()) {
    type[atom.symbol] = ++t;
    }
    }
    // BEGIN OF LAMMPS HEADER
    file << st.label << std::endl;
    file << std::endl;
    file << st.natoms() << " atoms" << std::endl;
    file << nelements.size() << " atom types" << std::endl;
    file << std::endl;
    // General triclinic box format
    std::vector<std::string> abcvec = {"avec", "bvec", "cvec"};
    for (int i=0; i<3; ++i) {
    file << std::right << std::fixed << std::setw(w)
    << std::setprecision(p) << st.cell(i,0);
    file << std::right << std::fixed << std::setw(w)
    << std::setprecision(p) << st.cell(i,1);
    file << std::right << std::fixed << std::setw(w)
    << std::setprecision(p) << st.cell(i,2)
    << " " << abcvec[i];
    file << std::endl;
    }
    file << " 0.0 0.0 0.0 abc origin" << std::endl;
    // END LAMMPS HEADER
    // BEGIN LAMMPS BODY
    file << std::endl;
    file << "Masses" << std::endl;
    file << std::endl;
    for (const auto &t: type) {
    file << t.second << " " << PeriodicTable::get_mass(t.first) << " # " << t.first << std::endl;
    }
    file << std::endl;
    file << "Atoms # atomic" << std::endl;
    file << std::endl;
    // atomic: atom-ID [int, 1-Natoms] atom-type [int, 1-Ntype] x y z
    size_t idx=1;
    for (const auto &atom : st) {
    file << std::right << std::fixed << std::setw(w) << idx;
    file << std::right << std::fixed << std::setw(w) << type[atom.symbol];
    file << std::right << std::fixed << std::setw(w)
    << std::setprecision(p) << atom.position(0);
    file << std::right << std::fixed << std::setw(w)
    << std::setprecision(p) << atom.position(1);
    file << std::right << std::fixed << std::setw(w)
    << std::setprecision(p) << atom.position(2);
    file << std::endl;
    idx++;
    }
    // END LAMMPS BODY
    file.close();
    }
    #include <tadah/mlip/structure.h>
    #include <tadah/mlip/structure_db.h>
    #include <tadah/mlip/dataset_writers/vasp_poscar_writer.h>
    #include <fstream>
    VaspPoscarWriter::VaspPoscarWriter(StructureDB& db) : DatasetWriter(db) {}
    void VaspPoscarWriter::write_data(const std::string& filename, const size_t i) {
    if (i >= stdb.size()) {
    throw std::out_of_range("Index i is out of range.");
    }
    std::ofstream file(filename);
    if (!file.is_open()) {
    throw std::runtime_error("Could not open the file: " + filename);
    }
    const Structure &st = stdb(i);
    // write scaling factor
    file << st.label << std::endl;
    file << "1.0" << std::endl;
    // write cell
    for (int i=0; i<3; ++i) {
    file << std::right << std::fixed << std::setw(w)
    << std::setprecision(p) << st.cell(i,0);
    file << std::right << std::fixed << std::setw(w)
    << std::setprecision(p) << st.cell(i,1);
    file << std::right << std::fixed << std::setw(w)
    << std::setprecision(p) << st.cell(i,2);
    file << std::endl;
    }
    // compute number of atoms for a given element
    const auto &elements = st.get_unique_elements();
    std::map<std::string, size_t> nelements;
    // Initialize the count for each element
    for (const auto& element : elements) {
    nelements[element.symbol] = 0;
    }
    // then count...
    for (const auto &atom : st) {
    nelements[atom.symbol]++;
    }
    // write elements
    for (const auto& pair: nelements) {
    file << pair.first << " ";
    }
    file << std::endl;
    // write number of every elements
    for (const auto& pair: nelements) {
    file << pair.second << " ";
    }
    file << std::endl;
    file << "Cartesian" << std::endl;
    for (const auto& pair: nelements) {
    for (const auto &atom : st) {
    if (pair.first == atom.symbol) {
    file << std::right << std::fixed << std::setw(w)
    << std::setprecision(p) << atom.position(0);
    file << std::right << std::fixed << std::setw(w)
    << std::setprecision(p) << atom.position(1);
    file << std::right << std::fixed << std::setw(w)
    << std::setprecision(p) << atom.position(2);
    file << std::endl;
    }
    }
    }
    file.close();
    }
    0% Loading or .
    You are about to add 0 people to the discussion. Proceed with caution.
    Please register or to comment