Instructions:
The project focuses on the use of FMCW radar.
It is used for data collection, point detection, tracking and other functions.
The project is broken down into several modules.
The aim of this division is to decouple as much as possible the functionalities present in each module, and make the development of new functionalities more flexible and rapid.

Some information will be presented to you in json format:
- module: the name of the module
- module_structure: the structure of the module (the files making up the module and their hierarchy)
- module_files_already_generated_doc: the documentation of the module's files if already generated
- other_modules_doc: the documentation of the other modules on which the module depends (possibly none at all)
- gen_doc_of_file: the file you will be given to generate the documentation of. If no file is given, the documentation of the entire module must be generated.
Your goal is to create a markdown documentation of the file you will be given, or the entire module if no file is given.
This documentation is intended to guide a developer who is new to the project, you can therefore add whatever you feel is relevant for this task.


Informations:
{"module": "radar_tracking", "module_structure": "radar_tracking/tracking_utils.py;radar_tracking\\conf/tracking.json;radar_tracking\\inference/example_kalman_filter.py;radar_tracking\\inference/example_tracking.py;radar_tracking\\models/kalman.py;radar_tracking\\models/tracking.py;radar_tracking\\models\\clustering/cluster.py;radar_tracking\\models\\clustering/cluster_predictor.py;radar_tracking\\models\\clustering/optimizer.py;radar_tracking\\models\\clustering\\algos/clustering_alogirthm.py;radar_tracking\\models\\clustering\\algos/dbscan.py;radar_tracking\\models\\clustering\\algos/gaussian_mixture.py;radar_tracking\\models\\clustering\\algos/meanshift.py;radar_tracking\\visuals/display.py;", "module_files_already_generated_doc": [{"file": "radar_tracking\\tracking_utils.md", "doc": "# radar_tracking/tracking_utils.py Documentation\n\n## Overview\n\nThe tracking_utils.py script is part of the radar_tracking module, which is focused on the tracking aspect of FMCW radar applications. It provides utility functions to configure and instantiate key components of the radar tracking system, such as cluster trackers and clustering algorithms. The script draws from the configuration files to create instances that adhere to the pre-defined parameters for the tracking functionality.\n\n## Functions\n\n### get_capture_limits_from_conf\n\nThis function extracts capture limits from the provided configuration object. It converts the configuration values into a structured NumPy array specifying the range (min-max) for the x, y, and z dimensions.\n\nParameters:\n- config: Configuration object with capture limits for x, y, and z axes.\n\nReturns:\n- capture_limits_array: A NumPy array with shape (min-max values, xyz).\n\n### get_cluster_tracker_from_conf\n\nThis function initializes a ClusterTracker object using the tracking-related settings from the configuration.\n\nParameters:\n- config: A configuration object that contains frame grouping size, frame interval, and tracking settings like max_height_w and others.\n\nReturns:\n- An instance of ClusterTracker with the provided weights and configurations.\n\n### get_clustering_algo_from_conf\n\nThis function sets up a clustering algorithm according to the defined configuration. It supports adjusting parameters like the vertical scale, trajectory memory duration, and others specific to the chosen clustering algorithm (DBSCAN in this instance).\n\nParameters:\n- config: Configuration object specifying clustering and tracking parameters, e.g., min_cluster_points, eps, nb_persons, etc.\n\nReturns:\n- An instance of ClusteringPredictor ready to be used for clustering and tracking purposes.\n\n## Usage\n\nThese utility functions are intended to be called with the appropriate configuration objects to dynamically create configured instances for tracking:\n\n```python\nfrom radar_tracking.tracking_utils import get_capture_limits_from_conf, get_cluster_tracker_from_conf, get_clustering_algo_from_conf\nconfig = \u00e2\u20ac\u00a6\ncapture_limits = get_capture_limits_from_conf(config)\ncluster_tracker = get_cluster_tracker_from_conf(config)\nclustering_algo = get_clustering_algo_from_conf(config)\n```\n\n\n\nDevelopers can use these functions to integrate tracking utilities without hardcoding parameters, enabling flexibility and ensuring consistency with configurations.\n\n## Data Flow\n\nThe workflow using tracking_utils.py typically follows these steps:\n\n1. A configuration object is generated or read from a configuration file (e.g., tracking.json).\n2. The aforementioned utility functions are called to create instances with the specified configuration.\n3. These instances are then utilized in the tracking algorithms to process radar data for point detection, tracking, and other functions.\n4. The tracking outputs can be visualized or further processed by other components within the radar_tracking module.\n\n## Conclusion\n\ntracking_utils.py is a key component of the radar_tracking module that streamlines the initialization and configuration of tracking systems within the FMCW radar project. By abstracting the setup details into configuration-driven utility functions, the script facilitates modular development, testing, and iteration of tracking functionalities."}, {"file": "radar_tracking\\models\\kalman.md", "doc": "# radar_tracking/models/kalman.py Documentation\n\n## Overview\n\nThis script contains implementations of Kalman and Unscented Kalman filters, providing functionalities for estimating the state of a system over time in presence of noise.\n\n## Enums\n\n### Trajectory\n\nAn Enum describing different types of trajectories:\n- CONST_VELOCITY: Constant velocity model.\n- CONST_ACCELERATION: Constant acceleration model.\n- VARIABLE_ACCELERATION: Variable acceleration model.\n\n## Functions\n\n### fx\n\nThe state transition function for the Unscented Kalman Filter that describes how the state evolves over time.\n- Parameters: x: current state vector, dt: time step\n- Returns: updated state vector\n\n### hx\n\nThe measurement function for the Unscented Kalman Filter that maps the true state space into the observed space.\n- Parameters: x: current state vector\n- Returns: measurement vector\n\n### get_unscented_KalmanFilter\n\nInitializes an Unscented Kalman Filter with the specified parameters.\n- Parameters: m_var: measurement noise variance, p_var: process noise variance, dt: time step, x_initial: initial state vector\n- Returns: instance of UnscentedKalmanFilter\n\n### get_linear_KalmanFilter\n\nCreates a linear Kalman Filter of a specified order.\n- Parameters: order: model order, m_var: measurement noise variance, p_var: process noise variance, dt: time step, x_initial: initial state vector\n- Returns: an instance of KalmanFilter\n\n### create_measurement_data\n\nSimulates a trajectory with measurement noise to generate both the true track and noisy measurements.\n- Parameters: speed: object speed, duration: simulation duration, p_std: process noise standard deviation, m_std: measurement noise standard deviation, trajectory_type: type of trajectory, dt: time step, start_pos: starting position\n- Returns: tuple of Numpy arrays representing the true track and noisy measurements\n\n### plot_kalman_graphs\n\nPlots the results of Kalman filtering and/or smoothing.\n- Parameters: measurements: noisy measurements, filter: Kalman filter estimates, track: true trajectory, Ms: smoothing estimates (optional), Covs: covariances (optional), Ps: covariance estimates from smoothing (optional), plot_only_filter: whether to plot only the filter results\n\n## Usage\n\nTo use the Kalman filters within this module, initialize with appropriate noise parameters and time step based on the radar system:\n\n```python\nfrom radar_tracking.models.kalman import get_linear_KalmanFilter, create_measurement_data\nkf = get_linear_KalmanFilter(order=1, m_var=0.1, p_var=0.1, dt=0.1)\ntrack, measurements = create_measurement_data(speed=1.0, duration=10.0, p_std=0.1, m_std=0.1, trajectory_type=Trajectory.CONST_VELOCITY)\n# Process measurements through the filter\u00e2\u20ac\u00a6\n```\n\n\nThese functions provide a layer of abstraction to easily employ Kalman filters in radar tracking applications, enabling rapid development and integration of new tracking features.\n\n## Data Flow\n\nThe typical data flow using kalman.py would be as follows:\n\n1. Initialize the Kalman filter with process and measurement noise statistics relevant to the radar setup.\n2. Generate or collect noisy measurements from the radar system.\n3. Update the Kalman filter sequentially with these measurements to estimate the system state.\n4. Optionally, plot the results to visualize the performance of the filter against the true trajectory.\n\n\n## Conclusion\n\nThe kalman.py script provides state estimation capabilities fundamental to many radar tracking scenarios. By encapsulating complex filtering and prediction algorithms into easy-to-use functions, it streamlines the process of incorporating sensor fusion and estimation techniques into the larger project framework."}, {"file": "radar_tracking\\models\\clustering\\cluster.md", "doc": "# radar_tracking/models/clustering/cluster.py Documentation\n\n## Overview\n\nThe script provides the Cluster class, which encapsulates the data and methods for managing a cluster of 3D points. Each cluster represents a grouping of points within the radar\u00e2\u20ac\u2122s observation space that is believed to belong to the same object or feature in the environment.\n\n## Class Description\n\n### Cluster\n\nThe Cluster class is responsible for storing and computing attributes based on a collection of 3D points.\n\n#### Initialization\n\nThe constructor requires the following parameters:\n- points: A NumPy array of 3D points associated with the cluster.\n- delta_t: The time difference between consecutive radar samples.\n- height_axis, depth_axis, width_axis: Indices indicating which columns correspond to the height, depth, and width dimensions.\n- ranges: A dictionary of axis indices to their respective ranges.\n- nb_steps_to_keep: The number of time steps worth of cluster attributes to retain in memory.\n\n#### Attributes\n\nKey attributes of a Cluster object include:\n- id: A unique identifier for the cluster.\n- centroid: The calculated geometric center of the cluster\u00e2\u20ac\u2122s points.\n- max_height: The maximum height value within the cluster.\n- density_distribution: A probability distribution over the height axis representing the density of points.\n- kalman_filter: An instance of a Kalman filter used for predicting the evolution of the cluster\u00e2\u20ac\u2122s state over time.\n\n#### Methods\n\nMethods provided by the Cluster class include:\n- get_points(): Retrieves the array of data points belonging to the cluster.\n- get_nb_points(): Returns the total number of points in the cluster.\n- compute_centroid(): Calculates the centroid of the cluster.\n- get_max_value(): Obtains the maximal value on a specified axis within the cluster.\n- compute_density_distribution(): Generates the density distribution along a specified axis.\n- predict_position(): Estimates the future position of the cluster.\n- compute_distribution_distance(): Computes the Wasserstein distance between two distributions.\n- compute_distance(): Determines the likeness distance between two clusters based on various weighted attributes.\n- UpdateFromCluster(): Updates the current cluster based on the geometry and state of another cluster.\n- get_estimated_velocity(): Returns the estimated velocity of the cluster from its Kalman filter.\n- get_estimated_position(): Provides the estimated position of the cluster from its Kalman filter.\n- serialize_cluster(): Serializes the cluster\u00e2\u20ac\u2122s attributes for storage or transmission.\n\n## Usage\n\nThe Cluster class serves as an essential component of radar-tracking algorithms, where point data is grouped based on spatial proximity or other clustering algorithms to form objects of interest. The class facilitates the tracking of objects by providing tools to analyze their motion and other characteristics.\n\n```python\nfrom radar_tracking.models.clustering.cluster import Cluster\n\n# Example of creating a cluster with detector points\ncluster = Cluster(points=detection_points, delta_t=0.1, height_axis=2, depth_axis=1, width_axis=0, ranges=ranges, nb_steps_to_keep=10)\n```\n\n## Data Flow\n\nIn a typical tracking system, the following data flow can be observed:\n1. Radar data is collected and pre-processed to form detectable points.\n2. Clustering algorithms such as DBSCAN aggregate these points into clusters.\n3. The Cluster objects are created and updated with new radar data points.\n4. Tracking algorithms make use of the Cluster objects to monitor and predict the trajectory of each object detected by the radar.\n\n## Integration with Other Modules\n\ncluster.py directly interfaces with clustering algorithms and Kalman filter implementations to provide a robust tracking capability. It potentially utilizes other module components such as radar_toolbox for data acquisition and radar_visuals for the visualization of clusters and their related attributes.\n\n## Conclusion\n\nThe cluster.py script provides a way to represent and manage groups of points as coherent objects for tracking purposes. It is a critical part of the radar tracking workflow and enhances the project\u00e2\u20ac\u2122s capacity to discern and follow distinct objects across a series of radar observations. Through the integration of mathematical models and statistical methods, the class provides tools necessary for advanced analysis within the radar tracking domain."}, {"file": "radar_tracking\\models\\clustering\\cluster_predictor.md", "doc": "# radar_tracking/models/clustering/cluster_predictor.py Documentation\n\n## Overview\n\nThis script provides the ClusteringPredictor class, responsible for predicting clustering behavior using various algorithms. This class plays a crucial role in radar-based tracking systems, enabling the categorization of points into discrete clusters which may represent individual objects or entities within the radar\u00e2\u20ac\u2122s observation field.\n\n## Class Definition\n\n### ClusteringPredictor\n\nThe ClusteringPredictor class is designed to facilitate the creation of clusters from sets of 3D points based on the specified clustering algorithm and other relevant parameters.\n\n#### Initialization\n\nThe constructor accepts the following parameters:\n\n- clustering_algo: Enum specifying the clustering algorithm to use (EAlgorithms).\n- dt: The time step between consecutive measurements.\n- height_axis: Axis index for height within the 3D point array.\n- depth_axis: Axis index for depth within the 3D point array.\n- width_axis: Axis index for width within the 3D point array.\n- ranges: Dictionary mapping axis indices to their min and max values.\n- nb_steps_to_keep: Number of steps to hold in memory for estimation and display.\n- nb_persons: Estimated number of persons in the cluster.\n- min_points: Minimum number of points to qualify as a cluster.\n- eps: Epsilon value for DBSCAN clustering.\n- vertical_scale: Scale factor applied to height values before clustering.\n\n#### Attributes\n\n- algo: An instance of the selected clustering algorithm initialized with the given parameters.\n\n#### Methods\n\n- _choose_algo: Private method to instantiate the appropriate clustering algorithm based on the selected enumeration type.\n- fit_predict: Applies the clustering algorithm to the scaled input data and returns a label for each point.\n- clusterize: Generates clusters from an array of 3D points and identifies noise.\n\n## Usage\n\nThe ClusteringPredictor class is used to segment radar data into meaningful clusters that can be used for tracking and object detection.\n\n```python\nfrom radar_tracking.models.clustering.cluster_predictor import ClusteringPredictor, EAlgorithms\n\n# Example initialization\ncluster_predictor = ClusteringPredictor(\n    clustering_algo=EAlgorithms.DBSCAN,\n    dt=0.1,\n    height_axis=2,\n    depth_axis=1,\n    width_axis=0,\n    ranges=dict(height=(0, 3), depth=(0, 5), width=(0, 5)),\n    nb_steps_to_keep=10,\n    nb_persons=2,\n    min_points=5,\n    eps=0.3,\n    vertical_scale=1\n)\n\n# Example usage\nclusters, noise = cluster_predictor.clusterize(points_3D)\n```\n\n\n## Data Flow\n\nThe ClusteringPredictor is integral to the data analysis workflow in a radar tracking system:\n\n1. 3D point data is collected from radar observations.\n2. The ClusteringPredictor applies the specified clustering algorithm to segment these points into clusters.\n3. Clusters are maintained and updated as new data arrives to track movement or changes over time.\n4. Noise is identified and separated from the meaningful clusters.\n\n## Integration with Other Modules\n\ncluster_predictor.py typically relies on the radar_toolbox for data preprocessing and radar_visuals for displaying the results of the clustering process. It may also utilize implementations of clustering algorithms within the same radar_tracking module, like DBSCAN or Mean Shift, to perform its predictions.\n\n## Conclusion\n\ncluster_predictor.py provides the ability to organize points detected by radar into distinct groups, which is essential for subsequent tracking and analysis tasks. By abstracting algorithm selection and point grouping into a unified interface, it simplifies integration into the larger radar tracking system and aids in the efficient development of new clustering and tracking functionalities."}], "other_modules_doc": [{"module": "radar_visuals", "doc": "# radar_visuals Module Documentation\n\n## Overview\n\nThe radar_visuals module is a dedicated visualization package within a project focused on the use of Frequency Modulated Continuous Wave (FMCW) radar. It is designed to provide tools and utilities for the rendering of radar data in various visual formats, supporting functionalities like data collection, point detection, and tracking analysis. The module aims to facilitate rapid development and integration of new visualization features through a decoupled and flexible structure.\n\n## Module Structure\n\nThe radar_visuals module currently contains the following file:\n\n- display.py: A Python script offering a suite of classes and functions for creating dynamic and static displays for radar data visualization.\n\n## Module Files Documentation\n\n### display.py\n\nThe display.py file within the radar_visuals package encompasses multiple visualization methods and is central to the module. Below is a summary of the provided documentation:\n\n#### Overview\nThe script is essential for visualizing radar data and includes capabilities for 2D, 3D, and polar plotting. It is versatile enough to accommodate both real-time and static data presentations.\n\n#### Components\nEnums such as PlayingMode, Projection, and GraphType allow the user to define the display behavior, the plot\u00e2\u20ac\u2122s projection type, and the graph style, respectively. Along with utility functions like color_from_id and plot_signal, the script provides two main classes:\n\n- UpdatableDisplay: The abstract base class for displays that can be updated, initializing the figure, axes, and other graphical elements.\n- SimpleUpdatableDisplay: A concrete implementation of UpdatableDisplay that prepares and updates displays with new data points.\n\n#### Functionalities\nThe primary functionalities include creating interactive graphs to visualize radar data, updating them according to predefined playing modes, and ensuring compatibility with different data types and visual projections.\n\n#### Data Flow\nThe typical workflow involves:\n1. Initializing a display object with the required properties.\n2. Accumulating or simulating radar data points.\n3. Updating the display as new data arrives through the show() method.\n4. Presenting the visual representation of the radar data to users based on the set playing mode.\n\n#### Developer Notes\nDevelopers are advised to match data dimensions with graph types and projections, manage update rates effectively, and assign unique colors to data sources using UUIDs for better data distinction.\n\n#### Integration\nDespite being part of the radar_visuals package, display.py operates independently from other components, specifically focusing on visualization purposes and not on signal processing.\n\n## Usage\n\nThe module can be employed to:\n\n- Visualize FMCW radar-related data points, signals, and more complex datasets.\n- Develop new visualization tools tailored to the specifics of radar data.\n- Enhance the interpretation of radar data through graphically rich plots.\n\n## Conclusion\n\nradar_visuals is a crucial module for the graphical representation and analysis of radar data within a larger FMCW radar-focused project. The modular structure accommodates efficient development, enabling users and developers to easily integrate new visualization techniques suited to their specific needs. The module\u00e2\u20ac\u2122s design streamlines the translation of complex data into understandable and insightful visual formats, supporting a wide range of functionalities from debugging to presentation."}, {"module": "radar_toolbox", "doc": "# radar_toolbox Module Documentation\n\n## Overview\n\nThe radar_toolbox module is a collection of tools designed for interfacing with Frequency Modulated Continuous Wave (FMCW) radar systems. It is utilized for various purposes such as data collection, point detection, tracking, and other radar signal processing functions. The module is structured to decouple functionalities into distinct units to promote flexibility and rapid development of new features.\n\n## Module Structure\n\nThe radar_toolbox module is composed of the following elements:\n\n- conf/\n  - Various configuration files setting parameters for radar initialization and different processing steps, such as profile_vs1642_exp.cfg which provides specific settings for radar models and data handling.\n- capture_session/\n  - This submodule contains scripts for setting up and managing radar data capture sessions, with scripts like main.py for starting, monitoring, and saving raw radar captures.\n- raw_data/\n  - A collection of code dealing with raw data handling, including adc.py for interfacing with Analog-to-Digital Converters and scripts to convert raw binary radar data into structured formats for analysis.\n- TI_data/\n  - Contains tools and scripts to communicate, configure, and process data from Texas Instruments (TI) mmWave radar boards, including sensor_com.py which outlines communication protocols and data parsing mechanisms.\n- fmcw_utils.py\n  - This utility file offers essential classes and functions for the processing and analysis of FMCW radar data, such as radar model enums and functions for loading and converting radar data.\n- utils.py\n  - General utility functions and classes that support the operation of the radar_toolbox module, with methods for loading configurations, data parsing, and more.\n\n## Module Files Documentation\n\nDevelopers new to radar_toolbox will find documentation for several key files within the module. An outline of this documentation includes:\n\n- fmcw_utils\n  - Detailed information on handling FMCW radar systems, managing configurations, processing radar signals, and transforming them into analyzable forms.\n- utils\n  - A comprehensive overview of utility functions that aid in loading configurations, preprocessing radar data, and assisting with model training and coordinate adjustments.\n- capture_session/main\n  - Instructions on setting up and conducting recording sessions with scripts that interact with the radar system to initiate and manage data capture.\n- raw_data/adc\n  - Documentation of the adc.py script which serves as an interface to ADC hardware, allowing for the capture and real-time processing of radar data streams.\n- raw_data/raw_bin_to_numpy\n  - Explains the process of converting raw binary radar data into a NumPy array and the steps involved in ensuring data integrity during conversion.\n- raw_data/record_raw_data\n  - A guide to a script focused on raw data recording, detailing the initiation of data capture and subsequent data stream management.\n- TI_data/record_ti_data\n  - Documentation for a script specific to TI radar hardware, describing real-time data capture and CSV data storage functionality.\n- TI_data/sensor_com\n  - Communication protocols and data structure parsing methods for TI mmWave radar boards are outlined for managing interactions with these devices.\n\n## Usage\n\nDevelopers can use the radar_toolbox module to:\n\n- Set up FMCW radar data capture sessions.\n- Record and process raw radar data.\n- Convert binary radar data captures into formats suitable for analysis, such as NumPy arrays.\n- Interact and configure TI mmWave radars for data acquisition.\n\n## Data Flow Summary\n\nThe data flow within the radar_toolbox module follows these general steps:\n\n1. Configuration is set up using JSON files and configuration profiles for the specific radar models.\n2. Data recording sessions are initiated, capturing the radar data and storing it in binary format.\n3. Raw binary data is processed, filtered, and organized into structured data arrays.\n4. Data is made ready for analysis, transformed into point clouds or other representations necessary for further processing and interpretation.\n\n## External Dependencies\n\nWhile the module works as an independent toolkit within the project scope, it interfaces with radar hardware and other software modules that handle advanced data analysis, visualization, and machine learning applications.\n\n## Overall Significance\n\nThe radar_toolbox module serves as the foundational toolset for FMCW radar systems, streamlining the process from initial data capture to data preparation for analytics. It emphasizes modularity, making it easier to grow and adapt the project with new functionalities."}], "gen_doc_of_file": {"path": "radar_tracking\\models\\tracking.py", "content": "from typing import List\n\nimport numpy as np\n\nfrom radar_tracking.models.clustering.cluster import Cluster\n\n\nclass ClusterTracker:\n    def __init__(self, max_height_w: float, density_distribution_w: float, nb_points_w: float, pos_w: float,\n                 keep_track_duration: float, dt: float):\n        \"\"\"\n        :param max_height_w: Weight given to max height\n        :param density_distribution_w: Weight given to density distribution\n        :param nb_points_w: Weight given to number of points\n        :param pos_w: Weight given to position\n        :param keep_track_duration: duration used to track clusters. If cluster not seen since more than this value, then\n        it is not tracked anymore.\n        :param dt: delta time between 2 updates.\n        \"\"\"\n        self.tracking_weights = {\"max_height_w\": max_height_w,\n                                 \"density_distribution_w\": density_distribution_w,\n                                 \"nb_points_w\": nb_points_w,\n                                 \"pos_w\": pos_w}\n        self.tracking_duration = keep_track_duration\n        self.dt = dt\n        self.tracked_clusters = {}  # Key=cluster value=elapsed time\n\n    def TrackNextTimeStep(self, current_clusters: List[Cluster], verbose: bool = False):\n        \"\"\"\n        Tries to match current clusters to tracked ones, according to tracking weights given at initialization.\n        If a current cluster matches a tracked one, its ID will be replaced with the previous cluster's ID.\n        :param current_clusters: Clusters to track.\n        \"\"\"\n\n        cluster_distances = []  # Stores pairs of clusters that have been compared\n        distances = []  # Stores distances between every current clusters and every tracked ones\n        # ------------ Cluster distances --------------\n        # We compute distances between each given cluster and each tracked ones\n        for current_cluster in current_clusters:\n            for tracked_cluster, t in self.tracked_clusters.items():\n                steps = round(t / self.dt)  # How many steps passed since this cluster has been tracked\n                distance = current_cluster.compute_distance(tracked_cluster, steps=steps, verbose=verbose,\n                                                            **self.tracking_weights)\n                cluster_distances.append((current_cluster, tracked_cluster))\n                distances.append(distance)\n        # ------------ Matching clusters --------------\n        # index of distance values in ascending order (smallest distance first)\n        idx_ordered_distances = np.argsort(np.array(distances))\n        matched_clusters_ids = set()  # Stores id of clusters that have been matched with another one\n        # We iterate over all cluster distance pairs, best matching pairs first (smallest distances)\n        for idx in idx_ordered_distances:\n            current_cluster, tracked_cluster = cluster_distances[idx]\n            # We check if current_cluster and tracked_cluster haven't been already matched\n            if (current_cluster.id in matched_clusters_ids) or (tracked_cluster.id in matched_clusters_ids):\n                continue  # If yes: no math, we analyze the next cluster_distances pair\n            steps = round(self.tracked_clusters[\n                              tracked_cluster] / self.dt)  # How many steps passed since this cluster has been tracked\n            if verbose:\n                print(f\"match : {current_cluster.id} => {tracked_cluster.id}\")\n            current_cluster.UpdateFromCluster(other_cluster=tracked_cluster, lagging_steps=steps)\n            matched_clusters_ids.add(current_cluster.id)\n        # ------------ Tracked Clusters Update ------------\n        clusters_to_untrack = []\n        for tracked_cluster, t in self.tracked_clusters.items():\n            # We check if any tracked cluster hasn't been paired\n            if tracked_cluster.id not in matched_clusters_ids:  # Unmatched clusters\n                if t > self.tracking_duration:  # If not matched since too long\n                    clusters_to_untrack.append(tracked_cluster)  # Then we remove this cluster from the tracking list\n                else:\n                    self.tracked_clusters[tracked_cluster] += self.dt  # Time since last match update\n            else:\n                clusters_to_untrack.append(tracked_cluster)\n        for cluster in clusters_to_untrack:\n            del self.tracked_clusters[cluster]\n        for cluster in current_clusters:\n            self.tracked_clusters[cluster] = self.dt\n\n    def serialize(self):\n        return [cluster.serialize_cluster() for cluster in self.tracked_clusters.keys()]\n\n\n"}}