2014-04-19 2 views
1

상자에 이상적인 가스의 움직임을 시뮬레이트하도록 설계된 코드가 있습니다. 그것은 몬테카를로 시뮬레이션의 대도시 방법을 기반으로합니다. 그러나 인접한 입자를 무작위로 선택한 입자를 찾을 때 경계 조건을 정의하기 위해 일련의 논리 문 (주로 ifs)을 사용했습니다. 알고리즘은 1x4 행렬 내부의 인접한 입자에 대해 1을 나타내며 입자가없는 인접한 점에 대해서는 0을 나타냅니다. 상자 가장자리에있는 모든 입자에 대해 상자 외부의 모든 인접 점을 0으로 자동 설정하는 알고리즘이 필요합니다. 이 논리 문장을 줄이고 동일한 결과를 얻는 방법이 있습니까? 코드는 아래에, 어떤 도움을 주셔서 감사합니다.MATLAB : 로직 스먼트의 코드 효율성 향상 (메트로폴리스 메서드)

% define constants 
beta = .01; %Inverse temperature 
N=2000; %Duration of simulation 
eps = -7; 
mu=9; 


for j=1:N 
    a=randi(L); 
    b=randi(L); 
    c=randi(L); 
    d=randi(L); 
    % Calculate energy at positions 
    if lattice(a,b)==1 && lattice(c,d)==0 
     %If distribution (according to energy) suggests move, 
       lattice(a,b)=0; 
      lattice(c,d)=1; 

     %Energy at random site/position 
     E = n*(mu-eps) 
      if (a~=1&& a~=L &&b~=1 && b~=L) 
       adjacent= [lattice(a-1,b) lattice(a+1,b) lattice(a,b+1) lattice(a,b-1) 1]; 
      else if (a==1 && b==1) 
        adjacent= [0 lattice(a+1,b) lattice(a,b+1) 0 1]; 
       else if (a==L && b==L) 
         adjacent= [lattice(a-1,b) 0 0 lattice(a,b-1) 1]; 
        else if(a==1&&b==L) 
          adjacent= [0 lattice(a+1,b) 0 lattice(a,b-1) 1]; 
         else if (a==L &&b==1) 
           adjacent= [lattice(a-1,b) 0 lattice(a,b+1) 0 1]; 
          else if (a==1 && b~=L && b~=1) 
            adjacent= [0 lattice(a+1,b) lattice(a,b+1) lattice(a,b-1) 1]; 
           else if (a==L && b~=L && b~=1) 
             adjacent= [lattice(a-1,b) 0 lattice(a,b+1) lattice(a,b-1) 1]; 
            else if (b==1&&a~=L&&a~=1) 
              adjacent= [lattice(a-1,b) lattice(a+1,b) lattice(a,b+1) 0 1]; 
             else if (b==L&&a~=L&&a~=1) 
               adjacent= [lattice(a-1,b) lattice(a+1,b) 0 lattice(a,b-1) 1]; 
              end 
             end 
            end 
           end 
          end 
         end 
        end 
       end 
      end 


      E1 = mu*sum(adjacent) + eps*sum(sum(adjacent.*adjacent)); 
      %This calculates the energy of the particle at its current 
      %position 

      if (c~=1&& c~=L &&d~=1 && d~=L) 
       adjacent1= [lattice(c-1,d) lattice(c+1,d) lattice(c,d+1) lattice(c,d-1) 1]; 
      else if (c==1 && d==1) 
        adjacent1= [0 lattice(c+1,d) lattice(c,d+1) 0 1]; 
       else if (c==L && d==L) 
         adjacent1= [lattice(c-1,d) 0 0 lattice(c,d-1) 1]; 
        else if(c==1&&d==L) 
          adjacent1= [0 lattice(c+1,d) 0 lattice(c,d-1) 1]; 
         else if (c==L &&d==1) 
           adjacent1= [lattice(c-1,d) 0 lattice(c,d+1) 0 1]; 
          else if (c==1 && d~=L && d~=1) 
            adjacent1= [0 lattice(c+1,d) lattice(c,d+1) lattice(c,d-1) 1]; 
           else if (c==L && d~=L && d~=1) 
             adjacent1= [lattice(c-1,d) 0 lattice(c,d+1) lattice(c,d-1) 1]; 
            else if (d==1&&c~=L&&c~=1) 
              adjacent1= [lattice(c-1,d) lattice(c+1,d) lattice(c,d+1) 0 1]; 
             else if (d==L&&c~=L&&c~=1) 
               adjacent1= [lattice(c-1,d) lattice(c+1,d) 0 lattice(c,d-1) 1]; 
              end 
             end 
            end 
           end 
          end 
         end 
        end 
       end 
      end 


      E2 = mu*sum(adjacent) + eps*sum(sum(adjacent1.*adjacent1)); 
      %Calculates the energy at randomly chosen position. 

      dE = E2-E1; %Change in energy of the particle as it goes from the two locations. 

      if rand<exp(-beta*dE) 
       lattice(a,b)=0; 
       lattice(c,d)=1; 
      end 



    end 
time(:,:,j)=lattice; 


end 

답변

2

모든 if else 문을 사용하지 않아도됩니다. 실제로 네 개의 논리 표현식을 평가하고이를 기반으로 색인을 선택합니다. 대신 if else 문장의 첫 번째 세트의 다음

ab = [a-1, b; a+1, b; a, b+1; a, b-1]; 
abIn = [a ~= 1; a ~= L; b ~= L; b ~= 1]; 
adjacent = zeros(1, 5); 
adjacent(abIn) = lattice(sub2ind([L, L], ab(abIn, 1), ab(abIn, 2))); 
adjacent(5) = 1; 

를 사용하고,뿐만 아니라 두 번째 세트의 이름을 변경할 수 있습니다. 여기에있는 아이디어는 테두리 안에있는 lattice 값만 가져 오는 것입니다. 네 번째 논리 표현식은 여기에서 네 번째 행의 logical indexing에 사용됩니다.