Skip to content

Commit

Permalink
unfinished update
Browse files Browse the repository at this point in the history
  • Loading branch information
shoubhikraj committed Jan 22, 2025
1 parent b37e265 commit f796974
Show file tree
Hide file tree
Showing 5 changed files with 106 additions and 40 deletions.
70 changes: 68 additions & 2 deletions autode/ext/ade_idpp.pyx
Original file line number Diff line number Diff line change
Expand Up @@ -34,11 +34,15 @@ cdef IdppParams handle_kwargs(kwargs):
cdef IdppParams calc_params
calc_params.k_spr = kwargs.get('k_spr', 1.0)
calc_params.sequential = kwargs.get('sequential', True)
calc_params.debug = kwargs.get('debug', False)
calc_params.rmsgtol = kwargs.get('rms_gtol', 2e-3)
calc_params.maxiter = kwargs.get('maxiter', 1000)
calc_params.add_img_maxgtol = kwargs.get('add_img_maxgtol', 0.005)
calc_params.add_img_maxiter = kwargs.get('add_img_maxiter', 30)

# change the debug option according to current logging level
debug_print = logger.isEnabledFor(logging.DEBUG)
calc_params.debug = debug_print

return calc_params


Expand Down Expand Up @@ -75,7 +79,6 @@ def get_interpolated_path(
if init_coords.shape != final_coords.shape:
raise ValueError("Coordinates must have the same shape")


# access raw memory block of the arrays
init_coords = np.ascontiguousarray(
init_coords.ravel(), dtype=np.double
Expand All @@ -95,6 +98,69 @@ def get_interpolated_path(
cdef double [:] img_coords_view = interm_img_coordinates
cdef IdppParams params = handle_kwargs(kwargs)

calculate_idpp_path(
&init_view[0],
&final_view[0],
int(coords_len),
n_images,
&img_coords_view[0],
params,
)
return interm_img_coordinates

def get_interp_path_length(
init_coords,
final_coords,
n_images: int,
**kwargs,
):
"""
Obtain the length of the interpolated path (using the IDPP method) from
the coordinates of the reactant and product states
Args:
init_coords (np.ndarray): Initial coordinates
final_coords (np.ndarray): Final coordinates
n_images (int): Number of images requested
Keyword Args:
sequential (bool): Whether to use the sequential IDPP
k_spr (float): The spring constant value
rms_gtol (float): The RMS gradient tolerance for the path
maxiter (int): Maximum number of iters for path
add_img_maxgtol (float): Max. gradient tolerance for adding
new images (only for sequential)
add_img_maxiter (int): Max. number of iters for adding new
images (only for sequential)
Returns:
(float): Length of the interpolated path
"""
if init_coords.shape != final_coords.shape:
raise ValueError("Coordinates must have the same shape")

# access raw memory block of the arrays
init_coords = np.ascontiguousarray(
init_coords.ravel(), dtype=np.double
)
final_coords = np.ascontiguousarray(
final_coords.ravel(), dtype=np.double
)
cdef double [:] init_view = init_coords
cdef double [:] final_view = final_coords
coords_len = init_coords.shape[0]

cdef IdppParams params = handle_kwargs(kwargs)

return get_path_length(
&init_view[0],
&final_view[0],
int(coords_len),
n_images,
params,
)


class IDPP:
def __init__(
self,
Expand Down
4 changes: 2 additions & 2 deletions autode/ext/include/idpp.h
Original file line number Diff line number Diff line change
Expand Up @@ -153,13 +153,13 @@ namespace autode
int coords_len,
int n_images,
double* all_coords_ptr,
IdppParams params);
const IdppParams& params);

double get_path_length(double* init_coords_ptr,
double* final_coords_ptr,
int coords_len,
int n_images,
IdppParams params);
const IdppParams& params);
}

