Skip to content

Commit

Permalink
Merge pull request #32 from quantumjot/update-docstrings
Browse files Browse the repository at this point in the history
First pass update of docstrings
  • Loading branch information
quantumjot authored May 27, 2021
2 parents 618a2de + 4ef424d commit 8ce4304
Show file tree
Hide file tree
Showing 8 changed files with 537 additions and 225 deletions.
112 changes: 112 additions & 0 deletions CONFIGURATION.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,112 @@
# Guide to `btrack` configuration parameters

This is a short guide to the configuration parameters for `btrack`

## Miscellaneous parameters
+ `max_search_radius` - the maximum search radius in isotropic unit of the data
+ `mode` - the update mode for the tracker
+ `volume` - estimate of the dimensions of the imaging volume


## Motion model
```json
"MotionModel": {
"name": "cell_motion",
"dt": 1.0,
"measurements": 3,
"states": 6,
"accuracy": 7.5,
"prob_not_assign": 0.001,
"max_lost": 5,
"A": {
"matrix": [1,0,0,1,0,0,
0,1,0,0,1,0,
0,0,1,0,0,1,
0,0,0,1,0,0,
0,0,0,0,1,0,
0,0,0,0,0,1]
},
"H": {
"matrix": [1,0,0,0,0,0,
0,1,0,0,0,0,
0,0,1,0,0,0]
},
"P": {
"sigma": 150.0,
"matrix": [0.1,0,0,0,0,0,
0,0.1,0,0,0,0,
0,0,0.1,0,0,0,
0,0,0,1,0,0,
0,0,0,0,1,0,
0,0,0,0,0,1]
},
"G": {
"sigma": 15.0,
"matrix": [0.5,0.5,0.5,1,1,1]

},
"R": {
"sigma": 5.0,
"matrix": [1,0,0,
0,1,0,
0,0,1]
}
}
```
+ `name` - this is the name of the model
+ `measurements` - the number of measurements of the system (e.g. x, y, z)
+ `states` - the number of states of the system (typically >= measurements)
+ `A` - State transition matrix
+ `B` - Control matrix
+ `H` - Observation matrix
+ `P` - Initial covariance estimate
+ `Q` - Estimated error in process
+ `R` - Estimated error in measurements
+ `accuracy` - integration limits for calculating the probabilities
+ `dt` - time difference, always 1
+ `max_lost` - number of frames without observation before marking a track as lost
+ `prob_not_assign` - the default probability to not assign a track
+ `sigma` - a scalar multiplication factor used for each matrix

## Hypothesis model

Below is an example of a configuration for the global optimizer.

```json
"HypothesisModel": {
"name": "cell_hypothesis",
"hypotheses": ["P_FP", "P_init", "P_term", "P_link", "P_branch", "P_dead"],
"lambda_time": 5.0,
"lambda_dist": 5.0,
"lambda_link": 5.0,
"lambda_branch": 5.0,
"eta": 1e-150,
"theta_dist": 5.0,
"theta_time": 5.0,
"dist_thresh": 10,
"time_thresh": 3,
"apop_thresh": 2,
"segmentation_miss_rate": 0.1,
"apoptosis_rate": 0.1,
"relax": false
}
```

The parameters are, as follows:
* `name` - this is the name of the model
* `hypotheses` - this is a list of hypotheses to generate for the optimizer
* `lambda_time` - a scaling factor for the influence of time when determining initialization or termination hypotheses
* `lambda_dist` - a scaling factor for the influence of distance at the border when determining initialization or termination hypotheses
* `lambda_link` - a scaling factor for the influence of track-to-track distance on linking probability
* `lambda_branch` - a scaling factor for the influence of cell state and position on division (mitosis/branching) probability
* `eta` - default low probability
* `theta_dist` - a threshold (in pixels) for the distance from the edge of the FOV to add an initialization or termination hypothesis
* `theta_time` - a threshold (in frames) for the time from the beginning or end of movie to add an initialization or termination hypothesis
* `dist_thresh` - bin size for considering hypotheses
* `time_thresh` - bin size for considering hypotheses
* `apop_thresh` - number of apoptotic detections, counted consecutively from the back of the track, to be considered a real apoptosis
* `segmentation_miss_rate` - miss rate for the segmentation, e.g. 1/100 segmentations incorrect = 0.01
* `apoptosis_rate` - rate of apoptosis detections
* `relax` - disables the `theta_dist` and `theta_time` thresholds to create termination and intialization hypotheses

## Object model
3 changes: 3 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -141,6 +141,9 @@ print(track_zero.children)
print(track_zero.generation)

