Dave Whipp wrote:
I was reading Synopsis 4 with regards to multi core programming. It
seems to be infused with a bias towards non-parallel models of
computation. Concurrently appears to be an add-on feature -- whereas
we should have a mindset that explicit sequential constraints are the
add-on feature.
Two statements that are missing from S04 (feel free to change the
names) are C<forall>; and a form of C<given> that tests/executes
multiple C<when> clauses in arbitrary order (without needing the
sequential C<continue> statement).
forall @a -> $x { ... }
runs the code block on each element of @a (no defined order). If @a is
a lazy generator then generation of values is concurrent with running
the code block on those generated values).
forall @a -> $x : sequential { ... }
forces an additional sequential constraint on the execution, such that
the Nth element of @a is not obtained until the code block has
executed for the (N-1)th. C<for> is an alias for this constrained
variant. C<for> implies this sequential constraint to avoid surprising
legacy (perl5) programmers.
Similarly, C<map>, C<classify>, C<grep>, C<reduce>, ... should all
accept this ":sequential" adverb to force them to iterate their lists
sequentially -- and should otherwise iterate in arbitrary/concurrent
order.
given $x :all { ... }
would run the code blocks of all C<when> statements (in the C<given>
block) which smart-match true against $x. The ":sequential" adverb
would be used to constrain execution of the C<when> blocks to run in
the order they appear in the source code. (it would be good if the
current C<given> could be thought of as using a ":first" modifier,
which runs the code block of the lexically first C<when> clause that
evaluates to true -- but which potentially tests multiple C<when>
clauses in parallel. Unfortunately the current language definition is
much too sequential for this viewpoint)
I think a major reason for the bias toward sequential processing is
that if code that should be processed sequentially is instead processed
concurrently then the results will almost always be incorrect.
Conversely, if code that should be processed concurrently is instead
processed sequentially, the results will be correct though the program
will take longer to run than necessary. I don't think it's unreasonable
to prefer always correct but slow to sometimes incorrect and fast,
especially if it is difficult to automatically tell which cases might
result in incorrect behavior.
On the other hand, this being Perl, I do believe it should be easy to
specify the concurrent case. I think that a <forall> keyword (and a
<givenall> keyword corresponding to <given>) would be a good idea.
These would not be quite parallel to <for> and <given> because there
would be some subtle differences arising from the concurrent
processing. For instance, <forall> probably should not be used with
<last>, because <last> should stop subsequent iterations and the
subsequent iterations could already have occurred when it is called.
Similarly, <givenall> should not be used with <continue>, because the
next case might already have been checked when <continue> is called.
Joe Gottman