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

Dear Monks

Is there a better way to do the following:
$string = "bcde" ; $string = "a".$string ;
I can imagine there is a better way to do this if you consider adding text at the end of the $string
$string = "abcd" ; $string .= "e" ;
Thnx
Luca

Replies are listed 'Best First'.
Re: add text to a string
by roboticus (Chancellor) on May 30, 2006 at 11:10 UTC
    jeanluca:

    I can't think of any better way to do string concatenations than the ones you presented. But next time you ask a question like this, you might want to tell us which measure of "better" you want: Faster? Smaller? More maintainable? On many occasions, you'll find that each measure of better leads to a different answer, and you'll find people giving you answers based on which "better" the writer is assuming you mean. (I keep tending toward "faster" because of my nature, but with the sort of stuff I do, I should be leaning toward clarity and maintainability...

    That said, I think the ones you presented are probably very good in all three measures. It's certainly clear and maintainable. I don't benchmark Perl programs, but it's such a common operation that I imagine the compiler does a pretty good job on speed and size as well. (There are more variations of "better" as well, but those are the only three I ever think about....)

    --roboticus

      you're right, sorry for that. The problem was that something like this
      $self->{blablabla}->{more_bla}->{and_more}->[$_] = "a".$self->{blablab +la}->{more_bla}->{and_more}[$_];
      doesn't look verywell.
      So I think the solution with substr looks much better!!
      But still, if something like '.=' exists, one would expect something simular for adding text to the front of a string!

      Luca

        Well, in addition to all that has been said thus far, you can also do

        $_ = 'a' . $_ for $self->{blablabla}->{more_bla}->{and_more}->[$_];

        You're right. That looks horrible. Maybe you should grab your value into a sensibly named lexical first, and reassign later so the whole operation looks clearer:

        my $entity = $self->{blablabla}{more_bla}{and_more}[$_]; $entity = 'a' . $entity; $self->{blablabla}{more_bla}{and_more}[$_] = $entity;

        This is marginally less efficient, particularly if the string in question is really big. But it deobfuscates what's going on. It would be really easy to miss the concatenation if you're reading through your code. But if you unpack your value into some sensibly named lexical before performing operations on it, the resulting code will be much easier to read.


        Dave

Re: add text to a string
by Zaxo (Archbishop) on May 30, 2006 at 10:57 UTC

    substr $string, 0, 0, 'a';
    or
    substr ($string, 0, 0) = 'a';
    or even,
    my $string = 'a'; $string .= 'bcde';
    ;-)

    $string = 'a' . $string; is fine.

    After Compline,
    Zaxo

Re: add text to a string
by prasadbabu (Prior) on May 30, 2006 at 10:56 UTC

    Here is one way to do it, but not more efficient. Also you can use substr.

    $string = "bcde" ; $string = "a$string"; print $string; To add at the end, $string = "abcd" ; $string = "${string}e" ; print $string;

    update:As roboticus suggested, unless you tell whether you need effieciency interms of smaller or execution speed or more maintainable, it ll be difficult to suggest correct method. roboticus++ :)

    Prasad

Re: add text to a string
by zakame (Pilgrim) on Jun 02, 2006 at 10:28 UTC
    Would this do?
    $str = 'bcde'; $new = join "" => a => split // => $str; # $new = 'abcde';
    That's warnings-tested, strict-approved. =)
Re: add text to a string
by Anonymous Monk on May 30, 2006 at 18:33 UTC
    Another idea.
    $string = "bcde"; $string =~ s/($_)/a$1/;

      Well, that won't work, but what you're going after would:

      $string = "bcde"; $string =~ s/^(.+)$/a$1/;

      Update: AM's suggestion does work (my bad), as does mine, and so would betterworld's below. However it just seems a silly way to go about it, with either $string = "a$string"; or $string = 'a' . $string; being the more traditional ways of doing it.



      --chargrill
      $,=42;for(34,0,-3,9,-11,11,-17,7,-5){$*.=pack'c'=>$,+=$_}for(reverse s +plit//=>$* ){$%++?$ %%2?push@C,$_,$":push@c,$_,$":(push@C,$_,$")&&push@c,$"}$C[$# +C]=$/;($#C >$#c)?($ c=\@C)&&($ C=\@c):($ c=\@c)&&($C=\@C);$%=$|;for(@$c){print$_^ +$$C[$%++]}
        Wouldn't it be more straightforward to do it like this:
        $string =~ s/^/a/;
      I think I red somewhere that using the variables like $1 which you get from that regular exopression makes you program slower!

      Luca