http://qs321.pair.com?node_id=413508

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

Hi all,

I have a string defined as follows:
my $str = 'params.$idx.arg';
$idx will be assigned with integer values in a loop as follows:
for my $idx (0..10) { &do_something($str); }
The thing is that I want $str in the loop to be interpulated with the value of $idx in each loop iteration (the above code will not take there of course), meaning do_something() will get a different parameter each loop iteration ('params.0.arg', 'params.1.arg', etc.).
How can I achive that?

Thanks

Retitled by davido: Corrected spelling of 'interpolation' to improve searchability.

Replies are listed 'Best First'.
Re: String interpolation
by fglock (Vicar) on Dec 09, 2004 at 13:03 UTC
    use strict; my $str = sub { "params.$_[0].arg" }; sub do_something { print +shift, "\n" } for my $idx (0..10) { do_something( $str->($idx) ); }

    output:

    params.0.arg params.1.arg params.2.arg params.3.arg params.4.arg params.5.arg params.6.arg params.7.arg params.8.arg params.9.arg params.10.arg
Re: String interpolation
by gellyfish (Monsignor) on Dec 09, 2004 at 13:19 UTC

    An alternative to the other suggestions is to use (s)printf:

    my $str = 'params.%d.arg'; + for my $idx (0 .. 9 ) { printf $str, $idx; }
    You will need to be careful in sanitizing the contents of $str if all or part of it is being taken from user (or otherwise untrusted) input .

    /J\

Re: String interpolation
by reneeb (Chaplain) on Dec 09, 2004 at 12:56 UTC
    use " instead of ':
    my $str = "params.$idx.arg";

    That means for your code:
    for(0..10){ my $str = "params.$idx.arg"; do_something($str); }
    A reply falls below the community's threshold of quality. You may see it by logging in.
Re: String interpolation
by edan (Curate) on Dec 09, 2004 at 13:09 UTC

    I think the easiest solution is using the dreaded string eval:

    for my $idx (0..10) { my $interp_str; eval "\$interp_str = qq($str)"; do_something($interp_str); }

    All the usual caveats about untainting user inputs apply, of course.

    --
    edan

Re: String interpolation
by kelan (Deacon) on Dec 09, 2004 at 13:24 UTC

    Do your own interpolation:

    for my $idx ( 0 .. 10 ) { my $newstr = $str; $newstr =~ s/\$idx/$idx/; do_something( $newstr ); }

Re: String interpolation
by kappa (Chaplain) on Dec 09, 2004 at 15:19 UTC
    That's eval thing.
    #! /usr/bin/perl -w use strict; my $str = '"number $idx\n"'; foreach my $idx (1 .. 10) { print eval($str); }
    --kap
Re: String interpolation
by hotshot (Prior) on Dec 09, 2004 at 15:02 UTC
    Thanks guys, but fglock's solution is the best for me, I wanted to avoid using additional temporary parameters (I already knew these options), but thanks anyway.