[Perl] 'perl -s' with strict

Reuven M. Lerner reuven at lerner.co.il
Mon Nov 4 07:12:23 PST 2002


>>>>> "Uri" == Uri Itscowits <iuri at sela.co.il> writes:

    Uri> How do I declare (?) the relevant $opt when using 'perl -s',
    Uri> so that STRICT keeps quiet ?

I hadn't ever used the -s option, so I looked it up in "perldoc
perlrun" to see what it does.

The basic idea is that -s automatically creates variables for
command-line arguments.  For example, consider the following program,
which I based on an example in "perldoc perlrun":

    #!/usr/bin/perl -s

    if ($q)
    {
	print "q = '$q'\n";
    }

    if ($xyz) 
    {
	print "xyz = '$xyz'\n";
    }  

If you invoke this program with

    test.pl -q

then you find that the $q variable has been defined, and its value is
1.  You can get fancier

    test.pl -q=5

and then you find that $q has been set to 5.

Similarly, $xyz is set if you pass an -xyz argument.  You can even mix
and match them:

    test.pl -q=5 -xyz='cherry pie'

Uri's question, then, asks what happens if you want to "use strict" at
the top of your program.  "use strict", of course, performs some
compile-time checking on your variables (among other things), to
ensure that all of the variables you use have been defined in the
current scope.  Of course, since $q and $xyz are never defined
explicitly, you lose.

There are several possible solutions:

(1) Don't "use strict".  

    In a word: Ugh.

(2) Anywhere you want to reference $q or $xyz, surround the code with
    a "no strict" block:

	#!/usr/bin/perl -s 
	use strict;

	{
	    no strict;

	    if ($q)
	    {
		print "q = '$q'\n";
	    }

	    if ($xyz) 
	    {
		print "xyz = '$xyz'\n";
	    }  
	}

    The good news is that the rest of your program runs with strict
    checking.  The bad news is that this is still pretty ugly.

(3) Declare the variables with "use vars" or "our":

	#!/usr/bin/perl -s 

	use strict;
	use vars qw($q $xyz);

	{
	    if ($q)
	    {
		print "q = '$q'\n";
	    }

	    if ($xyz) 
	    {
		print "xyz = '$xyz'\n";
	    }  
	}

    Because this works, it means that $q and $xyz are *global*
    variables, rather than lexical variables.

    This is almost the best solution.  

(4) Use Getopt::Long, which is my vote for a winning solution.

    -s is obviously weird and somewhat broken, and I'm not sure how
    good of a method it is for receiving values.  I think that you
    would be wise to switch to Getopt::Long, a standard module that
    handles input options with a huge amount of flexibility, and
    without this sort of breakage.

Reuven




More information about the Perl mailing list