use warnings; use strict; use Data::Dump qw/dd pp/; my @array1 = ('ux_prim_clk', 'ux_side_clk', 'ux_xtal_frm_refclk'); my @array2 = ('ccu_ux_xtal_frm_refclk_ack', 'ibbs_ux_prim_clkack', 'sbr_ux_side_clkack'); my @aoa1 = map { [ split /_/, $_ ] } @array1; my @output; # Using @array2 for the basis of ordering, so loop over that first for my $a2 ( map { [ split /_/, $_ ] } @array2 ) { #print "##### "; dd $a2; # debug # Now look through @array1 for the best match my ($highest_match, $highest_match_at_a1idx) = (-1); for my $i ( 0 .. $#aoa1 ) { # in this loop, keep track of index my $a1 = $aoa1[$i]; # The following code relies on @$a1 >= @$a2, so check that if ( @$a2 < @$a1 ) { warn "Skipping ".pp($a2, $a1); next } # Try matching $a1 against $a2 at different offsets for my $offset ( 0 .. @$a2 - @$a1 ) { my $match = 0; # Count the number of matching elements at each offset for my $j ( 0 .. $#$a1 ) { if ( $a2->[$offset+$j] eq $a1->[$j] ) { $match++ } else { last } # failed to match, stop looking } # If this index and offset matches better, record that if ( $match && $match > $highest_match ) { #dd $a2, $offset, $a1, $match; # debug $highest_match = $match; $highest_match_at_a1idx = $i; } } } if ( defined $highest_match_at_a1idx ) { push @output, $array1[$highest_match_at_a1idx] } else { warn "Failed to find match for ".pp($a2) } } dd @array1; dd @array2; dd @output; __END__ ("ux_prim_clk", "ux_side_clk", "ux_xtal_frm_refclk") ( "ccu_ux_xtal_frm_refclk_ack", "ibbs_ux_prim_clkack", "sbr_ux_side_clkack", ) ("ux_xtal_frm_refclk", "ux_prim_clk", "ux_side_clk")