in reply to Re^5: Unclear about 'our'
in thread Unclear about 'our'

One contrived example, using a private config-val instead of a public package var.
my $config = 42; my $change_allowed = 0; sub mult { $_[0] * $config } sub get_config { $config } sub set_config { $config = shift if $change_allowed; } # yadda

of course you could also put only those subs inside an extra block together with the closure var.

Cheers Rolf
(addicted to the 𐍀𐌴𐍂𐌻 Programming Language :)
Wikisyntax for the Monastery

Replies are listed 'Best First'.
Re^7: Unclear about 'our'
by haukex (Archbishop) on Dec 29, 2022 at 08:58 UTC
    of course you could also put only those subs inside an extra block together with the closure var.

    Ok, I see what you mean. Personally, I tend to think of closures as something you can make multiple instances of (sub foo { my $x=0; return sub {$x++} }), but if the code you showed was in a block, then I guess that can fit the definition of a closure too, since the subs are then the only thing to hold references to the variables.

      > Personally, I tend to think of closures as something you can make multiple instances of

      That's a further concept, building on top of closures.

      In what you show foo is a "generator" returning an anonymous sub, which is indeed enclosing $x ... but that's not necessary for a closure.

      A "closure" is the combination of a sub and "enclosed"° vars from the outer scope.

      you don't need generators for closures...

      see also Closure (computer programming) : "Operationally, a closure is a record storing a function together with an environment."

      But it's true that many - including me - often simply say "closure" for the "closure function"

      > but if the code you showed was in a block, then I guess that can fit the definition of a closure too

      an explicit block is just cosmetics, since the file-scope acts as a default block.

      > since the subs are then the only thing to hold references to the variables.

      That's bit confusing ... a sub will only hold reference to a variable form a surrounding scope if it's enclosed, i.e. explicitly used. You don't need a block to enforce this.

      Consider this example, where the second bar() will fail because there is no explicit use of $var, just a symbolic reference.

      Since it's not bound - here realized as the scratch pads of the sub increasing the ref-count - it can be destroyed.

      NB: I just need the block here because all calls are in the same file.

      use v5.12; use warnings; use Data::Dump qw/pp dd/; { my $var = 42; sub foo { warn $var; } sub bar { eval 'warn $var'; } foo(); bar(); } foo(); bar();

        42 at c:/tmp/pm/closure_demo.pl line 9. 42 at (eval 1) line 1. 42 at c:/tmp/pm/closure_demo.pl line 9. Variable "$var" is not available at (eval 2) line 1. Use of uninitialized value $var in warn at (eval 2) line 1. Warning: something's wrong at (eval 2) line 1.

      Cheers Rolf
      (addicted to the 𐍀𐌴𐍂𐌻 Programming Language :)
      Wikisyntax for the Monastery

      updates

      °) lexical vars in this case, package vars are just globally available...

        an explicit block is just cosmetics, since the file-scope acts as a default block.

        I'd be surprised if the definition of a closure really is that broad, but I don't have the time to research in detail right now. Update: To clarify: I did skim the Wikipedia article before posting and it makes it pretty clear to me that definitions differ, so I suspect that simply our definitions differ. In the context of Perl, perlglossary does say that a closure is "An anonymous subroutine that, when a reference to it is generated at runtime, keeps track of the identities of externally visible lexical variables, even after those lexical variables have supposedly gone out of scope."

        Update 2: Ok, so I did do at least a little bit more research. The above definition of a closure is repeated across much of the Perl documentation, but then there's Persistent variables with closures that shows a named sub that is closer to what you showed. So like I said, I guess definitions differ.

        > In what you show foo is a "generator" returning an anonymous sub,

        I have to somehow correct myself, because I can't find this definition of "generator" anymore. Maybe I saw it in HOP.

        I tried to reference WP, but Generator (computer programming) refers to something different. That's the yield concept from Python (gather-take in Raku), which is not a closure maker, but syntactic sugar for an iterator.

        Looks like the programming world is taking over the Python interpretation, ECMA6 introduced yield too.

        Cheers Rolf
        (addicted to the 𐍀𐌴𐍂𐌻 Programming Language :)
        Wikisyntax for the Monastery