Source code for topostats.statistics

"""Function for calculating statistics about a whole image, for example number of grains or surface roughness."""

import logging

import numpy as np
import numpy.typing as npt

from topostats.logs.logs import LOGGER_NAME

LOGGER = logging.getLogger(LOGGER_NAME)


[docs] def image_statistics( image: npt.NDArray, filename: str, pixel_to_nm_scaling: float, n_grains: int ) -> dict[str, int | str | float]: """ Calculate statistics pertaining to the whole image. Calculates the size of the image in pixels and metres, the root-mean-squared roughness and the grains per metre squared. Parameters ---------- image : np.ndarray Numpy 2D image array of the image to calculate stats for. filename : str The name of the file being processed. pixel_to_nm_scaling : float Float of the scaling factor between pixels and nanometres. n_grains : int Number of grains in image. Returns ------- dict[str, int | str | float] Dictionary of image statistics. """ image_stats = { "image": filename, "image_size_x_m": image.shape[1] * pixel_to_nm_scaling * 1e-9, "image_size_y_m": image.shape[0] * pixel_to_nm_scaling * 1e-9, "image_area_m2": None, "image_size_x_px": image.shape[1], "image_size_y_px": image.shape[0], "image_area_px2": None, "grains": n_grains, "grains_per_m2": None, "rms_roughness": None, } # Calculate areas image_stats["image_area_m2"] = image_stats["image_size_x_m"] * image_stats["image_size_y_m"] image_stats["image_area_px2"] = image_stats["image_size_x_px"] * image_stats["image_size_y_px"] # Calculate the RMS roughness of the sample on the flattened image. image_stats["rms_roughness"] = roughness_rms(image=image) * 1e-9 # ns-rse 2025-12-19 Need to reconcile grain density per threshold level, challenging as conceivably there could be > # 2 image_stats["grains_per_m2"] = image_stats["grains"] / image_stats["image_area_m2"] return image_stats
[docs] def roughness_rms(image: np.ndarray) -> float: """ Calculate the root-mean-square roughness of a heightmap image. Parameters ---------- image : np.ndarray 2-D numpy array of heightmap data to calculate roughness. Returns ------- float The RMS roughness of the input array. """ return np.sqrt(np.mean(np.square(image)))