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

Hi all,

I'm trying to figure out why I'm getting a "Useless use of a constant in void context" error message when running a program. I've read princepawn's Useless Use question, but I confess I'm not understanding what's being said. I'm still a fledgling, so some of the explanations are over my head. Note, however, that the program still generates my text file as I expect, so this error isn't stopping the program... I just want to understand it better. Below is my little program (which I think I stole mostly from Ovid):

#!/usr/bin/perl5 -w use strict; use File::Find; my $report = "LDT_results.txt"; open MYOUTPUT, "> $report" or die "Can't open $report: $!"; my @directories = ("/usr/local/lib"); my @foundfiles; # Collect all .pm files below each directory in @directories # and put them into @foundfiles find ( sub { push @foundfiles, $File::Find::name if /\.pm$/ }, @directories); # and output them all to the screen so I can see it's working my $pms = join("\n", @foundfiles), "\n"; print $pms; #and print them to my file "LDT_results.txt" print MYOUTPUT $pms; close MYOUTPUT;

I've tried tilly's and merlyn's suggestions about getting some diagnostics on the command line, but I don't seem to be able to get the right command going. I've tried the following:

command line>perldoc perldiag /Useless use -Mdiagnostics

and I get the following message:

syntax error in file /usr/local/bin/perldoc at line 5, next 2 tokens "use warnings"
syntax error in file /usr/local/bin/perldoc at line 17, next 2 tokens "my $bindir "
syntax error in file /usr/local/bin/perldoc at line 21, next 2 tokens "my $pod2man "
syntax error in file /usr/local/bin/perldoc at line 43, next 2 tokens "my $me "
syntax error in file /usr/local/bin/perldoc at line 55, next 2 tokens "my @global_found"
syntax error in file /usr/local/bin/perldoc at line 110, next 2 tokens "Text:"
syntax error in file /usr/local/bin/perldoc at line 111, next 2 tokens "Text:"
syntax error in file /usr/local/bin/perldoc at line 123, next 2 tokens "am_taint_checking("
syntax error in file /usr/local/bin/perldoc at line 154, next 2 tokens "}"
syntax error in file /usr/local/bin/perldoc at line 166, next 2 tokens "my $opts "
/usr/local/bin/perldoc has too many errors.

I know very little about Unix commands, but I'm starting to learn. I've also read some from the Llama book (I don't have the Camel book yet), but it's a little over my head.

If someone would be so kind as to explain why it doesn't like the way I'm using the variables, I'd appreciate it. Thanks!

Lori

Replies are listed 'Best First'.
Re: Help with error msg "Useless use..."
by dbwiz (Curate) on Sep 15, 2003 at 16:05 UTC

    Your line 17

    my $pms = join("\n", @foundfiles), "\n";
    is assigning the result of join to a variable. That's OK, but then you are also listing another scalar (,"\n") hoping it will go into $pms as well. It won't, and Perl is warning you about that.

    If your purpose is to concatenate the two elements, then you should use the "." (dot) operator instead.

    Perhaps you saw this working:

    print join("\n", @foundfiles), "\n";

    And that's fine, because print expects a list of arguments.

    As for the diagnostics business, what merlyn meant is to include the -Mdiagnostics in you command line. That is, if your script is called "lory.pl" you can run it this way:

    $ perl -Mdiagnostics lory.pl Useless use of a constant in void context at lory.pl line 17 (#1) (W void) You did something without a side effect in a context that + does nothing with the return value, such as a statement that doesn't re +turn a value from a block, or the left side of a scalar comma operator. +Very often this points not to stupidity on your part, but a failure of +Perl to parse your program the way you thought it would. For example, +you'd get this if you mixed up your C precedence with Python precedence +and said $one, $two = 1, 2; when you meant to say ($one, $two) = (1, 2); Another common error is to use ordinary parentheses to construct a + list reference when you should be using square or curly brackets, for example, if you say $array = (1,2); when you should have said $array = [1,2]; The square brackets explicitly turn a list value into a scalar val +ue, while parentheses do not. So when a parenthesized list is evaluat +ed in a scalar context, the comma is treated like C's comma operator, wh +ich throws away the left argument, which is not what you want. See perlref for more on this.

    All the lines you see are the result of diagnostic, which is explaining verbosely what you previously got in a dry warning.

    HTH

Re: Help with error msg "Useless use..."
by Paladin (Vicar) on Sep 15, 2003 at 16:00 UTC
    The full error message I get when running your code is Useless use of a constant in void context at test.pl line 17. and line 17 is
    my $pms = join("\n", @foundfiles), "\n";
    which joins together all the values in @foundfiles then throws it away, and assigns the "\n" to $pms.which parses as (my $pms = join("\n", @foundfiles)), "\n"; as pointed out by tye below. Assigning the value of join to $pms and doing nothing with the "\n", hence the error message. What you probably mean is
    my $pms = join("\n", @foundfiles) . "\n";
    (Note the period which is the string concatination operator, instead of the comma, which in scalar context evaluates its LHS, throws it away, then evaluates and returns its RHS)

    Update: Thanks tye. This will teach me to try and answer a PM post while answering support calls at work. Next time I'll ignore the calls.. must have my priorities straight.

      Good catch.

      Rather minor correction: The original gets parsed as:

      ( my $pms = join("\n", @foundfiles) ), "\n";
      not as
      my $pms = ( join("\n", @foundfiles), "\n" );
      so it is the "\n" that gets thrown away.

                      - tye
Re: Help with error msg "Useless use..."
by Lori713 (Pilgrim) on Sep 15, 2003 at 16:36 UTC
    My bad... I should have posted the entire error message. Sorry about that. Also, I appreciate everyone taking the time to explain why it wasn't working. I love this place!

    dbwiz is correct; the original program snippet I snatched from a reply Ovid made to someone only had the print command; I added the rest to get it to a file. I also got the command line to show me the diagnostics I wanted. Thanks!

    I changed my program as indicated, and it eliminates the error message, and I still get my expected output. Thanks to all of you for explaining, parsing, the Unix lesson, etc.!

Re: Help with error msg "Useless use..."
by Not_a_Number (Prior) on Sep 15, 2003 at 17:39 UTC

    A question: do you really need to join your array into a string?

    Unless you need your scalar $pms for something else later in your programme, I would suggest doing away with this line:

    my $pms = join("\n", @foundfiles) . "\n";

    and printing your array directly:

    print "$_\n" for @foundfiles; print MYOUTPUT "$_\n" for @foundfiles;

    dave

      Good question. I was thinking the join was necessary because it was joining the path info to the new line character. Of course, this just goes to show you what happens when you steal snippets, tinker with them, and just THINK you know how they work! ;-)

      I tried it your way and it works just fine! Thanks for showing me another way (which always adds more dimension to my learning and understanding Perl!).