import numpy as np
[docs]
class OptimizationStep:
"""Each instantiation of this class corresponds to a step in the optimization process.
Attributes
----------
structure: riigid.Structure
The initial structure of the optimization step
forces_on_atoms: numpy.ndarray of shape (n_atoms_in_structure, 3)
Forces acting on structure.atoms; [eV/Å]
energy: number
The energy of structure; [eV]
update_structure: riigid.Structure
The updated structure (generated by letting the forces act on structure)
forces_allowed, forces_raw: each a list of numpy.ndarrays of shape (3,)
Allowed (after restrictions) and raw force on each fragment in self.structure; [eV/Å]
torques_allowed, torques_raw: each a list of numpy.ndarrays of shape (3,)
Allowed (after restrictions) and raw torque on each fragment in self.structure; [eV]
Note
----
The stored forces and torques and the energy belong to "structure", not to
"updated_structure".
"""
def __init__(self, structure, forces_on_atoms, energy, updated_structure=None):
"""Initialize the optimization step.
Parameters
----------
structure: riigid.Structure
The initial structure of the optimization step
forces_on_atoms: numpy.ndarray of shape (n_atoms_in_structure, 3)
Forces acting on structure.atoms; [eV/Å]
energy: number
The energy of structure; [eV]
update_structure: riigid.Structure
The updated structure (generated by letting the forces act on structure)
"""
self.structure = structure
self.forces_on_atoms = forces_on_atoms
self.energy = energy
self.updated_structure = updated_structure
# Calculate force and torque on fragments
self.add_force_and_torque_on_fragments()
[docs]
def add_force_and_torque_on_fragments(self):
"""Calculate force and torque on fragments of self.structure."""
self.forces_allowed = []
self.forces_raw = []
self.torques_allowed = []
self.torques_raw = []
for fragment in self.structure.fragments:
force1, force2 = fragment.calculate_net_force_on_fragment(
forces_structure=self.forces_on_atoms
)
torque1, torque2 = fragment.calculate_torque_on_fragment(
forces_structure=self.forces_on_atoms
)
self.forces_allowed.append(force1)
self.forces_raw.append(force2)
self.torques_allowed.append(torque1)
self.torques_raw.append(torque2)
[docs]
def add_updated_structure(self, updated_structure):
"""Add/change the updated structure of the optimization step.
Parameters
----------
update_structure: riigid.Structure
The updated structure (generated by letting the forces act on structure)
"""
self.updated_structure = updated_structure
[docs]
def remove_updated_structure(self):
"""Remove the updated structure from the optimization step."""
self.updated_structure = None