How to genetate random number under constraint
조회 수: 6(최근 30일)
표시 이전 댓글
Muhammad Nabeel Hussain 2019년 9월 26일
댓글: Siavash Soltanahmadi 2021년 2월 14일
I want to genetate two vector X(size=37x1) and Y(size=37x1) of random numbers between
100 to 1900 such that difference between any two numbers of one vector X or Y should be greater than 200.
I have tried generating random number again and again while rejecting if they dont met constraint.
but it make infinte loop.
Actually X and Y are cordinates of turbines. Constraint is no turbine can be in the 200 meter radius of any other turbine. Any idea for doing this very fast? Thanks
댓글 수: 6
편집: Adam Danz 2019년 9월 26일
This takes milliseconds.
The main idea is to start off with a set of random coordinates and continually replace coordinates that are too close to another coordinate until either 1) all distances are less than the minimum distance requirement or 2) 100 attempts were made per coordinate.
nPoints = 37; %number of coordinates
lim = [100,1900]; %bounds of random numbers
minDist = 200; %minimum distance between turbines
% Create random coordinates and continually replace coordinates
% that are too close to another point. Stop when minimum distance
% is satisfied or after making nPoints*100 attempts.
xy = nan(nPoints,2);
c = 0; %Counter
while any(isnan(xy(:))) && c<(nPoints*100)
% Fill NaN values with new random coordinates
xy(isnan(xy)) = rand(1,sum(isnan(xy(:)))) * (lim(2)-lim(1)) + lim(1);
% Identify rows that are too close to another point
[~,isTooClose] = find(triu(squareform(pdist(xy)) < minDist,1));
% Replace too-close coordinates with NaN
xy(isTooClose,:) = NaN;
c = c+1;
% Throw error if the loop had to quit and missing values remain
error('The while-loop gave up. There are %d coordinates with missing values.',sum(isnan(xy(:,1))))
% Display number of attempts
fprintf('%d number of attempts.\n', c)
% Show the minimum distance
distances = squareform(pdist(xy));
fprintf('Min distance = %.2f\n', min(distances(distances~=0)))
% Plot results
plot(xy(:,1),xy(:,2), 'ks', 'MarkerSize', 10)
These data in the figure above were produced in <0.08 sec and the minimum distance between coordinates is 205.52.
댓글 수: 3
Siavash Soltanahmadi 2021년 2월 14일
Dear @Adam Danz,
Is there a way we could generate a second set of random number within the same range specified for the first set of random number, where the numbers in the second set are constrained by a different value to the first constraint?
To clarify, imagine within a same space we aim to obtain 12 coordinates, the minimum separation between 10 random coordinates has to be “2” and the minimum separation between another 2 coordinates (and between these 2 and the first 10 coordinates) has to be “5”.
Jos (10584) 2019년 9월 26일
Brute force attempt:
N = 20 ;
xyRange = [100 1900] ;
minimumDistance = 200 ;
attempt_counter = 1 ;
Distances = 0 ;
while any(Distances < minimumDistance) && attempt_counter < 10000
attempt_counter = attempt_counter + 1 ;
Pxy = randi(xyRange, N, 2) ;
Distances = pdist(Pxy) ;
if attempt_counter < 1000
plot(Pxy(:,1), Pxy(:,2),'bo') ;
disp('No positions found.') ;
Find more on Annotations 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!