🔍 Code Extractor

class HoloMap

Maturity: 55

HoloMap is an n-dimensional mapping container that stores viewable elements or overlays indexed by tuple keys along declared key dimensions, enabling interactive exploration through widgets.

File:
/tf/active/vicechatdev/patches/spaces.py
Lines:
30 - 431
Complexity:
complex

Purpose

HoloMap serves as a container for organizing and visualizing collections of viewable elements across multiple dimensions. It allows users to create interactive visualizations where elements can be explored by varying widgets that map to the key dimensions. The class supports operations like overlaying, gridding, layouting, and collating nested structures. It's particularly useful for time series data, parameter sweeps, or any multi-dimensional data exploration where you want to interactively navigate through different views of your data.

Source Code

class HoloMap(Layoutable, UniformNdMapping, Overlayable):
    """
    A HoloMap is an n-dimensional mapping of viewable elements or
    overlays. Each item in a HoloMap has an tuple key defining the
    values along each of the declared key dimensions, defining the
    discretely sampled space of values.

    The visual representation of a HoloMap consists of the viewable
    objects inside the HoloMap which can be explored by varying one
    or more widgets mapping onto the key dimensions of the HoloMap.
    """

    data_type = (ViewableElement, NdMapping, Layout)

    def __init__(self, initial_items=None, kdims=None, group=None, label=None, **params):
        super().__init__(initial_items, kdims, group, label, **params)

    @property
    def opts(self):
        return Opts(self, mode='holomap')

    def overlay(self, dimensions=None, **kwargs):
        """Group by supplied dimension(s) and overlay each group

        Groups data by supplied dimension(s) overlaying the groups
        along the dimension(s).

        Args:
            dimensions: Dimension(s) of dimensions to group by

        Returns:
            NdOverlay object(s) with supplied dimensions
        """
        dimensions = self._valid_dimensions(dimensions)
        if len(dimensions) == self.ndims:
            with item_check(False):
                return NdOverlay(self, **kwargs).reindex(dimensions)
        else:
            dims = [d for d in self.kdims if d not in dimensions]
            return self.groupby(dims, group_type=NdOverlay, **kwargs)


    def grid(self, dimensions=None, **kwargs):
        """Group by supplied dimension(s) and lay out groups in grid

        Groups data by supplied dimension(s) laying the groups along
        the dimension(s) out in a GridSpace.

        Args:
        dimensions: Dimension/str or list
            Dimension or list of dimensions to group by

        Returns:
            GridSpace with supplied dimensions
        """
        dimensions = self._valid_dimensions(dimensions)
        if len(dimensions) == self.ndims:
            with item_check(False):
                return GridSpace(self, **kwargs).reindex(dimensions)
        return self.groupby(dimensions, container_type=GridSpace, **kwargs)


    def layout(self, dimensions=None, **kwargs):
        """Group by supplied dimension(s) and lay out groups

        Groups data by supplied dimension(s) laying the groups along
        the dimension(s) out in a NdLayout.

        Args:
            dimensions: Dimension(s) to group by

        Returns:
            NdLayout with supplied dimensions
        """
        dimensions = self._valid_dimensions(dimensions)
        if len(dimensions) == self.ndims:
            with item_check(False):
                return NdLayout(self, **kwargs).reindex(dimensions)
        return self.groupby(dimensions, container_type=NdLayout, **kwargs)


    def options(self, *args, **kwargs):
        """Applies simplified option definition returning a new object

        Applies options defined in a flat format to the objects
        returned by the DynamicMap. If the options are to be set
        directly on the objects in the HoloMap a simple format may be
        used, e.g.:

            obj.options(cmap='viridis', show_title=False)

        If the object is nested the options must be qualified using
        a type[.group][.label] specification, e.g.:

            obj.options('Image', cmap='viridis', show_title=False)

        or using:

            obj.options({'Image': dict(cmap='viridis', show_title=False)})

        Args:
            *args: Sets of options to apply to object
                Supports a number of formats including lists of Options
                objects, a type[.group][.label] followed by a set of
                keyword options to apply and a dictionary indexed by
                type[.group][.label] specs.
            backend (optional): Backend to apply options to
                Defaults to current selected backend
            clone (bool, optional): Whether to clone object
                Options can be applied inplace with clone=False
            **kwargs: Keywords of options
                Set of options to apply to the object

        Returns:
            Returns the cloned object with the options applied
        """
        data = OrderedDict([(k, v.options(*args, **kwargs))
                             for k, v in self.data.items()])
        return self.clone(data)

    def _split_overlays(self):
        "Splits overlays inside the HoloMap into list of HoloMaps"
        if not issubclass(self.type, CompositeOverlay):
            return None, self.clone()

        item_maps = OrderedDict()
        for k, overlay in self.data.items():
            for key, el in overlay.items():
                if key not in item_maps:
                    item_maps[key] = [(k, el)]
                else:
                    item_maps[key].append((k, el))

        maps, keys = [], []
        for k, layermap in item_maps.items():
            maps.append(self.clone(layermap))
            keys.append(k)
        return keys, maps

    def _dimension_keys(self):
        """
        Helper for __mul__ that returns the list of keys together with
        the dimension labels.
        """
        return [tuple(zip([d.name for d in self.kdims], [k] if self.ndims == 1 else k))
                for k in self.keys()]

    def _dynamic_mul(self, dimensions, other, keys):
        """
        Implements dynamic version of overlaying operation overlaying
        DynamicMaps and HoloMaps where the key dimensions of one is
        a strict superset of the other.
        """
        # If either is a HoloMap compute Dimension values
        if not isinstance(self, DynamicMap) or not isinstance(other, DynamicMap):
            keys = sorted((d, v) for k in keys for d, v in k)
            grouped =  dict([(g, [v for _, v in group])
                             for g, group in groupby(keys, lambda x: x[0])])
            dimensions = [d.clone(values=grouped[d.name]) for d in dimensions]
            map_obj = None

        # Combine streams
        map_obj = self if isinstance(self, DynamicMap) else other
        if isinstance(self, DynamicMap) and isinstance(other, DynamicMap):
            self_streams = util.dimensioned_streams(self)
            other_streams = util.dimensioned_streams(other)
            streams = list(util.unique_iterator(self_streams+other_streams))
        else:
            streams = map_obj.streams

        def dynamic_mul(*key, **kwargs):
            key_map = {d.name: k for d, k in zip(dimensions, key)}
            layers = []
            try:
                self_el = self.select(HoloMap, **key_map) if self.kdims else self[()]
                layers.append(self_el)
            except KeyError:
                pass
            try:
                other_el = other.select(HoloMap, **key_map) if other.kdims else other[()]
                layers.append(other_el)
            except KeyError:
                pass
            return Overlay(layers)
        callback = Callable(dynamic_mul, inputs=[self, other])
        callback._is_overlay = True
        if map_obj:
            return map_obj.clone(callback=callback, shared_data=False,
                                 kdims=dimensions, streams=streams)
        else:
            return DynamicMap(callback=callback, kdims=dimensions,
                              streams=streams)



    def __mul__(self, other, reverse=False):
        """Overlays items in the object with another object

        The mul (*) operator implements overlaying of different
        objects.  This method tries to intelligently overlay mappings
        with differing keys. If the UniformNdMapping is mulled with a
        simple ViewableElement each element in the UniformNdMapping is
        overlaid with the ViewableElement. If the element the
        UniformNdMapping is mulled with is another UniformNdMapping it
        will try to match up the dimensions, making sure that items
        with completely different dimensions aren't overlaid.
        """
        if isinstance(other, HoloMap):
            self_set = {d.name for d in self.kdims}
            other_set = {d.name for d in other.kdims}

            # Determine which is the subset, to generate list of keys and
            # dimension labels for the new view
            self_in_other = self_set.issubset(other_set)
            other_in_self = other_set.issubset(self_set)
            dims = [other.kdims, self.kdims] if self_in_other else [self.kdims, other.kdims]
            dimensions = util.merge_dimensions(dims)

            if self_in_other and other_in_self: # superset of each other
                keys = self._dimension_keys() + other._dimension_keys()
                super_keys = util.unique_iterator(keys)
            elif self_in_other: # self is superset
                dimensions = other.kdims
                super_keys = other._dimension_keys()
            elif other_in_self: # self is superset
                super_keys = self._dimension_keys()
            else: # neither is superset
                raise Exception('One set of keys needs to be a strict subset of the other.')

            if isinstance(self, DynamicMap) or isinstance(other, DynamicMap):
                return self._dynamic_mul(dimensions, other, super_keys)

            items = []
            for dim_keys in super_keys:
                # Generate keys for both subset and superset and sort them by the dimension index.
                self_key = tuple(k for p, k in sorted(
                    [(self.get_dimension_index(dim), v) for dim, v in dim_keys
                     if dim in self.kdims]))
                other_key = tuple(k for p, k in sorted(
                    [(other.get_dimension_index(dim), v) for dim, v in dim_keys
                     if dim in other.kdims]))
                new_key = self_key if other_in_self else other_key
                # Append SheetOverlay of combined items
                if (self_key in self) and (other_key in other):
                    if reverse:
                        value = other[other_key] * self[self_key]
                    else:
                        value = self[self_key] * other[other_key]
                    items.append((new_key, value))
                elif self_key in self:
                    items.append((new_key, Overlay([self[self_key]])))
                else:
                    items.append((new_key, Overlay([other[other_key]])))
            return self.clone(items, kdims=dimensions, label=self._label, group=self._group)
        elif isinstance(other, self.data_type) and not isinstance(other, Layout):
            if isinstance(self, DynamicMap):
                def dynamic_mul(*args, **kwargs):
                    element = self[args]
                    if reverse:
                        return other * element
                    else:
                        return element * other
                callback = Callable(dynamic_mul, inputs=[self, other])
                callback._is_overlay = True
                return self.clone(shared_data=False, callback=callback,
                                  streams=util.dimensioned_streams(self))
            items = [(k, other * v) if reverse else (k, v * other)
                     for (k, v) in self.data.items()]
            return self.clone(items, label=self._label, group=self._group)
        else:
            return NotImplemented

    def __lshift__(self, other):
        "Adjoin another object to this one returning an AdjointLayout"
        if isinstance(other, (ViewableElement, UniformNdMapping, Empty)):
            return AdjointLayout([self, other])
        elif isinstance(other, AdjointLayout):
            return AdjointLayout(other.data+[self])
        else:
            raise TypeError('Cannot append {0} to a AdjointLayout'.format(type(other).__name__))


    def collate(self, merge_type=None, drop=[], drop_constant=False):
        """Collate allows reordering nested containers

        Collation allows collapsing nested mapping types by merging
        their dimensions. In simple terms in merges nested containers
        into a single merged type.

        In the simple case a HoloMap containing other HoloMaps can
        easily be joined in this way. However collation is
        particularly useful when the objects being joined are deeply
        nested, e.g. you want to join multiple Layouts recorded at
        different times, collation will return one Layout containing
        HoloMaps indexed by Time. Changing the merge_type will allow
        merging the outer Dimension into any other UniformNdMapping
        type.

        Args:
            merge_type: Type of the object to merge with
            drop: List of dimensions to drop
            drop_constant: Drop constant dimensions automatically

        Returns:
            Collated Layout or HoloMap
        """
        from .element import Collator
        merge_type=merge_type if merge_type else self.__class__
        return Collator(self, merge_type=merge_type, drop=drop,
                        drop_constant=drop_constant)()

    def decollate(self):
        """Packs HoloMap of DynamicMaps into a single DynamicMap that returns an
        HoloMap

        Decollation allows packing a HoloMap of DynamicMaps into a single DynamicMap
        that returns an HoloMap of simple (non-dynamic) elements. All nested streams
        are lifted to the resulting DynamicMap, and are available in the `streams`
        property.  The `callback` property of the resulting DynamicMap is a pure,
        stateless function of the stream values. To avoid stream parameter name
        conflicts, the resulting DynamicMap is configured with
        positional_stream_args=True, and the callback function accepts stream values
        as positional dict arguments.

        Returns:
            DynamicMap that returns an HoloMap
        """
        from .decollate import decollate
        return decollate(self)

    def relabel(self, label=None, group=None, depth=1):
        """Clone object and apply new group and/or label.

        Applies relabeling to children up to the supplied depth.

        Args:
            label (str, optional): New label to apply to returned object
            group (str, optional): New group to apply to returned object
            depth (int, optional): Depth to which relabel will be applied
                If applied to container allows applying relabeling to
                contained objects up to the specified depth

        Returns:
            Returns relabelled object
        """
        return super().relabel(label=label, group=group, depth=depth)

    def hist(self, dimension=None, num_bins=20, bin_range=None,
             adjoin=True, individually=True, **kwargs):
        """Computes and adjoins histogram along specified dimension(s).

        Defaults to first value dimension if present otherwise falls
        back to first key dimension.

        Args:
            dimension: Dimension(s) to compute histogram on
            num_bins (int, optional): Number of bins
            bin_range (tuple optional): Lower and upper bounds of bins
            adjoin (bool, optional): Whether to adjoin histogram

        Returns:
            AdjointLayout of HoloMap and histograms or just the
            histograms
        """
        if dimension is not None and not isinstance(dimension, list):
            dimension = [dimension]
        histmaps = [self.clone(shared_data=False) for _ in (dimension or [None])]

        if individually:
            map_range = None
        else:
            if dimension is None:
                raise Exception("Please supply the dimension to compute a histogram for.")
            map_range = self.range(kwargs['dimension'])

        bin_range = map_range if bin_range is None else bin_range
        style_prefix = 'Custom[<' + self.name + '>]_'
        if issubclass(self.type, (NdOverlay, Overlay)) and 'index' not in kwargs:
            kwargs['index'] = 0

        for k, v in self.data.items():
            hists = v.hist(adjoin=False, dimension=dimension,
                           bin_range=bin_range, num_bins=num_bins,
                           style_prefix=style_prefix, **kwargs)
            if isinstance(hists, Layout):
                for i, hist in enumerate(hists):
                    histmaps[i][k] = hist
            else:
                histmaps[0][k] = hists

        if adjoin:
            layout = self
            for hist in histmaps:
                layout = (layout << hist)
            if issubclass(self.type, (NdOverlay, Overlay)):
                layout.main_layer = kwargs['index']
            return layout
        else:
            if len(histmaps) > 1:
                return Layout(histmaps)
            else:
                return histmaps[0]