#endif // ADE_EXT_IDPP_H
4 changes: 2 additions & 2 deletions autode/ext/src/idpp.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -707,7 +707,7 @@ namespace autode {
int coords_len,
int n_images,
double* all_coords_ptr,
IdppParams params) {
const IdppParams& params) {
/* Calculate the IDPP path from initial to final coordinates. This takes
* in the coordinates as pointers to the beginning of numpy arrays, and
* therefore must be provided contiguous arrays. Additionally, the
Expand Down Expand Up @@ -782,7 +782,7 @@ namespace autode {
double *final_coords_ptr,
int coords_len,
int n_images,
IdppParams params) {
const IdppParams& params) {
/* Calculate the path length for the IDPP path from the initial to
* final set of coordinates. Takes in pointer arrays (from numpy
* buffers) and returns the cumulative sum length.
Expand Down
4 changes: 2 additions & 2 deletions autode/ext/wrappers.pxd
Original file line number Diff line number Diff line change
Expand Up @@ -111,11 +111,11 @@ cdef extern from "include/idpp.h" namespace "autode":
int coords_len,
int n_images,
double* all_coords_ptr,
IdppParams params) except +
const IdppParams & params) except +

cdef extern from "include/idpp.h" namespace "autode":
double get_path_length(double *init_coords_ptr,
double *final_coords_ptr,
int coords_len,
int n_images,
IdppParams params) except +
const IdppParams & params) except +
64 changes: 32 additions & 32 deletions autode/neb/idpp.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
from autode.log import logger
import logging
from autode.values import PotentialEnergy
from ade_idpp import get_interpolated_path, get_interp_path_length

if TYPE_CHECKING:
from autode.neb.original import Image, Images
Expand All @@ -25,12 +26,14 @@ class IDPP:
"""

def __init__(
self,
n_images: int,
sequential: bool = True,
k_spr: float = 1.0,
rms_gtol: float = 2e-3,
maxiter: int = 1000,
self,
n_images: int,
sequential: bool = True,
k_spr: float = 1.0,
rms_gtol: float = 2e-3,
maxiter: int = 1000,
add_img_maxgtol: float = 2e-3,
add_img_maxiter: int = 30,
):
"""
Initialise an IDPP calculation
Expand All @@ -40,7 +43,9 @@ def __init__(
k_spr: The spring constant
sequential: Whether to use sequential IDPP
rms_gtol: RMS gradient tolerance for path
maxiter: Maximum number of LBFGS iterations
maxiter: Maximum number of iterations for path
add_img_maxgtol: Maximum gradient tolerance for adding images
add_img_maxiter: Maximum number of iterations for adding images
"""
assert n_images > 2, "Must have more than 2 images"
self._n_images = int(n_images)
Expand All @@ -51,11 +56,18 @@ def __init__(
self._rms_gtol = float(rms_gtol)
assert maxiter > 0, "Maximum iterations must be positive"
self._maxiter = int(maxiter)
assert (
add_img_maxgtol > 0
), "Add image gradient tolerance must be positive"
self._add_img_maxgtol = float(add_img_maxgtol)
assert (
add_img_maxiter > 0
), "Add image maximum iterations must be positive"
self._add_img_maxiter = int(add_img_maxiter)
# TODO: make default arguments simpler and allow None

def get_path(
self,
init_coords: np.ndarray,
final_coords: np.ndarray
self, init_coords: np.ndarray, final_coords: np.ndarray
) -> np.ndarray:
"""
Get the IDPP path between the intial and final coordinates
Expand All @@ -68,31 +80,19 @@ def get_path(
(np.ndarray): Numpy array of coordinates of the
intermediate images in the path
"""

#cdef double [:] init_view = init_coords
#cdef double [:] final_view = final_coords

if init_coords.shape != final_coords.shape:
raise ValueError(
"Initial and final coordinates must have the same shape"
)
coords_len = init_coords.shape[0]
assert coords_len % 3 == 0, "Coordinate array has incorrect dimensions"
img_coordinates = np.zeros(
shape=((self._n_images - 2) * coords_len,),
order="C",
dtype=np.double
)
#cdef double [:] img_coords_view = img_coordinates

debug_print = logger.isEnabledFor(logging.DEBUG)
# TODO: send this to cython function
# access raw memory block of the arrays
init_coords = np.ascontiguousarray(
init_coords.ravel(), dtype=np.double
)
final_coords = np.ascontiguousarray(
final_coords.ravel(), dtype=np.double
return get_interpolated_path(
init_coords,
final_coords,
self._n_images,
sequential=self._sequential,
k_spr=self._k_spr,
rms_gtol=self._rms_gtol,
maxiter=self._maxiter,
add_img_maxgtol=self._add_img_maxgtol,
add_img_maxiter=self._add_img_maxiter,
)

return img_coordinates

0 comments on commit f796974

Please sign in to comment.