```
### Configuration

For a complete guide to configuration, see `CONFIGURATION.md`.

### Visualizing track data with napari

Expand Down
150 changes: 89 additions & 61 deletions btrack/btypes.py
Original file line number Diff line number Diff line change
Expand Up @@ -27,20 +27,16 @@


class PyTrackObject(ctypes.Structure):
""" TrackObject
"""The base `btrack` track object.
Attributes
----------
Notes
-----
Primitive class to store information about an object. Essentially a single
object in a field of view, with some member variables to keep track of data
associated with an object.
Args:
position: 2D/3D position
dummy: is this a real object or a dummy object (e.g. when lost)
label: object classification
properties: object attributes, essentially metadata about object
Properties:
probability: class label probabilities
"""

_fields_ = [
Expand Down Expand Up @@ -181,13 +177,7 @@ def tracker_active(self):


class MotionModel:
""" MotionModel
Kalman filter:
'Is an algorithm which uses a series of measurements observed over time,
containing noise (random variations) and other inaccuracies, and produces
estimates of unknown variables that tend to be more precise than those that
would be based on a single measurement alone.'
"""The `btrack` motion model
Args:
name: a name identifier
Expand All @@ -209,10 +199,15 @@ class MotionModel:
if they are incorrectly sized.
load(): load a motion model from a JSON file.
Notes:
This is just a wrapper for the data with a few convenience functions
thrown in. Matrices must be stored Fortran style, because Eigen uses
column major and Numpy uses row major storage.
Notes
-----
'Is an algorithm which uses a series of measurements observed over time,
containing noise (random variations) and other inaccuracies, and produces
estimates of unknown variables that tend to be more precise than those that
would be based on a single measurement alone.'
This is just a wrapper for the data with a few convenience functions
thrown in. Matrices must be stored Fortran style, because Eigen uses
column major and Numpy uses row major storage.
References:
'A new approach to linear filtering and prediction problems.'
Expand Down Expand Up @@ -285,7 +280,7 @@ def load(filename):


class ObjectModel:
""" ObjectModel
"""The `btrack` object model.
This is a class to deal with state transitions in the object, essentially
a Hidden Markov Model. Makes an assumption that the states are all
Expand Down Expand Up @@ -329,39 +324,72 @@ def load(filename):


class Tracklet:
""" Tracklet
"""A `btrack` Tracklet object used to store track information.
Parameters
----------
ID : int
A unique integer identifier for the tracklet.
data : list[PyTrackObject]
The objects linked together to form the track.
parent : int,
The identifiers of the parent track(s).
children : list
The identifiers of the child tracks.
fate : constants.Fates, default = constants.Fates.UNDEFINED
An enumerated type describing the fate of the track.
Attributes
----------
x : list[float]
The list of x positions.
y : list[float]
The list of y positions.
z : list[float]
The list of z positions.
t : list[float]
The list of timestamps.
dummy : list[bool]
A list specifying which objects are dummy objects inserted by the tracker.
parent : int, list
The identifiers of the parent track(s).
refs : list[int]
Returns a list of PyTrackObject identifiers used to build the track.
Useful for indexing back into the original data, e.g. table of
localizations or h5 file.
label : list[str]
Return the label of each object in the track.
state : list[int]
Return the numerical label of each object in the track.
softmax : list[float]
If defined, return the softmax score for the label of each object in the
track.
properties : Dict[str, np.ndarray]
Return a dictionary of track properties derived from PyTrackObject
properties.
root : int,
The identifier of the root ID if a branching tree (ie cell division).
is_root : boole
Flag to denote root track.
is_leaf : bool
Flag to denote leaf track.
start : int, float
First time stamp of track.
stop : int, float
Last time stamp of track.
kalman : np.ndarray
Return the complete output of the kalman filter for this track. Note,
that this may not have been returned while from the tracker. See
`BayesianTracker.return_kalman` for more details.
Notes
-----
Tracklet object for storing and updating linked lists of track objects.
Forms the data structure for an individual tracklet.
Track 'fates' are the selected hypotheses after optimization. Defined in
constants.Fates
Intrinsic properties can be accesses as attributes, e.g:
track.x returns the track x values
Args:
ID: unique identifier
data: trajectory
kalman: Kalman filter output
labels: class labels for each object
fate: the fate of the track
Members:
__len__: length of the trajectory in frames (including interpolated)
Properties:
x: x position
y: y position
z: z position
parent: parent tracklet
root: root tracklet if a branching tree (ie cell division)
motion_model: typically a reference to a Kalman filter or motion model
is_root: boolean flag to denote root track
is_leaf: boolean flag to denote leaf track
start: first time stamp of track
stop: last time stamp of track
Forms the data structure for an individual tracklet. Track 'fates' are the
selected hypotheses after optimization. Defined in constants.Fates. Intrinsic
properties can be accesses as attributes, e.g: track.x returns the track
x values.
"""

def __init__(
Expand Down Expand Up @@ -508,21 +536,21 @@ def kalman(self, data):
self._kalman = data

def mu(self, index):
""" Return the Kalman filter mu. Note that we are only returning the mu
for the positions (e.g. 3x1) """
"""Return the Kalman filter mu. Note that we are only returning the mu
for the positions (e.g. 3x1)."""
return np.matrix(self.kalman[index, 1:4]).reshape(3, 1)

def covar(self, index):
""" Return the Kalman filter covariance matrix. Note that we are
only returning the covariance matrix for the positions (e.g. 3x3) """
"""Return the Kalman filter covariance matrix. Note that we are
only returning the covariance matrix for the positions (e.g. 3x3)."""
return np.matrix(self.kalman[index, 4:13]).reshape(3, 3)

def predicted(self, index):
""" Return the motion model prediction for the given timestep. """
return np.matrix(self.kalman[index, 13:]).reshape(3, 1)

def to_dict(self, properties: list = constants.DEFAULT_EXPORT_PROPERTIES):
""" Return a dictionary of the tracklet which can be used for JSON
"""Return a dictionary of the tracklet which can be used for JSON
export. This is an ordered dictionary for nicer JSON output.
"""
trk_tuple = tuple([(p, getattr(self, p)) for p in properties])
Expand All @@ -540,10 +568,10 @@ def to_array(self, properties: list = constants.DEFAULT_EXPORT_PROPERTIES):
return tmp_track

def in_frame(self, frame):
""" Return true or false as to whether the track is in the frame """
"""Return true or false as to whether the track is in the frame."""
return self.t[0] <= frame and self.t[-1] >= frame

def trim(self, frame, tail=75):
""" Trim the tracklet and return one with the trimmed data """
"""Trim the tracklet and return one with the trimmed data."""
d = [o for o in self._data if o.t <= frame and o.t >= frame - tail]
return Tracklet(self.ID, d)
Loading

0 comments on commit 8ce4304

Please sign in to comment.