Parameters

Name Type Default Kind
bases Layoutable, UniformNdMapping, Overlayable -

Parameter Details

initial_items: Initial data items to populate the HoloMap. Can be a list of (key, value) tuples, a dictionary, or another mapping object. Keys should be tuples matching the dimensionality of kdims.

kdims: Key dimensions that define the indexing structure of the HoloMap. Can be a list of Dimension objects or strings that will be converted to Dimensions. These dimensions define the parameter space that can be explored.

group: String identifier for grouping related HoloMaps together. Used for organization and identification purposes.

label: String label for the HoloMap instance. Used for display and identification purposes.

params: Additional keyword parameters passed to parent classes (Layoutable, UniformNdMapping, Overlayable). Can include various configuration options.

Return Value

Instantiation returns a HoloMap object that acts as a container for viewable elements. Methods return various types: overlay() returns NdOverlay objects, grid() returns GridSpace, layout() returns NdLayout, options() returns a cloned HoloMap with applied options, collate() returns a collated Layout or HoloMap, decollate() returns a DynamicMap, hist() returns AdjointLayout or histograms, and relabel() returns a relabeled clone.

Class Interface

Methods

__init__(self, initial_items=None, kdims=None, group=None, label=None, **params)

Purpose: Initialize a HoloMap instance with optional initial data and configuration

