Fractal Dimensions

Functions for calculating fractal dimensions of objects and object ensembles.

objscale.individual_fractal_dimension(arrays: ~numpy.ndarray[tuple[int, ...], ~numpy.dtype[~numpy._typing._array_like._ScalarType_co]] | list[~numpy.ndarray[tuple[int, ...], ~numpy.dtype[~numpy._typing._array_like._ScalarType_co]]], x_sizes: ~numpy.ndarray[tuple[int, ...], ~numpy.dtype[~numpy._typing._array_like._ScalarType_co]] | list[~numpy.ndarray[tuple[int, ...], ~numpy.dtype[~numpy._typing._array_like._ScalarType_co]]] | None = None, y_sizes: ~numpy.ndarray[tuple[int, ...], ~numpy.dtype[~numpy._typing._array_like._ScalarType_co]] | list[~numpy.ndarray[tuple[int, ...], ~numpy.dtype[~numpy._typing._array_like._ScalarType_co]]] | None = None, min_length_scale: float = <object object>, max_length_scale: float = <object object>, bins: int | None = 30, return_values: bool = False, method: str = <object object>, filled: bool = <object object>, min_a: float = <object object>, max_a: float = <object object>) tuple[float, float] | tuple[float, float, ndarray[tuple[int, ...], dtype[_ScalarType_co]], ndarray[tuple[int, ...], dtype[_ScalarType_co]]][source]

Calculate the individual fractal dimension Df of objects within arrays.

The method uses linear regression on log(length scale) vs. log(perimeter), omitting structures touching the array edge.

Parameters:
  • arrays (list of np.ndarray) – List of boolean 2D arrays.

  • x_sizes (np.ndarray or list, optional) – Pixel sizes in the x direction. If None, assume all pixel dimensions are 1. If np.ndarray, use these for each array in ‘arrays’. If list, assume x_sizes[i] corresponds to arrays[i].

  • y_sizes (np.ndarray or list, optional) – Pixel sizes in the y direction. If None, assume all pixel dimensions are 1. If np.ndarray, use these for each array in ‘arrays’. If list, assume y_sizes[i] corresponds to arrays[i].

  • min_length_scale (float, default=3) – Minimum length scale to include. Filters on the x-axis quantity: sqrt(area) for area methods, width or height for those methods.

  • max_length_scale (float, default=np.inf) – Maximum length scale to include.

  • bins (int or None, default=30) – Number of bins along the log10 length scale for averaging. The regression is performed on the bin-averaged values. If None, fit on all individual points without binning.

  • return_values (bool, default=False) – If True, return additional data used in the calculation.

  • method (str, default='filled perimeter vs filled area') –

    Which perimeter and length-scale combination to use. Options:

    • 'filled perimeter vs filled area': fill holes, regress log(perimeter) vs log(sqrt(area)). Default.

    • 'summed perimeter vs unfilled area': no hole filling, perimeter includes inner boundaries, area excludes holes.

    • 'filled perimeter vs width': fill holes, regress log(perimeter) vs log(bounding-box width).

    • 'filled perimeter vs height': fill holes, regress log(perimeter) vs log(bounding-box height).

    • 'summed perimeter vs width': no hole filling, regress log(perimeter) vs log(bounding-box width).

    • 'summed perimeter vs height': no hole filling, regress log(perimeter) vs log(bounding-box height).

  • filled (bool, optional) –

    Deprecated since version Use: method instead. filled=True maps to 'filled perimeter vs filled area'; filled=False maps to 'summed perimeter vs unfilled area'.

  • min_a (float, optional) –

    Deprecated since version Use: min_length_scale instead. Converted via sqrt(min_a).

  • max_a (float, optional) –

    Deprecated since version Use: max_length_scale instead. Converted via sqrt(max_a).

Returns:

  • Df (float) – The individual fractal dimension.

  • uncertainty (float) – Uncertainty estimate (95% confidence).

  • log10_length_scale (np.ndarray, optional) – Log10 of the length-scale values (bin centers if bins is not None). Only returned if return_values=True.

  • log10_p (np.ndarray, optional) – Log10 of perimeter values (bin means if bins is not None). Only returned if return_values=True.

Raises:

ValueError – If array shapes don’t match pixel size shapes, if an invalid method is given, or if deprecated and new parameters are mixed.

objscale.ensemble_correlation_dimension(arrays: ndarray[tuple[int, ...], dtype[_ScalarType_co]] | list[ndarray[tuple[int, ...], dtype[_ScalarType_co]]], x_sizes: ndarray[tuple[int, ...], dtype[_ScalarType_co]] | None = None, y_sizes: ndarray[tuple[int, ...], dtype[_ScalarType_co]] | None = None, minlength: str | float = 'auto', maxlength: str | float = 'auto', interior_circles_only: bool = False, return_C_l: bool = False, bins: ndarray[tuple[int, ...], dtype[_ScalarType_co]] | int | None = None, point_reduction_factor: float = 1, nbins: int = 50) tuple[float, float] | tuple[float, float, ndarray[tuple[int, ...], dtype[_ScalarType_co]], ndarray[tuple[int, ...], dtype[_ScalarType_co]]][source]

