Code for getting statistics on movement tracks (coordinates) of agents

3 Ansichten (letzte 30 Tage)
I'm looking for any existing code, Matlab toolkit, or whatever, to help this task: given X,Y coordinate pairs of moving discrete agents in several classes (e.g., A, B), calculate statistics like whether a given class's agents tend to approach some class’s agents more than others, mean path length, persistence, etc. across the classes, and whether objects convert classes after specific touching events? Specifically, I’ve got red and green cells moving around on a flat surface and I have their positions as a function of time. I want to analyze their behavior (a video of their movement over time) to find any patterns of how they move, whom they preferentially get close to, and whether they change colors after hanging out with a specific type (more than null hypothesis). The more relationships (patterns) could be discovered, the better (e.g., are there unbiased machine learning packages that could extract patterns that I didn't even think to test). I would be happy with code that does object tracking, or I can do that in another pre-processing routine and just have data like
timestamp, X position, Y position, color
for some dozens of agents, over time. Any ideas for how to extract any significant relationships between the variables across agents?

Akzeptierte Antwort

Image Analyst
Image Analyst am 5 Aug. 2018
You need to get this book:
Analysing spatial point patterns in R
Adrian Baddeley
CSIRO and University of Western Australia
Adrian.Baddeley@csiro.au
adrian@maths.uwa.edu.au
It's the bible of spatial statistics. You should look at the Morishita plot and Fry plot. They describe the tendency for points of certain classes to avoid or attract each other. Here is a snippet:
18 Exploring dependence between points
Suppose that a point pattern appears to have constant intensity, and we wish to assess whether the pattern is Poisson. The alternative is that the points are dependent (they exhibit ‘interaction’). Classical writers suggested a simple trichotomy between ‘independence’ (the Poisson process), ‘regularity’ (where points tend to avoid each other), and ‘clustering’ (where points tend to be close together). [The concept of ‘clustering’ does not imply that the points are organised into identifiable ‘clusters’; merely that they are closer together than expected for a Poisson process.]
One simple diagnostic for dependence between points is a Morishita plot. The spatial domain is divided into quadrats, and the 2 statistic based on quadrat counts is computed. The quadrats are repeatedly subdivided. The Morishita plot shows the 2 statistic against the linear size of the quadrats.
A more sophisticated option is the Fry plot. This is a scatterplot of the vector differences xj − xi between all pairs of distinct points in the pattern. Suppose you have printed the point pattern on a sheet of paper. Take a sheet of tracing paper, and mark a red dot in the middle. Now place the tracing paper over the point pattern, and move it until the red dot coincides with one of the data points. Now copy all the other data points onto the tracing paper. Repeat this for every data point, and you have the Fry plot.
Below is code to construct the Fry plot from xPoints and yPoints. It gets them from a binary image. If you already have the points, you can skip that and use your points.
% Construct Fry Plot
[rows, columns] = size(binaryImage);
fryPlot = zeros(2 * rows, 2 * columns);
[yPoints, xPoints] = find(binaryImage);
radialProfile = zeros(1, round(2 * sqrt(rows^2 + columns^2)));
sumOfRadii = 0;
numPoints = length(yPoints); % Number of points in the binary image.
for p1 = 1 : numPoints
for p2 = 1 : numPoints
if p2 == p1
continue;
end
deltaRow = yPoints(p2) - yPoints(p1) + rows;
deltaCol = xPoints(p2) - xPoints(p1) + columns;
fryPlot(deltaRow, deltaCol) = fryPlot(deltaRow, deltaCol) + 1;
radius = sqrt((deltaRow - rows)^2 + (deltaCol - columns)^2);
% Add it into the mean profile, but need to round radius to the nearest integer greater than 0.
index = round(radius)+1;
radialProfile(index) = radialProfile(index) + 1;
% Sum up the radius so we can get the mean radius.
sumOfRadii = sumOfRadii + radius;
end
end
% Get the average radius
meanRadius = sumOfRadii / (numPoints * (numPoints-1));
% axes(handles.axes2);
figure;
subplot(2, 2, 1);
% Central point is so huge because every point is zero distance from itself.
% But the ring 1 pixel away is zero because we said there could be no pixels adjacent to other pixels.
fryPlot(rows, columns) = 0; % Zero out the origin because it will have the most because every point is zero distance from itself.
% Now get mean values in a line above the center.
neighboringMean = mean(fryPlot(rows-2, columns-1:columns+1));
fryPlot(rows-1:rows+1, columns-1:columns+1) = neighboringMean; % Zero out the origin because it will have the most because every point is zero distance from itself.
imshow(fryPlot, []);
title('Fry Plot', 'FontSize', fontSize);
% Show the mean radius as a circle over the fry plot
hold on;
viscircles([columns, rows], meanRadius);
% Display histogram of radii
subplot(2, 2, 2);
histogram(fryPlot(fryPlot>0));
grid on;
title('Histogram of Radii in Fry Plot', 'FontSize', fontSize);
  2 Kommentare
Image Analyst
Image Analyst am 6 Aug. 2018
Michael, was that helpful?
You can also use pdist2() of the stats toolbox to compute distances of every point to every other point.
Michael Levin
Michael Levin am 6 Aug. 2018
Yes thank you!! I'm going over all this stuff right now. Much appreciated!

Melden Sie sich an, um zu kommentieren.

Weitere Antworten (0)

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!

Translated by