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

Guys,
I want to use bitwise XOR operator which is known to be fast for bitwise testing. What I intend to do below is to find number of matching positions (except N matching is not counted).
my $s1 = "STCATTNNNSATCGCT"; my $s2 = "ATCGTCGSNNNNATCG"; ## # 0 # # There are 4 matching positions - marked with (#) - # and notice that matching N is not counted (0)
My best attempt with it is this, which leads me nowhere.
my $match = $s1 ^ $s2; my $match_count = $match =~ tr/\00//; print "$match_count\n"; # This gives 5, because N is counted. # How can I make it to return 4 instead?
Because the code I have below - using subscripted for loop - already does its job, but it is horribly slow:
get_match_count($s1,$s2); sub get_match_count { my ( $k, $l ) = @_; return 0 if $k eq $l; my $len = length($k); my $num_match = 0; for ( my $i = 0; $i < $len; $i++ ) { next if ( substr( $k, $i, 1 ) eq 'N' and substr( $l, $i, 1 ) eq 'N' ); ++$num_match if substr( $k, $i, 1 ) eq substr( $l, $i, 1 ); } print "$num_match\n"; return $num_match; }

Regards,
Edward

Replies are listed 'Best First'.
Re: Conditional Bitwise XOR(^) Operator in Matching Chars Count of Two Strings
by GrandFather (Saint) on Nov 09, 2005 at 02:04 UTC

    Mutate the Ns first:

    use strict; use warnings; use Data::Dumper; my $s1 = "STCATTNNNSATCGCT"; my $s2 = "ATCGTCGSNNNNATCG"; $s1 =~ tr/N/n/; my $merge = $s1 ^ $s2; my $count = $merge =~ tr/\0//; print $count;

    Prints:

    4

    Perl is Huffman encoded by design.
      Changing the transliteration line to tr/SACTG/_____/c; allows you to specify the characters that you want to keep. This maybe easier to work with in a biomed application.