Calculate the correlation dimension D where C_l ∝ l^D for binary arrays.

The resulting dimension is for the set of object edge points.

This function is a thin wrapper around ensemble_sandbox_renyi_dimension() at q=2: the Grassberger-Procaccia correlation integral is exactly the q=2 case of the sandbox partition function (M_i^{q-1} = M_i and sum_i M_i is the pair count). The function is preserved under its historical name because Grassberger-Procaccia is the standard designation for the q=2 correlation dimension. For arbitrary q, call ensemble_sandbox_renyi_dimension() directly.

Parameters:
  • arrays (list or np.ndarray) – List of binary arrays to calculate correlation dimension of.

  • x_sizes (np.ndarray, optional) – Pixel sizes in the x direction. If None, assume all pixel dimensions are 1. This single grid is used for every array in arrays.

  • y_sizes (np.ndarray, optional) – Pixel sizes in the y direction. If None, assume all pixel dimensions are 1. This single grid is used for every array in arrays.

  • minlength (str or float, default='auto') – Minimum length scale for correlation calculation. If ‘auto’, uses 8 times the minimum pixel size.

  • maxlength (str or float, default='auto') – Maximum length scale for correlation calculation. If ‘auto’, uses 0.33 times the minimum array dimension.

  • interior_circles_only (bool, default=False) – If True, only use circle centers that are at least maxlength distance from all array edges to avoid boundary effects. Defaults to False; see the section “Correlation dimension and domain boundary effects” at https://thomasddewitt.com/thought-cloud/too-many-exponents/index.html for the rationale.

  • return_C_l (bool, default=False) – If True, return dimension, error, bins, C_l. Otherwise, return dimension, error.

  • bins (None, int, or array-like, optional) –

    Values of l to use for the regression. Can be: - None: automatically calculate as logarithmically spaced intervals between

    3*minimum length and the array width or height using nbins points

    • int: number of logarithmically spaced bins to generate automatically

    • array-like: explicit bin edges to use

  • point_reduction_factor (float, default=1) – Draw N/point_reduction_factor circles, where N is the total number of available circles. Choose the circle centers randomly. Must be >= 1.

  • nbins (int, default=50) – Number of bins to use when bins=None or when bins is an int. Only used for automatic bin generation.

Returns:

  • dimension (float) – The correlation dimension.

  • error (float) – Error estimate for the dimension (95% CI half-width).

  • bins (np.ndarray, optional) – The bins used for calculation. Only returned if return_C_l=True.

  • C_l (np.ndarray, optional) – The correlation integral values (= sandbox Z_{q=2} = sum_i M_i). Only returned if return_C_l=True.

Raises:

ValueError – If arrays contain NaN values, if pixel sizes are invalid, or if scale range is insufficient.

See also

ensemble_sandbox_renyi_dimension

The general sandbox-method Rényi family for arbitrary q. This function is the q=2 case.

ensemble_box_renyi_dimension

The box-counting Rényi family.

objscale.ensemble_box_dimension(binary_arrays: ndarray[tuple[int, ...], dtype[_ScalarType_co]] | list[ndarray[tuple[int, ...], dtype[_ScalarType_co]]], set: str = 'edge', max_box_size: int | None = None, min_box_size: int = 8, box_sizes: str | ndarray[tuple[int, ...], dtype[_ScalarType_co]] = 'default', return_values: bool = False) tuple[float, float] | tuple[float, float, ndarray[tuple[int, ...], dtype[_ScalarType_co]], ndarray[tuple[int, ...], dtype[_ScalarType_co]]][source]

Calculate the ensemble box-counting dimension of binary arrays.

Equivalent to ensemble_box_renyi_dimension(..., q=0). Kept as a convenience wrapper because box counting is the most familiar special case.

Parameters:
  • binary_arrays (list of np.ndarray or np.ndarray) – A list of 2D binary arrays or a single 2D binary array.

  • set (str, default='edge') –

    Specifies which set to consider for box counting: - ‘edge’: Box dimension of the set of boundaries (1-pixels with at

    least one 0-neighbor).

    • ’ones’: Box dimension of the set of 1-pixels.

  • max_box_size (int or None, default=None) – Largest box size in pixels. If None, uses the smaller array dimension.

  • min_box_size (int, default=8) – Smallest box size in pixels. The default of 8 keeps the fit away from pixel-discretization noise at the smallest scales.

  • box_sizes (array-like or 'default', default='default') – Box sizes used. If ‘default’, uses powers of 2 from min_box_size up to max_box_size.

  • return_values (bool, default=False) – If True, return additional data used in the calculation.

