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

I'm trying to write an anagram finder that searches through /usr/dict/words. I know there were some other posts on this, but I tried to write my own. Basically, I wanted it to do this:
% anagram_finder.pl elloh hello %
I have some code that does it using a for loop, but I wanted to get it to work using "grep". I thought it would be cleaner and nicer. This doesn't work, though I have been trying very hard to find my mistake but I have been unlucky so far:
open DICT, "</usr/dict/words" or die "no more words: $!"; $a = join "", sort split "", lc shift; print join "\n", grep {$a eq join "", sort split "", lc} <DICT>;
Any help would be greatly appreciated.

Paul Chou

Replies are listed 'Best First'.
Re: Anagram finder
by jeroenes (Priest) on Apr 24, 2001 at 09:43 UTC
    You're bitten by newlines.

    print join "\n", grep {chomp; $a eq join "", sort split "", lc} <DICT> +;

    Jeroen
    "We are not alone"(FZ)
    And yes, I tested it. Is not bothered by the sub-grief, apparently

      Thank you all very much. I'm still pretty new to perl, and I guess I got confused with "chop" and "chomp" which giving me problems (and why I didn't include it).

      Paul

Re (tilly) 1: Anagram finder
by tilly (Archbishop) on Apr 24, 2001 at 09:40 UTC
    The automagic "is or isn't there a sub there?" is giving you grief.

    It is trying to treat split as the sort sub, and not as part of how you get a list into the sort.

    UPDATE
    jeroenes is correct. I should have tested before tossing that out. I guess it is better about finding keywords. But try putting a subroutine that you have created there and it will be cheerfully abused:

    sub my_split { split "", shift; } print join "", sort my_split("qwerty");
Re: Anagram finder
by frankus (Priest) on Apr 24, 2001 at 19:15 UTC
    You could try for more lines and less memory strain:
    open DICT, "</usr/dict/words" or die "no more words: $!"; $a = join "", sort split "", lc shift; for(<DICT>){ $b = lc($_); chomp($b); $b = join("",sort(split //,$b)); if($a eq $b){print} }
    Hint: Take a look at Mastering Perl Algorithms.

    This way, the contents of dictionary aren't loaded into an array, advisable if you're playing on anything smaller than an Enterprise Server.
    I like the concise style of code though ;0).

    --
    
    Brother Frankus.