Parameters:

  • initial_items: Initial data items to populate the HoloMap
  • kdims: Key dimensions defining the indexing structure
  • group: Group identifier for organization
  • label: Label for display and identification
  • params: Additional configuration parameters

Returns: None (constructor)

@property opts(self) property

Purpose: Returns an Opts accessor for applying options in holomap mode

Returns: Opts object configured for holomap mode

overlay(self, dimensions=None, **kwargs) -> NdOverlay

Purpose: Group data by supplied dimension(s) and overlay each group into NdOverlay objects

Parameters:

  • dimensions: Dimension(s) to group by for overlaying
  • kwargs: Additional keyword arguments passed to groupby or NdOverlay

Returns: NdOverlay object(s) with elements overlaid along the specified dimensions

grid(self, dimensions=None, **kwargs) -> GridSpace

Purpose: Group data by supplied dimension(s) and lay out groups in a grid structure

Parameters:

  • dimensions: Dimension(s) to group by for grid layout
  • kwargs: Additional keyword arguments passed to groupby or GridSpace

Returns: GridSpace with elements arranged in a grid along specified dimensions

layout(self, dimensions=None, **kwargs) -> NdLayout

Purpose: Group data by supplied dimension(s) and create an NdLayout arrangement

Parameters:

  • dimensions: Dimension(s) to group by for layout
  • kwargs: Additional keyword arguments passed to groupby or NdLayout

