2017-05-24 9 views
1

2dボックスに円形粒子のモーションをシミュレートするコードを記述しました。彼らが箱の外に出るたびに、箱の中と壁の近くに入れます。私は2つの円の中心間の距離が2R以下になると、それらの中心を結ぶ線に沿って円の中心間の距離が離れるように分離することを意味するコードの直径(2R)をコードに追加したい2Rに等しい。Matlabで互いに衝突できないランダムウォーカーをシミュレート

パーティクルの重なりを避けるコードを提案する人はいませんか?

これが重複している私のコードでは考慮されていません。ここで

clear all 
close all 
l = 224; nn = 800; %number of particles 
time = 1000; dd = 1; 
x= l*rand(1,nn); 
y= l*rand(1,nn); 

for t = 1:time; 
x= x + rand(1,nn)-0.5* ones(1,nn); 
y=y+rand(1,nn)-0.5* ones (1,nn); 
index = (x < 0); x(index) = abs(normrnd(0,1,1,nnz(index))); 
index = (y < 0); y(index) = abs(normrnd(0,1,1,nnz(index))); 
index = (x > l); x(index) = l-abs(normrnd(0,1,1,nnz(index))); 
index = (y > l); y(index) = l-abs(normrnd(0,1,1,nnz(index))); 
end 
+0

だから、それが壁に接触するまで各粒子は、それが「跳ね返る」と、直進し、あなたはまた、粒子の粒子を含めたいです衝突? – Wolfie

+0

2つの円の中心間の距離が2R以下になると、各ステップの方向と長さのステップが変化します(乱数を使用しています).2つの円の中心間の距離が2R以下になると、円の中心の数が@Wolfieと等しくなる –

+0

お願いしますか? @ Wolfie –

答えて

2

は何をしたいんいくつかのコメントのコードです。特に:

  • psizeは、相互作用のために定義された粒度である。
  • pdist2を使用してポイントツーポイントの距離が見つかりました。
  • あまりにも近い点は、ある距離(dp倍の現在の距離、dp=1/2の場合、xとyの距離が2倍の場合)で互いに離れて衝突がなくなるまで移動します。

詳細については、コメントを参照してください。

clear; close all; 
l = 224; nn = 800; % number of particles 
time = 100; 
x = l*rand(1,nn); y = l*rand(1,nn); 
psize = 2;   % Particle size for interaction 
dp = 0.1; 

figure; hold on; axis([0 l 0 l]); 
for t = 1:time; 
    % Random movement 
    movement = 2*rand(2,nn)-1; 
    x = x + movement(1,:); 
    y = y + movement(2,:); 
    index = (x < 0); x(index) = abs(normrnd(0,1,1,nnz(index))); 
    index = (y < 0); y(index) = abs(normrnd(0,1,1,nnz(index))); 
    index = (x > l); x(index) = l-abs(normrnd(0,1,1,nnz(index))); 
    index = (y > l); y(index) = l-abs(normrnd(0,1,1,nnz(index))); 

    % Particle interaction. Loop until there are no clashes. For 
    % robustness, some max iteration counter should be added! 
    numclash = 1; 
    while numclash > 0 
     dists = pdist2([x;y]', [x;y]'); % Distances between all particles 
     dists(dists < psize) = NaN;  % Those too close are assigned NaN 
     tooclose = isnan(tril(dists,-1)); % All NaNs identified by logical 
     [clash1,clash2] = find(tooclose); % Get particles which are clashing 
     numclash = numel(clash1);   % Get number of clashes 
     % All points where there was a clash, move away from each other 
     x(clash1) = x(clash1) + (x(clash1)-x(clash2))*dp; 
     x(clash2) = x(clash2) - (x(clash1)-x(clash2))*dp; 
     y(clash1) = y(clash1) + (y(clash1)-y(clash2))*dp; 
     y(clash2) = y(clash2) - (y(clash1)-y(clash2))*dp; 
    end 

    % Plot to visualise results. Colour fade from dark to bright green over time 
    scatter(x,y,'.','markeredgecolor',[0.1,t/time,0.4]); 
    drawnow; 
end 
hold off 

結果:

random walk


編集:

明確図について、あなたは

scatter(x,y,[],C*(t/time),'.'); % the (t/time) factor makes it fade from dark to light 
を使用して、いくつかのカラーマトリックス C = rand(nn,3);とプロットを初期化することができ

これは、以前と同じように暗い色から明るい色にフェードするのではなく、暗い色から明るい色に消える色を各粒子に与えます。結果はこのようなものになるだろう:

colours

+0

私はclash1とclash2 –

+0

'clash1'の各パーティクルは' clash2'の対応するパーティクルと衝突します。私は分かりませんが、実際に衝突しているかどうかを明確に確認できるように、正しいサイズの円としてパーティクルを使用してください。この回答がうまくいく場合は、それを合格とマークしてください。 – Wolfie

+0

5個または8個のパーティクルがtogheterに衝突すると、コードは正常に機能しますか? –

関連する問題