develooper Front page | perl.perl5.porters | Postings from July 2021

Re: Review of `defer` (was: FINALLY - ready for comments/review)

Thread Previous | Thread Next
From:
Oodler 577 via perl5-porters
Date:
July 28, 2021 19:34
Subject:
Re: Review of `defer` (was: FINALLY - ready for comments/review)
Message ID:
20210728193354.GJ28661@odin.sdf-eu.org
* Paul "LeoNerd" Evans <leonerd@leonerd.org.uk> [2021-07-28 20:13:03 +0100]:

Thanks for the information, this is super helpful.

I'm still left to wonder that if, "defer" and "finally" are so similar
and in fact tied to a similar mechanism underneath; do they need to be
called different things - or is there an opportunity to simply go with
one or the other? And since Try::Tiny has already established "finally"
as way to schedule tied unconditional action, would it make sense to
proactively eliminate a potential source of confusion?

To be clear, I am not suggesting "defer" be renamed to "finally"; but
it seems like there potential to make them "look" the same.

What we will have:

# bare block
{
 defer { do stuff .. at end of block };
 ...
}

# Try::Tiny (effectively what Try::Tiny is handing via prototyping coersion):
try {
  ...
}
catch {
  ...
}
finally {
  ...
}

Something more consistent:

# consistent with Try::Tiny
sub dostuff {

}
finally {

}

~or

sub dostuff {
  finally { ... };
}

~or

# bare block (rather than 'defer')
{
  finally { ... };
  ...
}

~or

{
  ...
}
finally {
  ...
}

Finally, I'd like to point out, ever just to get it on the record;
"defer" is not "like" the others here:

* sub END {}
* try {} catch {} finally {}
* { defer {} };

I'd also like point out since we're also discussing "concurrency";
that "defer" means something different in a concurrent or asynchronous
context (to me, someone who considered himself informated on the matter)
and in a "sequential context".

Based on the overarching point on my talk about sequential consistency
and the conflicts this causes on a high level depending on talking about
perl (sequential process) or Perl (syntax that naturally invites concurrent
semantics); I ask that some soul searching be done on this topic. Lest I be
accused of bikeshedding, on the contrary I believe we can avoid adding more
communication barriers (in the community) and also take advantage of this
opportunity to err on the side of "consistency" rather than add to the entropy
or chaos that clearly already weighs us down tremendously.

So what am I suggesting?

1. fine tune the semantics of "defer" considering both TT's "finally"
2. adjust the name of "defer" (if needed) considering the mental dissonace
forced upon us by this idea of perl (sequential) and Perl (begs concurrent
semantics).

Cheers,
Brett

> On Wed, 28 Jul 2021 17:48:47 +0000
> Oodler 577 via perl5-porters <perl5-porters@perl.org> wrote:
> 
> > This part made me get it more fully:
> > 
> >    The operation can be considered a little similar to an END block
> > 
> > Since the topic of Try::Tiny and requiring a "catch" block has come
> > up, I feel like it's approproprite to request that there be some
> > consistency between a generic "defer" block and the optional
> > "finally" block of Try::Tiny.
> 
> Yes. `defer` is in many ways a prereq of adding `finally`, because once
> OP_PUSHDEFER exists, then try/finally can simply use that in its
> implementation.
> 
> > Questions:
> > 
> > a. does "defer" work if at the same "scope" as END? (and it's my
> > understanding that END is executed regardless of the predestined exit
> > code (e.g., 0, 255 (die), or something else).
> > 
> >   #foo.pl
> >   my $foo = q{bar};
> >   defer { print qq{hi!\n} };
> >   sub END {
> >     print qq{bye!\n};
> >   }
> 
> I'm not sure I follow the question here. But here's the behaviour:
> 
> $ ./perl -Ilib -I. -E 'use feature "defer";
>   defer { say "Hi!" }
>   END { say "Bye!" }
>   '
> defer is experimental at -e line 2.
> Hi!
> Bye!
> 
> > b. are there any effective differences between "defer" and
> > Try::Tiny's "finally"?
> 
> defer happens at the exit of its own containing block.
> finally of try/finally acts as if there was a containing block around
> the try/finally statement.
> 
>   {
>     defer { say "Later"; }
>     say "First";
>   }
> 
> equiv to
> 
>   try { say "First"; }
>   finally { say "Later"; }
> 
> > c. if "b" is, "not fundamentally", would it behoove us to make
> > "defer" and "finally" consistent to the point that "defer" becomes
> > "finally" and can be defined either inside the block to which it
> > apples or can be added to the end of the block as "finally" appears
> > to be in Try::Tiny ( I understand 'catch' and 'finally' are actually
> > taken to be parameters of 'try', and prototype coersion is utilize
> > for the desired effect)?
> > 
> > Ultimately, this boils down to this - it seems "defer" and "finally"
> > are similar enough in nature (at least from the effective view of the
> > developer), that it would be highly beneficial to make them
> > consistently applied from the developer perspective. If we do not
> > deeply consider this, then I am afraid we will be introducing yet
> > another inconsistency.
> 
> Yes; they'll be implemented by the same underlying mechanism. See above.
> 
> > I'd like to point on that Qore has "on_exit" for subroutines, which
> > seems like what "defer" would emulate if defined inside of a sub
> > block.
> > 
> >    https://docs.qore.org/qore-1.0.2/lang/html/statements.html#on_exit
> > 
> > I thought D lang had the same sort of thing, but I can't seem to find
> > it at this moment.
> 
> Go's `defer` operates at the function level too. It's not a great fit
> for Perl's very lexical nature.
> 
> -- 
> Paul "LeoNerd" Evans
> 
> leonerd@leonerd.org.uk      |  https://metacpan.org/author/PEVANS
> http://www.leonerd.org.uk/  |  https://www.tindie.com/stores/leonerd/

-- 
--
oodler@cpan.org
oodler577@sdf-eu.org
SDF-EU Public Access UNIX System - http://sdfeu.org
irc.perl.org #openmp #pdl #native

Thread Previous | Thread Next


nntp.perl.org: Perl Programming lists via nntp and http.
Comments to Ask Bjørn Hansen at ask@perl.org | Group listing | About