Beefy Boxes and Bandwidth Generously Provided by pair Networks
more useful options
 
PerlMonks  

Re: Recognizing pattern in 2D grid

by Athanasius (Archbishop)
on Jan 16, 2018 at 03:49 UTC ( [id://1207333]=note: print w/replies, xml ) Need Help??


in reply to Recognizing pattern in 2D grid

Hello pwagyi,

I think an array of arrays (AoA) is a better data structure for this task than a hash of hashes (HoH). And if each datum is only a single character, as in the example given, you can use regular expressions to do the searching. The following script lacks proper error checking, etc., but should give you an idea of how to proceed:

use strict; use warnings; my @grid = ( [ qw( a a b a c ) ], [ qw( a a a c f ) ], [ qw( a f c 1 b ) ], [ qw( a w x c z ) ], [ qw( a q q q c ) ], ); recognize( pattern => 'horizontal', min => 3 ); recognize( pattern => 'vertical', min => 5 ); recognize( pattern => 'diagonal', min => 2 ); sub recognize { my %config = @_; my $pattern = $config{pattern} // 'horizontal'; my $min = $config{min} // 3; my $reps = $min - 1; if ($pattern eq 'horizontal') { for my $row (0 .. $#grid) { my $string; $string .= $_ for $grid[$row]->@*; print "Found $pattern pattern '$&' in row $row\n" while $string =~ /(.)\1{$reps,}/g; } } elsif ($pattern eq 'vertical') { for my $col (0 .. $#{ $grid[0] }) { my $string; $string .= $_->[$col] for @grid; print "Found $pattern pattern '$&' in column $col\n" while $string =~ /(.)\1{$reps,}/g; } } elsif ($pattern eq 'diagonal') { my $string; $string .= $grid[$_][$_] for 0 .. $#grid; print "Found $pattern pattern '$&' in left-right diagonal\n" while $string =~ /(.)\1{$reps,}/g; my $col = $#grid; $string = ''; for my $row (0 .. $#grid) { $string .= $grid[$row][$col--]; } print "Found $pattern pattern '$&' in right-left diagonal\n" while $string =~ /(.)\1{$reps,}/g; } else { die "Unknown pattern '$pattern', stopped"; } }

Output:

13:48 >perl 1862_SoPW.pl Found horizontal pattern 'aaa' in row 1 Found horizontal pattern 'qqq' in row 4 Found vertical pattern 'aaaaa' in column 0 Found diagonal pattern 'aa' in left-right diagonal Found diagonal pattern 'ccc' in left-right diagonal Found diagonal pattern 'ccc' in right-left diagonal 13:57 >

Update: It occurs to me, belatedly, that a “diagonal” pattern might mean a sequence on any diagonal, and not just one of the two major diagonals, as I naïvely assumed. Extending the code to allow for matches on any diagonal is hereby left as the proverbial exercise for the reader. :-)

Hope that helps,

Athanasius <°(((><contra mundum Iustus alius egestas vitae, eros Piratica,

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: note [id://1207333]
help
Chatterbox?
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others avoiding work at the Monastery: (6)
As of 2024-04-19 11:46 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found