How to create a solid spherical cluster with random distribution of points

2 views (last 30 days)
Hi all, Kindly help me with this.. I need to create a solid (3D) spherical cluster of n random points with 0 as centroid and radius as 2. Points not just on the surface but inside the spherical cluster too. Somewhat like this http://www.mlahanas.de/MOEA/HDRMOGA/Image105.gif
Moreover i want to save all the distances of these random points from centroid in a variable.
Thanks a ton
  2 Comments
Walter Roberson
Walter Roberson on 12 Apr 2012
What properties should the random distribution have? Uniform in volume? Equal-spaced concentric shells? Equal angle? Expotential Do the points have an associated volume or can they be placed arbitrarily close to each other?
Matt Kindig
Matt Kindig on 12 Apr 2012
Vinita, all of Walter's questions are worth considering. My proposed solution does what you want, but will (by the nature of uniform distributions) tend to make points closer to the centroid really close together, which might need be useful to you.

Sign in to comment.

Answers (3)

James Tursa
James Tursa on 13 Apr 2012
Here is my cut at it.
The asin( ) correction is to take care of the fact that we need progressively fewer samples as we get closer to the poles as a function of phi. The relative proportion is governed by the cos function, integrate that to get a sin distribution, and then invert that to get the actual function we need to use on our uniform random samples.
The ^(1/3) is to take care of the fact that as we move out in radius the distribution needs to progressively get more samples. Volume increases by cube of radius, so invert that to get the (1/3) exponent to use on our uniform random samples.
Seems to get the expected results for various spherical sections and spherical caps.
% Uniformly distributed points inside sphere of radius R
% James Tursa
%/
centroid = [0 0 0]; % Center of sphere
R = 2; % Radius of sphere
n = 10000000; % Number of points
phi = asin(2*rand(n,1)-1); %phi between -pi/2 and pi/2, tapering at poles
theta = 2*pi*rand(n,1); %theta between 0 and 2pi
radius = R*rand(n,1).^(1/3); %radius between 0 and R, biased outwards for volume
[x,y,z] = sph2cart(theta, phi, radius);
xyz = [ x+centroid(1), y+centroid(2), z+centroid(3)];
%\
% Visualize
%/
plot3(x,y,z,'.');
grid on
%\
% Check expected number inside smaller volumes
%/
V = (4/3)*pi*R^3;
h = 0.50*R;
h34 = 0.75*R;
Vhalf = (4/3)*pi*h^3;
V34 = (4/3)*pi*h34^3;
r = sqrt(x.*x+y.*y+z.*z);
a = sqrt(R^2 - (R-h)^2);
Vcap = (pi*h/6)*(3*a^2+h^2);
disp(' ');
fprintf('R = %f , h = %f , g = %f\n',R,h,h34);
disp(' ');
fprintf('Expected number of samples inside radius h = %d\n',n*Vhalf/V);
fprintf('Actual number of samples inside radius h = %d\n',sum(r<h));
disp(' ');
fprintf('Expected number of samples inside radius g = %d\n',n*V34/V);
fprintf('Actual number of samples inside radius g = %d\n',sum(r<h34));
disp(' ');
fprintf('Expected number of samples inside spherical cap h = %d\n',round(n*Vcap/V));
fprintf('Actual number of samples inside spherical cap x > h = %d\n',sum(x> h));
fprintf('Actual number of samples inside spherical cap x <-h = %d\n',sum(x<-h));
fprintf('Actual number of samples inside spherical cap y > h = %d\n',sum(y> h));
fprintf('Actual number of samples inside spherical cap y <-h = %d\n',sum(y<-h));
fprintf('Actual number of samples inside spherical cap z > h = %d\n',sum(z> h));
fprintf('Actual number of samples inside spherical cap z <-h = %d\n',sum(z<-h));
disp(' ');
  3 Comments
Vinita
Vinita on 13 Apr 2012
This is great.
But now the only problem is that I need only the magnitude of the distances of the points from the centroid(only the magnitude of polar coordinates).Look at this figure :-
http://1.bp.blogspot.com/_wrPEFjzD-9o/TTiqlLzm_fI/AAAAAAAAFe8/rY3WVP39nFo/s400/graph+paper+polar+coordinates.PNG
So I need only thr r (magnitude/distance part) from the centroid for each point.
What we have right now is x,z & z coordinates of each point.
Thats it
James Tursa
James Tursa on 13 Apr 2012
Ummmm ... the r you are talking about sounds like the r that is already in the code. Am I missing something?

Sign in to comment.


Matt Kindig
Matt Kindig on 12 Apr 2012
centroid = [0 0 0];
Rad = 2; %desired radius
n = 100; %or however many points you want
phi = 2*pi*rand(n,1); %phi between 0 and 2pi
theta = pi*rand(n,1); %theta between 0 and pi
radius = Rad*rand(n,1); %radius between 0 and Rad
[x,y,z] = sph2cart(theta, phi, radius);
xyz = [ x+centroid(1), y+centroid(2), z+centroid(3)];
%'radius' contains the distances to the centroid
  4 Comments
Vinita
Vinita on 13 Apr 2012
Thanks a ton Matt Kindig !!!!
Could you pls tell me if these points are randomly distributed or not.
Because thats the main concern
Richard Brown
Richard Brown on 13 Apr 2012
They'll be clustered about the centre and also more dense towards the north and south pole

Sign in to comment.


Richard Brown
Richard Brown on 13 Apr 2012
Here's the lazy (no thinking, no maths) way. It will be slow(ish), but serves to illustrate the idea. I'm sure you can think up optimisations if you require them.
n = 1000;
i = 0;
X = zeros(3, n);
while i < n
x = 4*rand(3, 1) - 2;
if norm(x) <= 2
i = i + 1;
X(:, i) = x;
end
end
plot3(X(1,:), X(2,:), X(3,:), '.'), axis equal

Categories

Find more on Mathematics in Help Center and File Exchange

Community Treasure Hunt

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

Start Hunting!