Beefy Boxes and Bandwidth Generously Provided by pair Networks
There's more than one way to do things
 
PerlMonks  

comment on

( [id://3333]=superdoc: print w/replies, xml ) Need Help??

One initial note: "10234" would be a better starting point than "12345".

For the problem sub check_duplicates(), if you're going to write it that way you need to allow for the fact that you'll get 5 mandatory matches, when you compare digit-1 to digit-1 etc: you can allow for that by subtracting 5 from $flag.

Another approach is to use indices to iterate over the arrays so that you can avoid comparing a digit against itself:

for my $i (0 .. $#digits) { for my $j (0 .. $#digits) { next if $i == $j; ++$flag if $digit[$i] == $digit[$j]; } }

Another way to avoid it, since an equality check is symmetrical, is to iterate the inner loop only over the digits following the current outer digit:

for my $i (0 .. $#digits) { for my $j ($i + 1 .. $#digits) { ++$flag if $digits[$i] == $digits[$j]; } }

But I'd rather use a simple regexp:

sub check_duplicates { my $candidate = shift; ++$flag if $candidate =~ /(.).*\1/; }

For check_prime(), note that a character class (/[2357]/) is more efficient than an alternation (/2|3|5|7/), but for counting the number of occurrences of a class of characters tr/// is faster still:

sub check_prime { my $candidate = shift; ++$flag if 2 != $candidate =~ tr/2357//; }

As a general efficiency rule, duplicated effort is a red flag: rather than let each check subroutine split the candidate to an array, you could do it once in the main loop and pass a reference to the resulting array as a second argument to the relevant check subroutines.

Note also that you can gain time by ordering the check subroutines so that the ones most likely to fail or quickest to check appear earlier (at least if you also follow others' advice and short-circuit on the first failure) - in this respect, I'd check for duplicates first, but I'd also be inclined to avoid checking all of (for example) 44000 .. 44999 by checking for where the first duplicate occurs:

for (my $candidate = 10234; $candidate <= 98765; ++$candidate) { # we want to jump eg from 10992 to 11000 # note not 'next': we've already incremented if the s/// succeeds redo if $candidate =~ s{ ^ (.*? (.) .*? \2) (.*) }{ ($1 + 1) . ("0" x length($3)) }ex; ... }

On another topic, you've done a good job of writing self-documenting code here, but I should mention that while I agree with other respondents about removing the use of $flag, I'd otherwise suggest renaming it - since it will have a true value if the candidate is not acceptable, I'd call it something like $bad or $fail and then finish the main loop with:

print "$candidate\n" unless $bad;

Hugo

In reply to Re: Simple Math Puzzle... by hv
in thread Simple Math Puzzle... by Daruma

Title:
Use:  <p> text here (a paragraph) </p>
and:  <code> code here </code>
to format your post; it's "PerlMonks-approved HTML":



  • Are you posting in the right place? Check out Where do I post X? to know for sure.
  • Posts may use any of the Perl Monks Approved HTML tags. Currently these include the following:
    <code> <a> <b> <big> <blockquote> <br /> <dd> <dl> <dt> <em> <font> <h1> <h2> <h3> <h4> <h5> <h6> <hr /> <i> <li> <nbsp> <ol> <p> <small> <strike> <strong> <sub> <sup> <table> <td> <th> <tr> <tt> <u> <ul>
  • Snippets of code should be wrapped in <code> tags not <pre> tags. In fact, <pre> tags should generally be avoided. If they must be used, extreme care should be taken to ensure that their contents do not have long lines (<70 chars), in order to prevent horizontal scrolling (and possible janitor intervention).
  • Want more info? How to link or How to display code and escape characters are good places to start.
Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Chatterbox?
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others scrutinizing the Monastery: (None)
    As of 2024-04-25 01:51 GMT
    Sections?
    Information?
    Find Nodes?
    Leftovers?
      Voting Booth?

      No recent polls found