in reply to How not to use "our"?

How can I improve my code to achieve a similar behaviour i.e. to be able access a common variable but without resorting to globals?
You don't. A variable either is lexical, or it can be accessed from elsewhere, and hence it's a global.
I've read in a number of places that we rarely have to declare variables with "our" and it's usually a bad idea.
If you read statements like that without context, discard them. "A little knowledge is worse than no knowledge". If it did come with context, then read and remember the context as well.

Your example is an excellent case for 'our'.

What is, IMO, bad is your use of string literals. I would write it as:

use strict; use Exporter qw(import); our @EXPORT = qw($tinytext $text $mediumtext $longtext); our $tinytext = 100; our $text = 200; our $mediumtext = 500; our $longtext = 2000;
Then, if you mistype 'tinytext' in your main code, you get a compile time error, instead of a run time uninitialized error. Using string literals as hash keys in the way you're doing is like coding without lexical variables, and warnings turned off.

Replies are listed 'Best First'.
Re^2: How not to use "our"?
by PeterPeiGuo (Hermit) on Nov 29, 2010 at 14:58 UTC

    A quick comment/addition to the first two paragraphs: in cases where the common values are constant (or near-constant), one alternative is to wrap those values in a class and provide accessors. This provides commonly available values without global.

    Peter (Guo) Pei

      You're just replacing global scalars with global subs.

      Except for slowing down your code and making it longer, that isn't much of an improvement.

Re^2: How not to use "our"?
by Anonymous Monk on Nov 30, 2010 at 10:06 UTC

    Maybe it's just me. I prefer to put them in a hash (or hash reference) - it's a bit like organising things into a cabinet.

    my $chapters = { one => 'Chapter 1: AAA', two => 'Chapter 2: BBB', three => 'Chapter 3: CCC', };

    The above is more organised than having 3 separate variables. Any thoughts from the monks?

      If you think about it, a package symbol table (stash) *is* a hash, so the individual package variables within a package who's only purpose is to hold constants or configuration parameters is already organised as you would like it.

      If you then avoid exporting the individual variables and use them as $config::one, $config::two etc. then you've got the best of both worlds.

      The variables are nicely organised, and you also get typo checking at compile time:

      >perl -c -wE"package x;our $fred=50;package main; print $x::fred,$x::d +erf" Name "x::derf" used only once: possible typo at -e line 1. -e syntax OK

      Examine what is said, not who speaks -- Silence betokens consent -- Love the truth but pardon error.
      "Science is about questioning the status quo. Questioning authority".
      In the absence of evidence, opinion is indistinguishable from prejudice.

        Need a little clarification. So it's better to export a collective hash (reference) or individual variables (as suggested by JavaFan)?

      It's your code, so you can do whatever you want to do. But how is putting 3 things in a hash (so you have four things) more organized than 3 things in a stash (which is also a hash)? And if you want to actually export your hash, you need to stuff the hash inside your stash (ending with with five things). It's like the difference of three drawers in a cupboard vs three drawers in a cabinet in a cupboard.

      But the main problem I have is the same problem I have with neither using strict, nor warnings.

      use strict; use warnings; my $chapters = { one => 'Chapter 1: AAA', two => 'Chapter 2: BBB', three => 'Chapter 3: CCC', }; say "We start with $chapters->{noe}"; # Compiler neither gives an er +ror, nor a warning.
      vs
      package chapters; our $one = 'Chapter 1: AAA'; our $two = 'Chapter 2: BBB'; our $three = 'Chapter 3: CCC'; package main; use strict; use warnings; say "We start with $chapters::noe"; # Compile time error.
      You're free to not use strict or warnings, but I think they are sane things to use. And it doesn't make sense to put a "use strict;" in your code, and then use code that won't be checked by strict.

        I see your point.

        If I've several groups of variables (other than chapters), I would have to have a module for each group e.g. Chapters.pm, Authors.pm, References.pm.

        To avoid that, I have a module that stores all the different groups of variables. To help me organise the code, I use a hash reference for each group e.g. $chapters, $authors, etc (so $chapters stores all the chapter information, $authors stores all the author information, etc)

        Hm...don't know. Does that sound strange or silly?