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

default values for lists

by pike (Monk)
on Sep 17, 2002 at 15:00 UTC ( #198502=perlquestion: print w/ replies, xml ) Need Help??
pike has asked for the wisdom of the Perl Monks concerning the following question:

I often use default values for scalar variables, e. g.

$val = $x || $default

Now I tried this for lists, but it doesn't work - or, to be precise, it works only if the first list is empty, because otherwise the first list is interpreted in scalar context:

@a = (); @b = qw (one two three); @c = qw (four five); @d = @a || @c; #gives ('four', 'five') - OK @d = @b || @c; #gives ('3') - yikes!

Can I inhibit the interpretation of the first list as scalar? Or is the only way to get the desired behaviour:

@list = @a; @list = @default unless @list;

Thanks for your suggestions,

pike

Comment on default values for lists
Select or Download Code
Re: default values for lists
by fglock (Vicar) on Sep 17, 2002 at 15:03 UTC
    try this:  @d = @a ? @a : @c;
      OK, maybe I should have given more context: I was trying to strip of the ending of words, do something with the words and put the ending back on, like this:

      my ($end) = $word =~ /(e?s)$/ || (''); ... #do something with $word $word = "$word$end";

      If the word does not end in s/es, I get a warning about uninitialized variables where I append $end - which I wanted to avoid.

      I thought about the ternary, but I don't want to evaluate the regex twice.

      I simplified the problem because IMO it boils down to the question if I can enforce list context on the part before the ||. But maybe I oversimplified it.

      Thanks anyway for the suggestion.

      pike

        Ah, ok. Try this:

        ($begin, $end) = $word =~ /(.*?)(es|s|)$/;
        Then I'd say my $end = $word =~ /(e?s)$/ ? $1 : '';

        Makeshifts last the longest.

Re: default values for lists
by Elgon (Curate) on Sep 17, 2002 at 15:09 UTC

    Hi pike,

    You could try using the trinary operator...

    @d = @a ? @a : @c;

    In the example given, if @a returns true (in scalar context ie. has a nonzero length) then it is copied into @d, otherwise the contents of @c are copied into @d.

    Update: Arrgh, fglock beat me to it!

    "Rule #17 of Travel: Never try and score dope off Hassidic Jews while under the impression that they are Rastafarians."
           - Pete McCarthy, McCarthy's Bar

Re: default values for lists
by RMGir (Prior) on Sep 17, 2002 at 15:12 UTC
    There are a few options I can see. If it's completely "either @a or @default", or if you want all of @a, and fill in with the first few from @default if @a is short, then you could do this:
    @list=(@a,@default)[0..$#default];
    As an alternative, you could do:
    @list=map {$_>$#a ? $default[$_] : $a[$_] } 0..$#default;
    It's a lot easier to do default values if you use hashes, though.
    --
    Mike
Re: default values for lists
by blokhead (Monsignor) on Sep 17, 2002 at 17:42 UTC
    Assuming I've not misintepreted your question, I'd lean towards a solution something like this:
    my @defaults = qw/one two three four five/; my @a = qw/un deux trois/; $a[$_] ||= $defaults[$_] for (0 .. $#defaults); print "@a\n"; # prints "un deux trois four five"
    Again, if you're looking for a completely either-or approach to the two lists, then the aforementioned trinary operator is probably the best choice. If you want to take from @a or @defaults on a per-element basis, then the trinary operator won't give you the desired results -- you'll need to use an approach like mine or RMGir's above.

    blokhead

Log In?
Username:
Password:

What's my password?
Create A New User
Node Status?
node history
Node Type: perlquestion [id://198502]
Approved by Elgon
help
Chatterbox?
and the web crawler heard nothing...

How do I use this? | Other CB clients
Other Users?
Others making s'mores by the fire in the courtyard of the Monastery: (13)
As of 2014-09-23 05:01 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    How do you remember the number of days in each month?











    Results (210 votes), past polls