Returns: NdLayout with elements arranged along specified dimensions

options(self, *args, **kwargs) -> HoloMap

Purpose: Apply simplified option definitions to all elements in the HoloMap, returning a new object

Parameters:

  • args: Sets of options in various formats (Options objects, type specs, or dictionaries)
  • backend: Backend to apply options to (defaults to current selected backend)
  • clone: Whether to clone the object (default True); False applies options in-place
  • kwargs: Keyword options to apply to elements

Returns: Cloned HoloMap with options applied to all contained elements

_split_overlays(self) -> tuple

Purpose: Internal method to split overlays inside the HoloMap into a list of HoloMaps

Returns: Tuple of (keys, maps) where keys are overlay keys and maps are corresponding HoloMaps

_dimension_keys(self) -> list

Purpose: Internal helper for __mul__ that returns keys with dimension labels

Returns: List of tuples pairing dimension names with key values

_dynamic_mul(self, dimensions, other, keys) -> DynamicMap

Purpose: Internal method implementing dynamic overlaying of DynamicMaps and HoloMaps

Parameters:

  • dimensions: Merged dimensions for the result
  • other: Other object to overlay with
  • keys: Keys for the overlay operation

Returns: DynamicMap that dynamically overlays elements from both objects

__mul__(self, other, reverse=False) -> HoloMap | DynamicMap

