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

Hi everyone, I am in need of assistance D: I am writing a battleship program, and I take in user coordinates with the format of a10, b1 , c5 etc. The module I have takes in the coordinates with the format of A:10, B:1, C:5 etc. I wrote some very poor code which has uninitialized errors, but it gets the job done. This is it here:
$combined = uc($topLeftCoord); @chars = (split //, $combined); print "@chars\n"; if ($chars[2] == 0){ $combined = $chars[0] . ":" . $chars[1] . $chars[2]; } else{ $combined = $chars[0] . ":" . $chars[1]; }
This is just a bit of it, but it's where the problem lies. I uppercase the letter, split on every new character, print for debugging, my board is 10x10, so the max it can be is 10, so if the 3rd element is 0, I'll concatenate it onto the string for use in my module. It's very poorly written but that's why I'm here, to make it better =P. How would I use substitution with regular expressions to do this job? Or would it be better to split and concatenate. Thanks for any help!

Replies are listed 'Best First'.
Re: How would I change a10 into A:10 in perl?
by lidden (Curate) on Dec 03, 2010 at 00:58 UTC
    It can be done in one line:

    $combined =~ s/(\w)(\d+)/uc($1) . ":$2" /e;
      Thank you very much! I just began learning regular expressions so I was avoiding it ^^;.
        It's hard to learn something by avoiding it!
      Though it's a good attempt, I'm not too impressed.
      • If the requirements change from 1 letter to more, your code won't handle it.
      • Your right hand side for the substitution is uglier than it should be.

      My proposed fix:

      $combined =~ s/([a-z]+)(\d+)/\U$1:$2/i;

            "If the requirements change from 1 letter to more, your code won't handle it. "

        If the requirements change from letters to kanji or hiragana characters, *your code* won't handle it either. And that is just as likely.

        Coding now to exceed the known requirements, in order to cater for some future, speculative change, is a waste of time and effort.

        When (if!) the requirements change, the the code can be changed to match the new requirements.

Re: How would I change a10 into A:10 in perl?
by BrowserUk (Patriarch) on Dec 03, 2010 at 01:01 UTC
    $s = 'a10';; $s =~ s[(.)(.+)][\U$1:$2];; print $s;; A:10

    Examine what is said, not who speaks -- Silence betokens consent -- Love the truth but pardon error.
    "Science is about questioning the status quo. Questioning authority".
    In the absence of evidence, opinion is indistinguishable from prejudice.
Re: How would I change a10 into A:10 in perl?
by hbm (Hermit) on Dec 03, 2010 at 01:04 UTC

    Or:

    ($combined = $topLeftCoord) =~ s/([a-z])(\d+)/\U$1:$2/;
Re: How would I change a10 into A:10 in perl?
by Tails (Novice) on Dec 03, 2010 at 01:13 UTC
    Thanks everyone for the help! You all rock! :D
Re: How would I change a10 into A:10 in perl?
by umasuresh (Hermit) on Dec 03, 2010 at 01:05 UTC
    May be something like this:
    $a = "a10, b10, C10"; $a =~ s/([a-z])([0-9]+)/\u\1\:\2/g; print "$a\n";

    UPDATE: Already shown by other monks!

      As the the warnings would have told you if you'd have tried running your code with strictures:

      \1 better written as $1 at ... \2 better written as $2 at ...
      True laziness is hard work
        \1 and \2 are not stricture errors (use strict does not generate warnings - they are fatal errors). They are warnings, and require warnings to be turned on.