Beefy Boxes and Bandwidth Generously Provided by pair Networks
Don't ask to ask, just ask
 
PerlMonks  

Re: Trying to understand subtleties of Getopt::Long, please help

by Rudif (Hermit)
on Sep 24, 2007 at 20:44 UTC ( #640817=note: print w/replies, xml ) Need Help??


in reply to Trying to understand subtleties of Getopt::Long, please help

Thank you ikegami, Joost and Sidhekin

The *option's argument* is required, not the option itself.

What is "mandatory" and "optional" is not the option itself (options are by their nature always optional) but rather the associated argument.

In other words, the additional processing is only invoked if the arguments are specified.

Right, you clarified what was confusing me.

I would prefer the is_deeply method of comparing complex structure.

I agree, now that you mentioned it: easier to read, easier to update when developing the script.

I also found an interesting discussion of its limitations and alternatives in Does Data::Dumper give you eye strain? Use Test::More::is_deeply() for debugging!

The revised script below reflects the insights.

Rudif

#!perl -w use strict; my $version = 0.02; use Getopt::Long; $|++; use Test::More tests => 32; ## The option name as specified to the GetOptions() function is called + the option specification. ## Later we'll see that this specification can contain more than just +the option name. ## The reference to the variable is called the option destination. { my $case = "Case 1 - from module synopsis"; local @ARGV = (); my $data = "file.dat"; my $length = 24; my $verbose; my $result = GetOptions( "length=i" => \$length, # numeric "file=s" => \$data, # string "verbose" => \$verbose # flag ); ok( $result, 'Case 1 from module synopsis' ); is_deeply( [ $data, $length, $verbose ], [ 'file.dat', 24, undef ] +, 'Case 1 from module synopsis' ); } ## For options that take values it must be specified whether the optio +n value is required or not, and what kind of value the option expects +. ## Three kinds of values are supported: integer numbers, floating poin +t numbers, and strings. ## If the option value is required, Getopt::Long will take the command + line argument that follows the option and assign this to the option +variable. ## If, however, the option value is specified as optional, this will o +nly be done if that value does not look like a valid command line opt +ion itself. { my $case = "Case 2 - option has default value, none given"; local @ARGV = (); my $tag = 'deftag'; my $result = GetOptions( 'tag=s' => \$tag ); ok( $result, $case ); is_deeply( [$tag], ['deftag'], $case ); } { my $case = "Case 3 - option has default value, option with value g +iven"; local @ARGV = ('--tag=MYTAG'); my $tag = 'deftag'; my $result = GetOptions( 'tag=s' => \$tag ); ok( $result, $case ); is_deeply( [$tag], ['MYTAG'], $case ); } { my $case = "Case 4 - option has default value, option with value a +nd unknown option given"; local @ARGV = ('--bingo --tag=OTHERTAG'); my $tag = 'deftag'; my $result = GetOptions( 'tag=s' => \$tag ); ok( !$result, $case ); is_deeply( [$tag], ['deftag'], $case ); } ## In the option specification, the option name is followed by an equa +ls sign = and the letter s. ## The equals sign indicates that this option requires a value. ## The letter s indicates that this value is an arbitrary string. ## Other possible value types are i for integer values, and f for floa +ting point values. { my $case = "Case 5a - options have no default values, option value +s required if option given, no options given"; local @ARGV = (); my $tag; my $ival; my $result = GetOptions( 'tag=s' => \$tag, 'ival=i' => \$ival ); ok( $result, $case ); is_deeply( [ $tag, $ival ], [ undef, undef ], $case ); } { my $case = "Case 5b - options have no default values, option value +s required if option given, options with values given"; local @ARGV = ( '--tag=thisyear', '--ival=2007' ); my $tag; my $ival; my $result = GetOptions( 'tag=s' => \$tag, 'ival=i' => \$ival ); ok( $result, $case ); is_deeply( [ $tag, $ival ], [ 'thisyear', 2007 ], $case ); } { my $case = "Case 5c - options have no default values, option value +s required if option given, options without values given"; local @ARGV = ( '--tag', '--ival' ); my $tag; my $ival; my $result = GetOptions( 'tag=s' => \$tag, 'ival=i' => \$ival ); ok( $result, $case ); is_deeply( [ $tag, $ival ], [ '--ival', undef ], $case ); } { my $case = "Case 5x - options have default values, option values r +equired if option given, no options given"; local @ARGV = (); my $tag = 'deftag'; my $ival = -1; my $result = GetOptions( 'tag=s' => \$tag, 'ival=i' => \$ival ); ok( $result, $case ); is_deeply( [ $tag, $ival ], [ 'deftag', -1 ], $case ); } { my $case = "Case 5y - options have default values, option values r +equired if option given, options with values given"; local @ARGV = ( '--tag=thisyear', '--ival=2007' ); my $tag = 'deftag'; my $ival = -1; my $result = GetOptions( 'tag=s' => \$tag, 'ival=i' => \$ival ); ok( $result, $case ); is_deeply( [ $tag, $ival ], [ 'thisyear', 2007 ], $case ); } { my $case = "Case 5z - options have default values, option values r +equired if option given, options without values given"; local @ARGV = ( '--tag', '--ival' ); my $tag = 'deftag'; my $ival = -1; my $result = GetOptions( 'tag=s' => \$tag, 'ival=i' => \$ival ); ok( $result, $case ); is_deeply( [ $tag, $ival ], [ '--ival', -1 ], $case ); } ## Using a colon : instead of the equals sign indicates that the optio +n value is optional. ## In this case, if no suitable value is supplied, string valued optio +ns get an empty string '' assigned, while numeric options are set to +0. { my $case = "Case 6a - options have no default values, option value +s not required if options given, no options given"; local @ARGV = (); my $tag; my $ival; my $result = GetOptions( 'tag:s' => \$tag, 'ival:i' => \$ival ); ok( $result, $case ); is_deeply( [ $tag, $ival ], [ undef, undef ], $case ); } { my $case = "Case 6b - options have no default values, option value + not required if option given, options with values given"; local @ARGV = ( '--tag=thisyear', '--ival=2007' ); my $tag; my $ival; my $result = GetOptions( 'tag:s' => \$tag, 'ival:i' => \$ival ); ok( $result, $case ); is_deeply( [ $tag, $ival ], [ 'thisyear', 2007 ], $case ); } { my $case = "Case 6c - options have no default values, option value + not required if option given, options without values given"; local @ARGV = ( '--tag', '--ival' ); my $tag; my $ival; my $result = GetOptions( 'tag:s' => \$tag, 'ival:i' => \$ival ); ok( $result, $case ); is_deeply( [ $tag, $ival ], [ '', 0 ], $case ); } { my $case = "Case 6x - options have default values, option values n +ot required if options given, no options given"; local @ARGV = (); my $tag = 'deftag'; my $ival = -1; my $result = GetOptions( 'tag:s' => \$tag, 'ival:i' => \$ival ); ok( $result, $case ); is_deeply( [ $tag, $ival ], [ 'deftag', -1 ], $case ); } { my $case = "Case 6y - options have default values, option value no +t required if option given, options with values given"; local @ARGV = ( '--tag=thisyear', '--ival=2007' ); my $tag = 'deftag'; my $ival = -1; my $result = GetOptions( 'tag:s' => \$tag, 'ival:i' => \$ival ); ok( $result, $case ); is_deeply( [ $tag, $ival ], [ 'thisyear', 2007 ], $case ); } { my $case = "Case 6z - options have default values, option value no +t required if option given, options without values given"; local @ARGV = ( '--tag', '--ival' ); my $tag = 'deftag'; my $ival = -1; my $result = GetOptions( 'tag:s' => \$tag, 'ival:i' => \$ival ); ok( $result, $case ); is_deeply( [ $tag, $ival ], [ '', 0 ], $case ); } __END__

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: note [id://640817]
help
Chatterbox?
and the web crawler heard nothing...

How do I use this? | Other CB clients
Other Users?
Others avoiding work at the Monastery: (4)
As of 2023-02-04 22:52 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?
    I prefer not to run the latest version of Perl because:







    Results (31 votes). Check out past polls.

    Notices?