Returns:

  • dimension (float) – The estimated box-counting dimension.

  • error (float) – The error of the estimate.

  • box_sizes (np.ndarray, optional) – Box sizes used. Only returned if return_values=True.

  • number_boxes (np.ndarray, optional) – Number of nonempty boxes (pooled across the input ensemble) at each box size. Only returned if return_values=True.

Raises:

ValueError – If an unsupported value is provided for ‘set’ or if arrays contain NaN values.

objscale.individual_correlation_dimension(array: ndarray[tuple[int, ...], dtype[_ScalarType_co]], n: int = 1, x_sizes: ndarray[tuple[int, ...], dtype[_ScalarType_co]] | None = None, y_sizes: ndarray[tuple[int, ...], dtype[_ScalarType_co]] | None = None, minlength: str | float = 'auto', maxlength: str | float = 'auto', return_C_l: bool = False, point_reduction_factor: float = 1, nbins: int = 50, filled: bool = True) tuple[float, float] | tuple[float, float, ndarray[tuple[int, ...], dtype[_ScalarType_co]], ndarray[tuple[int, ...], dtype[_ScalarType_co]]][source]

Calculate the correlation dimension of the Nth largest structure in an array.

Removes border-touching structures, isolates the Nth largest remaining structure, crops to its bounding box, and computes the correlation dimension via ensemble_correlation_dimension().

Parameters:
  • array (np.ndarray) – 2-D binary array. May optionally have np.nan at borders; if not, a NaN border is added internally.

  • n (int, default=1) – Which structure to analyze, ranked by pixel count (1 = largest).

  • x_sizes (np.ndarray, optional) – Pixel sizes in the x direction. If None, assume all pixel dimensions are 1.

  • y_sizes (np.ndarray, optional) – Pixel sizes in the y direction. If None, assume all pixel dimensions are 1.

  • minlength (str or float, default='auto') – Minimum length scale for correlation calculation. If ‘auto’, uses 8 times the minimum pixel size.

  • maxlength (str or float, default='auto') – Maximum length scale for correlation calculation. If ‘auto’, uses 0.33 * max(bbox_height, bbox_width) of the isolated structure in physical units.

  • return_C_l (bool, default=False) – If True, return dimension, error, bins, C_l. Otherwise, return dimension, error.

  • filled (bool, default=True) – If True, fill interior holes in the isolated structure before computing the correlation dimension, so that only the outer boundary contributes. If False, holes are left as-is and interior boundaries are included.

  • point_reduction_factor (float, default=1) – Draw N/point_reduction_factor circles, where N is the total number of available circles. Must be >= 1.

  • nbins (int, default=50) – Number of logarithmically spaced bins for the correlation integral.

Returns:

  • dimension (float) – The correlation dimension.

  • error (float) – Error estimate for the dimension (95% confidence interval).

  • bins (np.ndarray, optional) – The bins used for calculation. Only returned if return_C_l=True.

  • C_l (np.ndarray, optional) – The correlation integral values. Only returned if return_C_l=True.

Raises:

ValueError – If array is not 2-D, n < 1, or n exceeds the number of available structures after border removal.

objscale.get_coords_of_boundaries(array: ndarray[tuple[int, ...], dtype[_ScalarType_co]]) ndarray[tuple[int, ...], dtype[_ScalarType_co]][source]

Find coordinates of pixels with value 1 that are adjacent to pixels with value 0.

Parameters:

array (np.ndarray) – 2-D binary array.

Returns:

Array of shape (n_boundaries, 2) where each element is a pair of indices corresponding to the locations of pixels with value 1 that are adjacent to a pixel of value 0.

Return type:

np.ndarray

Notes

Topology is toroidal, so pixels on one edge are considered adjacent to pixels on the opposite edge.

Examples

>>> array1 = np.zeros((10, 10))
>>> array1[6:8, 6:8] = 1
>>> array1[3:4, 2:5] = 1
>>> array2 = np.zeros((10, 10))
>>> for i, j in get_coords_of_boundaries(array1):
...     array2[i, j] = 1
>>> np.all(array2 == array1)
True
objscale.get_locations_from_pixel_sizes(pixel_sizes_x: ndarray[tuple[int, ...], dtype[_ScalarType_co]], pixel_sizes_y: ndarray[tuple[int, ...], dtype[_ScalarType_co]]) tuple[ndarray[tuple[int, ...], dtype[_ScalarType_co]], ndarray[tuple[int, ...], dtype[_ScalarType_co]]][source]

Convert pixel sizes to cumulative location coordinates.

Parameters:
  • pixel_sizes_x (np.ndarray) – 2-D array of pixel sizes in x direction.

  • pixel_sizes_y (np.ndarray) – 2-D array of pixel sizes in y direction.

Returns:

  • locations_x (np.ndarray) – Cumulative x locations.

  • locations_y (np.ndarray) – Cumulative y locations.