w8lle has asked for the wisdom of the Perl Monks concerning the following question:

Hi!

I have a main script and a module I created myself:

main.pl:

#!/usr/bin/perl use strict; use warnings; use lib "."; use failingFormat qw (&printFormat); printFormat ("TEST", "Testing to print the TEST format.");

failingFormat.pm:

#!/usr/bin/perl use strict; use warnings; use Exporter; my $PKG = "failingFormat"; our $VERSION = "0.0.01"; our @ISA = qw (Exporter); our @EXPORT_OK = qw ( &printFormat ); my $text2print; sub printFormat { $~ = shift; $text2print = shift; write; $~ = "STDOUT"; } format TEST = ^<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<< $text2print ~~ ^<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<< $text2print . 1;

In Perl v5.8.8, this works OK, but in v5.10.0 it complains about $text2print being uninitialized. To get this to work, I have to declare $text2print in main.pl:

our $text2print

And then use that parameter in my module ($main::text2print).

Is that a feature or a fault introduced in the later version?

Replies are listed 'Best First'.
Re: Must use global variables in format in module; feature or fault?
by Anonymous Monk on Aug 22, 2012 at 02:42 UTC

    Though it isn't mentioned very explicitly, it looks like a bug that was fixed in a later version.

    Closures, eval and lexicals

    There have been many fixes in the area of anonymous subs, lexicals and closures. Although this means that Perl is now more "correct", it is possible that some existing code will break that happens to rely on the faulty behaviour. In practice this is unlikely unless your code contains a very complex nesting of anonymous subs, evals and lexicals.

    I remember from experience that you can fix your code by wrapping your format declarations in BEGIN {}

    Though I would probably switch to Perl6::Form, its all green on 5.8.8

    And @_ is already a global which you could use :)

    sub printFormat { local $~ = shift; return write; } BEGIN { format TEST = ^<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<< $_[0] ~~ ^<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<< $_[0] . our %N2I = ( text2print => 0, ); format TESTNAMEY = ^<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<< $_[$N2I{text2print}] ~~ ^<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<< $_[$N2I{text2print}] . use constant do { my $ix = 0; +{ map { $_ => $ix++ } qw[ TEXT2PRINT ] } }; format TESTNAMEDCONSTANTY = ^<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<< $_[TEXT2PRINT] ~~ ^<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<< $_[TEXT2PRINT] . }

      THANKS :-)

      I suspected this was a bug; I just couldn't find it myself. I've updated my code now...