Purpose: Overlay items in the HoloMap with another object using the * operator

Parameters:

  • other: Object to overlay with (HoloMap, ViewableElement, or compatible type)
  • reverse: Whether to reverse the overlay order

Returns: New HoloMap or DynamicMap with overlaid elements

__lshift__(self, other) -> AdjointLayout

Purpose: Adjoin another object to this HoloMap using the << operator

Parameters:

  • other: Object to adjoin (ViewableElement, UniformNdMapping, Empty, or AdjointLayout)

Returns: AdjointLayout containing this HoloMap and the adjoined object

collate(self, merge_type=None, drop=[], drop_constant=False) -> HoloMap | Layout

Purpose: Reorder and merge nested containers by collapsing dimensions

Parameters:

  • merge_type: Type of object to merge into (defaults to HoloMap)
  • drop: List of dimensions to drop during collation
  • drop_constant: Whether to automatically drop constant dimensions

Returns: Collated Layout or HoloMap with restructured nesting

decollate(self) -> DynamicMap

Purpose: Pack a HoloMap of DynamicMaps into a single DynamicMap that returns a HoloMap

Returns: DynamicMap with lifted streams that returns HoloMap of non-dynamic elements

relabel(self, label=None, group=None, depth=1) -> HoloMap

Purpose: Clone the HoloMap and apply new group and/or label to specified depth

Parameters:

  • label: New label to apply
  • group: New group to apply
  • depth: Depth to which relabeling is applied to nested objects

Returns: Relabeled clone of the HoloMap

hist(self, dimension=None, num_bins=20, bin_range=None, adjoin=True, individually=True, **kwargs) -> AdjointLayout | HoloMap | Layout

Purpose: Compute and optionally adjoin histograms along specified dimension(s)

Parameters:

  • dimension: Dimension(s) to compute histogram on (defaults to first value dimension)
  • num_bins: Number of bins for the histogram
  • bin_range: Tuple of (lower, upper) bounds for bins
  • adjoin: Whether to adjoin histogram to original HoloMap
  • individually: Whether to compute histogram ranges individually per element
  • kwargs: Additional arguments like 'index' for overlay selection

