How to parallelise sections of my for loop
    3 vues (au cours des 30 derniers jours)
  
       Afficher commentaires plus anciens
    
Hello, 
I am trying to think of a way to make my for loop quicker. It has occurred to me that I could parallelise the commands in the loops and then bring them back together at the end. Is there such a thing in matlab or am I overcomplicating everything?
My MWE is:
for kx = 1:length(w) 
    for ky = 1:length(w) %These could be linearised
        for kkx = 1:length(w)
            for kky = 1:length(w)
                for freq_sign_ansatz = 1:2 
                    for freq_sign_test = 1:2
                        [pqf, v1qf, v2qf, pw1f, pw2f, v1w1f, v1w2f, v2w1f, v2w2f] = Convection_basis(kx,ky,kkx,kky,w, freq_ansatz, freq_test);
                        pq_freq(freq_sign_ansatz, freq_sign_test) = pqf(kx,ky,kkx,kky,freq_ansatz, freq_test);
                        v1w1_freq(freq_sign_ansatz, freq_sign_test) = v1w1f(kx,ky,kkx,kky,freq_ansatz, freq_test);
                        v1w2_freq(freq_sign_ansatz, freq_sign_test) = v1w2f(kx,ky,kkx,kky,freq_ansatz, freq_test);
                        v2w1_freq(freq_sign_ansatz, freq_sign_test) = v2w1f(kx,ky,kkx,kky,freq_ansatz, freq_test);
                        v2w2_freq(freq_sign_ansatz, freq_sign_test) = v2w2f(kx,ky,kkx,kky,freq_ansatz, freq_test);
                        pw1_freq(freq_sign_ansatz, freq_sign_test) = pw1f(kx,ky,kkx,kky,freq_ansatz, freq_test);
                        pw2_freq(freq_sign_ansatz, freq_sign_test) = pw2f(kx,ky,kkx,kky,freq_ansatz, freq_test);
                        v1q_freq(freq_sign_ansatz, freq_sign_test) = v1qf(kx,ky,kkx,kky,freq_ansatz, freq_test);
                        v2q_freq(freq_sign_ansatz, freq_sign_test) = v2qf(kx,ky,kkx,kky,freq_ansatz, freq_test);
                     end
                end 
                index = [(kx - 1) * Length_Wavenumbers + ky, (kkx - 1) * Length_Wavenumbers + kky];
                if w(kkx) == w(kx) && w(kx) == 0 && (w(kky) == w(ky) && w(kky) == 0) && zero_counter == 0
                    zero_counter = 1;
                    zero_entries(zero_counter) = {index};
                end
                pq{index(1), index(2)} = pq_freq; %pd_dxw
                v1w1{index(1), index(2)} = v1w1_freq; %pd_dxw
                v1w2{index(1), index(2)} = v1w2_freq; %pd_dxw
                v2w1{index(1), index(2)} = v2w1_freq; %pd_dxw
                v2w2{index(1), index(2)} = v2w2_freq; %pd_dxw
                pw1{index(1), index(2)} = pw1_freq; %pd_dxw
                pw2{index(1), index(2)} = pw2_freq; %pd_dxw
                v1q{index(1), index(2)} = v1q_freq; %vd_dxq
                v2q{index(1), index(2)} = v2q_freq; %vd_dxq
             end
        end
    end
end
Clearly here I could linearise some of the for loops through combinations of kx,ky,kkx,kky but I was interested whether there is a way of parallelising it as each pw1 etc are square matrices which are independent of each other before I combine them into a cell. 
I am new to the way of parallelising things. 
0 commentaires
Réponse acceptée
  Gaurav Garg
    
 le 12 Oct 2020
        Hi,
Rather than using 4-6 for loops, you can try making a single for loop traversing through all the elements. 
For example -
for i = 1:2
    for j = 1:2
        %do anything
    end
end
can be rewritten as (using parfor loop)
parfor i=1:4
    [r,c] = ind2sub([2 2],i)
    disp(r);
    disp(c);
end
Here, ind2sub function has been used to convert the single iterator into r and c which are the iterators i and j in the first case.
Similarly you can rewrite your loops as (not tested)-
parfor x = 1:length(w)*length(w)*length(w)*length(w)
    [kx, ky, kkx, kky] = ind2sub([length(w) length(w) length(w) length(w)],x);
end
Plus de réponses (0)
Voir également
Catégories
				En savoir plus sur Loops and Conditional Statements dans Help Center et File Exchange
			
	Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!

