Updating variable inside parfor

20 views (last 30 days)
Hello,
I have a variable that I want to update inside a parfor loop:
a = 1;
parfor i = 1: 10
a = a + 1;
disp(a);
end
How can I do this? Can I use data queues to do this, if yes, how.
I am new to parallel computing.
My goal is to print the value of a everytime it is updated.
Edit: I was able to do this as below. But it uses a global variable. Is there a better way?
global a
a = 1;
q = parallel.pool.DataQueue;
afterEach(q, @my_increment);
parfor i = 1: 10
send(q, i);
end
function my_increment(m)
global a
a = a + 1;
fprintf('a\n', x);
end
Would using persistent variables be better than this?

Accepted Answer

Raymond Norris
Raymond Norris on 13 Aug 2023
Moved: Matt J on 13 Aug 2023
The example Use a DataQueue Object and parfor to Update a Wait Bar in
will also show using a waitbar to display completion.
You could use a persistent variable (if you only want to see how many iterations are completed), which is what the above example uses
q = parallel.pool.DataQueue;
afterEach(q, @my_increment);
parfor i = 1:10
send(q, i);
end
function my_increment(~)
persistent a
if isempty(a)
a = 1;
else
a = a + 1;
end
fprintf('a: %d\n', a);
end
But there are two isues with this
  • This assumes that the loop variable always starts at 1. I would suggest you have a separate counter that always starts at 1 so that you're not dependent on the loop variable, whch might start at (say) 5.
  • Because a in my_increment is persistent, it's also persistent between runs. Therefore, if you run your code a second time, you'll start where you left off last time (i.e., at 10). You'll want to clear your function to reset your persistent variable (and assuming you didn't mlock your function ;) )
For multiple runs, you'll need to call your code as such
my_fcn
clear my_fcn
my_fcn
  3 Comments
Sean Sullivan
Sean Sullivan on 14 Sep 2023
If you just want to keep track of the total number of iterations that have been started print that number, could you just print the loop variable?
parfor idx=1:10
disp(idx)
end
Walter Roberson
Walter Roberson on 14 Sep 2023
parfor does not execute loops in order. Indeed, if you do not happen to have the Parallel Computing Toolbox, then the loops will be executed in serial in reverse order. If you do have PCT then parfor allocates chunks of iterations to workers -- so what might be displayed is 61, 81, 1, 41, 82, 83, 21 (for example). Displaying the parfor index does not give any useful information about how many iterations have been done so-far -- not unless you have been mentally counting the outputs as they go by.

Sign in to comment.

More Answers (1)

Matt J
Matt J on 12 Aug 2023
Edited: Matt J on 12 Aug 2023
The best way is as you first had it:
a=1;
parfor i = 1: 10
a = a + 1;
end
There is no way, however, that you can get the updates to display to the screen reliably in serial order (including your approach with a global variable). That is because the updates are not being processed serially. They are being processed in parallel.
  19 Comments
atharva aalok
atharva aalok on 13 Aug 2023
No I do not want things to happen serially.
I am running calculations in parallel and as @Walter Roberson pointed and my code example in the Edit, I just want to keep track of the total number of iterations that have been started and I want to print the number to see that visually.
Walter Roberson
Walter Roberson on 13 Aug 2023
Try the parfor waitbar.

Sign in to comment.

Categories

Find more on Loops and Conditional Statements in Help Center and File Exchange

Products


Release

R2022a

Community Treasure Hunt

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

Start Hunting!