Returns: AdjointLayout of HoloMap and histograms if adjoin=True, otherwise just histograms as HoloMap or Layout

Attributes

Name Type Description Scope
data_type tuple Class variable defining allowed data types that can be stored in the HoloMap: (ViewableElement, NdMapping, Layout) class
kdims list[Dimension] Key dimensions that define the indexing structure and parameter space of the HoloMap instance
data OrderedDict Internal storage for the mapping of keys to viewable elements (inherited from UniformNdMapping) instance
group str Group identifier for organizing related HoloMaps instance
label str Label for display and identification of the HoloMap instance instance
ndims int Number of key dimensions (inherited property from parent classes) instance
type type Type of elements stored in the HoloMap (inherited from UniformNdMapping) instance

Dependencies

  • numpy
  • param
  • itertools
  • functools
  • collections
  • contextlib
  • types
  • numbers
  • inspect

Required Imports

import numpy as np
import param
from itertools import groupby
from functools import partial
from collections import defaultdict, OrderedDict
from contextlib import contextmanager
from types import FunctionType
from numbers import Number

Conditional/Optional Imports

These imports are only needed under specific conditions:

from inspect import FullArgSpec

Condition: Python 3.x

Required (conditional)
from inspect import ArgSpec as FullArgSpec

Condition: Python 2.x fallback

Optional

Usage Example

import holoviews as hv
from holoviews import HoloMap, Curve
import numpy as np

# Create data for different time points
data = {}
for i in range(5):
    xs = np.linspace(0, 10, 100)
    ys = np.sin(xs + i)
    data[i] = Curve((xs, ys))

# Create HoloMap with time dimension
holomap = HoloMap(data, kdims=['time'])

# Overlay all elements
overlaid = holomap.overlay()

# Create grid layout
grid = holomap.grid()

# Apply options
styled = holomap.options(color='red', line_width=2)

# Compute histogram
hist_layout = holomap.hist(dimension='y', adjoin=True)

# Relabel
relabeled = holomap.relabel(label='Sine Waves', group='Timeseries')

Best Practices

  • Always define kdims when creating a HoloMap to ensure proper indexing and widget generation
  • Use consistent key tuple lengths matching the number of key dimensions
  • When overlaying HoloMaps, ensure dimension compatibility - one set of dimensions should be a subset of the other
  • Use clone=False in options() method only when you're certain you don't need the original object
  • For large datasets, consider using DynamicMap instead of HoloMap to avoid memory issues
  • When using collate(), be aware it restructures nested containers and may change the navigation structure
  • Use overlay() for combining elements along dimensions, grid() for spatial layouts, and layout() for flexible arrangements
  • The hist() method with adjoin=True creates side-by-side layouts; use adjoin=False to get just the histograms
  • When multiplying HoloMaps with *, ensure dimensional compatibility to avoid exceptions
  • Store the result of operations like overlay(), grid(), and layout() as they return new objects rather than modifying in place

Similar Components

AI-powered semantic similarity - components with related functionality:

  • class DynamicMap 70.1% similar

    A DynamicMap is a type of HoloMap where the elements are dynamically generated by a callable. The callable is invoked with values associated with the key dimensions or with values supplied by stream parameters.

    From: /tf/active/vicechatdev/patches/spaces.py
  • class GridSpace 59.4% similar

    GridSpace is a container class for organizing elements in a 1D or 2D grid structure with floating-point keys, ensuring all contained elements are of the same type.

    From: /tf/active/vicechatdev/patches/spaces.py
  • function layer_sort 57.9% similar

    Computes a global topological ordering of layers from a HoloMap containing CompositeOverlay objects by analyzing layer dependencies and sorting them.

    From: /tf/active/vicechatdev/patches/util.py
  • class GridMatrix 55.4% similar

    GridMatrix is a container class for heterogeneous Element types arranged in a grid layout where axes don't represent coordinate space but are used to plot various dimensions against each other.

    From: /tf/active/vicechatdev/patches/spaces.py
  • class Config_v4 55.2% similar

    A configuration class that manages global HoloViews behavior settings, including deprecation warnings, default colormaps, and rendering parameters.

    From: /tf/active/vicechatdev/patches/util.py
← Back to Browse