| line | stmt | bran | cond | sub | pod | time | code | 
| 1 |  |  |  |  |  |  | package Bio::ToolBox::db_helper::useq; | 
| 2 |  |  |  |  |  |  |  | 
| 3 |  |  |  |  |  |  | # modules | 
| 4 |  |  |  |  |  |  | require Exporter; | 
| 5 | 1 |  |  | 1 |  | 481 | use strict; | 
|  | 1 |  |  |  |  | 35 |  | 
|  | 1 |  |  |  |  | 28 |  | 
| 6 | 1 |  |  | 1 |  | 4 | use Carp; | 
|  | 1 |  |  |  |  | 2 |  | 
|  | 1 |  |  |  |  | 58 |  | 
| 7 | 1 |  |  | 1 |  | 6 | use List::Util qw(min max sum); | 
|  | 1 |  |  |  |  | 1 |  | 
|  | 1 |  |  |  |  | 68 |  | 
| 8 | 1 |  |  | 1 |  | 5 | use Statistics::Lite qw(median); | 
|  | 1 |  |  |  |  | 1 |  | 
|  | 1 |  |  |  |  | 33 |  | 
| 9 | 1 |  |  | 1 |  | 4 | use Bio::ToolBox::db_helper::constants; | 
|  | 1 |  |  |  |  | 2 |  | 
|  | 1 |  |  |  |  | 51 |  | 
| 10 | 1 |  |  | 1 |  | 5 | use Bio::DB::USeq; | 
|  | 1 |  |  |  |  | 2 |  | 
|  | 1 |  |  |  |  | 1143 |  | 
| 11 |  |  |  |  |  |  | our $VERSION = '1.51'; | 
| 12 |  |  |  |  |  |  |  | 
| 13 |  |  |  |  |  |  |  | 
| 14 |  |  |  |  |  |  | # Exported names | 
| 15 |  |  |  |  |  |  | our @ISA = qw(Exporter); | 
| 16 |  |  |  |  |  |  | our @EXPORT = qw( | 
| 17 |  |  |  |  |  |  | collect_useq_scores | 
| 18 |  |  |  |  |  |  | collect_useq_position_scores | 
| 19 |  |  |  |  |  |  | open_useq_db | 
| 20 |  |  |  |  |  |  | ); | 
| 21 |  |  |  |  |  |  |  | 
| 22 |  |  |  |  |  |  | # Hash of USeq chromosomes | 
| 23 |  |  |  |  |  |  | our %USEQ_CHROMOS; | 
| 24 |  |  |  |  |  |  | # sometimes user may request a chromosome that's not in the useq file | 
| 25 |  |  |  |  |  |  | # that could lead to an exception | 
| 26 |  |  |  |  |  |  | # we will record the chromosomes list in this hash | 
| 27 |  |  |  |  |  |  | # $USEQ_CHROMOS{useqfile}{chromos} | 
| 28 |  |  |  |  |  |  | # we also record the chromosome name variant with or without chr prefix | 
| 29 |  |  |  |  |  |  | # to accommodate different naming conventions | 
| 30 |  |  |  |  |  |  |  | 
| 31 |  |  |  |  |  |  | # Opened USeq db objects | 
| 32 |  |  |  |  |  |  | our %OPENED_USEQ; | 
| 33 |  |  |  |  |  |  | # a cache for opened USeq databases, primarily for collecting scores | 
| 34 |  |  |  |  |  |  | # caching here is only for local purposes of collecting scores | 
| 35 |  |  |  |  |  |  | # db_helper also provides caching of db objects but with option to force open in | 
| 36 |  |  |  |  |  |  | # the case of forking processes - we don't have that here | 
| 37 |  |  |  |  |  |  |  | 
| 38 |  |  |  |  |  |  | # The true statement | 
| 39 |  |  |  |  |  |  | 1; | 
| 40 |  |  |  |  |  |  |  | 
| 41 |  |  |  |  |  |  |  | 
| 42 |  |  |  |  |  |  |  | 
| 43 |  |  |  |  |  |  | sub collect_useq_scores { | 
| 44 |  |  |  |  |  |  |  | 
| 45 |  |  |  |  |  |  | # passed parameters as array ref | 
| 46 |  |  |  |  |  |  | # chromosome, start, stop, strand, strandedness, method, db, dataset | 
| 47 | 7 |  |  | 7 | 1 | 8 | my $param = shift; | 
| 48 |  |  |  |  |  |  |  | 
| 49 |  |  |  |  |  |  | # adjust strand method | 
| 50 | 7 |  |  |  |  | 9 | my $strand; | 
| 51 | 7 | 100 |  |  |  | 23 | if ($param->[STND] eq 'antisense') { | 
|  |  | 100 |  |  |  |  |  | 
| 52 | 1 |  |  |  |  | 3 | $strand = $param->[STR] * -1; | 
| 53 |  |  |  |  |  |  | } | 
| 54 |  |  |  |  |  |  | elsif ($param->[STND] eq 'all') { | 
| 55 |  |  |  |  |  |  | # Bio::DB::USeq will translate this properly, and collect from | 
| 56 |  |  |  |  |  |  | # both strands as necessary | 
| 57 | 5 |  |  |  |  | 7 | $strand = 0; | 
| 58 |  |  |  |  |  |  | } | 
| 59 |  |  |  |  |  |  | else { | 
| 60 |  |  |  |  |  |  | # default | 
| 61 | 1 |  |  |  |  | 1 | $strand = $param->[STR]; | 
| 62 |  |  |  |  |  |  | } | 
| 63 |  |  |  |  |  |  |  | 
| 64 |  |  |  |  |  |  | # unlikely there are more than one useq file, but just in case | 
| 65 | 7 |  |  |  |  | 8 | my @scores; | 
| 66 | 7 |  |  |  |  | 18 | for (my $d = DATA; $d < scalar @$param; $d++) { | 
| 67 |  |  |  |  |  |  |  | 
| 68 |  |  |  |  |  |  | # open a new db object | 
| 69 | 7 |  |  |  |  | 17 | my $useq = _get_useq($param->[$d]); | 
| 70 |  |  |  |  |  |  |  | 
| 71 |  |  |  |  |  |  | # check chromosome first | 
| 72 | 7 | 50 |  |  |  | 19 | my $chromo = $USEQ_CHROMOS{$param->[$d]}{$param->[CHR]} or next; | 
| 73 |  |  |  |  |  |  |  | 
| 74 |  |  |  |  |  |  | # need to collect the scores based on the type of score requested | 
| 75 | 7 | 100 |  |  |  | 21 | if ($param->[METH] eq 'count') { | 
|  |  | 100 |  |  |  |  |  | 
|  |  | 100 |  |  |  |  |  | 
| 76 |  |  |  |  |  |  | # need to collect features across the region | 
| 77 | 1 |  |  |  |  | 4 | my $iterator = $useq->get_seq_stream( | 
| 78 |  |  |  |  |  |  | -seq_id     => $chromo, | 
| 79 |  |  |  |  |  |  | -start      => $param->[STRT], | 
| 80 |  |  |  |  |  |  | -end        => $param->[STOP], | 
| 81 |  |  |  |  |  |  | -strand     => $strand, | 
| 82 |  |  |  |  |  |  | ); | 
| 83 | 1 | 50 |  |  |  | 231 | return unless $iterator; | 
| 84 |  |  |  |  |  |  |  | 
| 85 |  |  |  |  |  |  | # count each feature | 
| 86 | 1 |  |  |  |  | 4 | while (my $f = $iterator->next_seq) { | 
| 87 | 437 |  |  |  |  | 35929 | push @scores, 1; | 
| 88 |  |  |  |  |  |  | } | 
| 89 |  |  |  |  |  |  | } | 
| 90 |  |  |  |  |  |  | elsif ($param->[METH] eq 'ncount') { | 
| 91 |  |  |  |  |  |  | # need to collect features across the region | 
| 92 | 1 |  |  |  |  | 5 | my $iterator = $useq->get_seq_stream( | 
| 93 |  |  |  |  |  |  | -seq_id     => $chromo, | 
| 94 |  |  |  |  |  |  | -start      => $param->[STRT], | 
| 95 |  |  |  |  |  |  | -end        => $param->[STOP], | 
| 96 |  |  |  |  |  |  | -strand     => $strand, | 
| 97 |  |  |  |  |  |  | ); | 
| 98 | 1 | 50 |  |  |  | 194 | return unless $iterator; | 
| 99 |  |  |  |  |  |  |  | 
| 100 |  |  |  |  |  |  | # store the names | 
| 101 | 1 |  |  |  |  | 4 | while (my $f = $iterator->next_seq) { | 
| 102 | 437 |  | 33 |  |  | 30240 | push @scores, $f->display_name || $f->primary_id; | 
| 103 |  |  |  |  |  |  | # if no display name, a primary_id should automatically be generated | 
| 104 |  |  |  |  |  |  | } | 
| 105 |  |  |  |  |  |  | } | 
| 106 |  |  |  |  |  |  | elsif ($param->[METH] eq 'pcount') { | 
| 107 |  |  |  |  |  |  | # need to collect features across the region | 
| 108 | 1 |  |  |  |  | 6 | my $iterator = $useq->get_seq_stream( | 
| 109 |  |  |  |  |  |  | -seq_id     => $chromo, | 
| 110 |  |  |  |  |  |  | -start      => $param->[STRT], | 
| 111 |  |  |  |  |  |  | -end        => $param->[STOP], | 
| 112 |  |  |  |  |  |  | -strand     => $strand, | 
| 113 |  |  |  |  |  |  | ); | 
| 114 | 1 | 50 |  |  |  | 190 | return unless $iterator; | 
| 115 |  |  |  |  |  |  |  | 
| 116 |  |  |  |  |  |  | # precisely count each feature | 
| 117 | 1 |  |  |  |  | 3 | while (my $f = $iterator->next_seq) { | 
| 118 | 437 | 100 | 66 |  |  | 32996 | push @scores, 1 if | 
| 119 |  |  |  |  |  |  | ($f->start >= $param->[STRT] and $f->end <= $param->[STOP]); | 
| 120 |  |  |  |  |  |  | } | 
| 121 |  |  |  |  |  |  | } | 
| 122 |  |  |  |  |  |  | else { | 
| 123 |  |  |  |  |  |  | # everything else is just scores | 
| 124 | 4 |  |  |  |  | 17 | push @scores, $useq->scores( | 
| 125 |  |  |  |  |  |  | -seq_id     => $chromo, | 
| 126 |  |  |  |  |  |  | -start      => $param->[STRT], | 
| 127 |  |  |  |  |  |  | -end        => $param->[STOP], | 
| 128 |  |  |  |  |  |  | -strand     => $strand, | 
| 129 |  |  |  |  |  |  | ); | 
| 130 |  |  |  |  |  |  | } | 
| 131 |  |  |  |  |  |  | } | 
| 132 |  |  |  |  |  |  |  | 
| 133 | 7 | 50 |  |  |  | 5354 | return wantarray ? @scores : \@scores; | 
| 134 |  |  |  |  |  |  | } | 
| 135 |  |  |  |  |  |  |  | 
| 136 |  |  |  |  |  |  |  | 
| 137 |  |  |  |  |  |  |  | 
| 138 |  |  |  |  |  |  | sub collect_useq_position_scores { | 
| 139 |  |  |  |  |  |  |  | 
| 140 |  |  |  |  |  |  | # passed parameters as array ref | 
| 141 |  |  |  |  |  |  | # chromosome, start, stop, strand, strandedness, method, db, dataset | 
| 142 | 5 |  |  | 5 | 1 | 6 | my $param = shift; | 
| 143 |  |  |  |  |  |  |  | 
| 144 |  |  |  |  |  |  | # adjust strand method | 
| 145 | 5 |  |  |  |  | 6 | my $strand; | 
| 146 | 5 | 50 |  |  |  | 12 | if ($param->[STND] eq 'antisense') { | 
|  |  | 50 |  |  |  |  |  | 
| 147 | 0 |  |  |  |  | 0 | $strand = $param->[STR] * -1; | 
| 148 |  |  |  |  |  |  | } | 
| 149 |  |  |  |  |  |  | elsif ($param->[STND] eq 'all') { | 
| 150 |  |  |  |  |  |  | # Bio::DB::USeq will translate this properly, and collect from | 
| 151 |  |  |  |  |  |  | # both strands as necessary | 
| 152 | 0 |  |  |  |  | 0 | $strand = 0; | 
| 153 |  |  |  |  |  |  | } | 
| 154 |  |  |  |  |  |  | else { | 
| 155 |  |  |  |  |  |  | # default | 
| 156 | 5 |  |  |  |  | 7 | $strand = $param->[STR]; | 
| 157 |  |  |  |  |  |  | } | 
| 158 |  |  |  |  |  |  |  | 
| 159 |  |  |  |  |  |  | # unlikely there are more than one useq file, but just in case | 
| 160 | 5 |  |  |  |  | 8 | my %pos2score; | 
| 161 | 5 |  |  |  |  | 10 | for (my $d = DATA; $d < scalar @$param; $d++) { | 
| 162 |  |  |  |  |  |  |  | 
| 163 |  |  |  |  |  |  | # open a new db object | 
| 164 | 5 |  |  |  |  | 9 | my $useq = _get_useq($param->[$d]); | 
| 165 |  |  |  |  |  |  |  | 
| 166 |  |  |  |  |  |  | # check chromosome first | 
| 167 | 5 | 50 |  |  |  | 13 | my $chromo = $USEQ_CHROMOS{$param->[$d]}{$param->[CHR]} or next; | 
| 168 |  |  |  |  |  |  |  | 
| 169 |  |  |  |  |  |  | # collect the features overlapping the region | 
| 170 | 5 |  |  |  |  | 19 | my $iterator = $useq->get_seq_stream( | 
| 171 |  |  |  |  |  |  | -seq_id     => $chromo, | 
| 172 |  |  |  |  |  |  | -start      => $param->[STRT], | 
| 173 |  |  |  |  |  |  | -end        => $param->[STOP], | 
| 174 |  |  |  |  |  |  | -strand     => $strand, | 
| 175 |  |  |  |  |  |  | ); | 
| 176 | 5 | 50 |  |  |  | 722 | return unless $iterator; | 
| 177 |  |  |  |  |  |  |  | 
| 178 |  |  |  |  |  |  | # collect each feature | 
| 179 | 5 |  |  |  |  | 12 | while (my $f = $iterator->next_seq) { | 
| 180 |  |  |  |  |  |  |  | 
| 181 |  |  |  |  |  |  | # determine position to record | 
| 182 | 244 |  |  |  |  | 20256 | my $position; | 
| 183 | 244 | 50 |  |  |  | 338 | if ($f->start == $f->end) { | 
| 184 |  |  |  |  |  |  | # just one position recorded | 
| 185 | 0 |  |  |  |  | 0 | $position = $f->start; | 
| 186 |  |  |  |  |  |  | } | 
| 187 |  |  |  |  |  |  | else { | 
| 188 |  |  |  |  |  |  | # calculate the midpoint | 
| 189 | 244 |  |  |  |  | 2596 | $position = int( | 
| 190 |  |  |  |  |  |  | ( ($f->start + $f->end) / 2) + 0.5 | 
| 191 |  |  |  |  |  |  | ); | 
| 192 |  |  |  |  |  |  | } | 
| 193 |  |  |  |  |  |  |  | 
| 194 |  |  |  |  |  |  | # check the position | 
| 195 |  |  |  |  |  |  | next unless ( | 
| 196 |  |  |  |  |  |  | # want to avoid those whose midpoint are not technically | 
| 197 |  |  |  |  |  |  | # within the region of interest | 
| 198 | 244 | 100 | 100 |  |  | 2862 | $position >= $param->[STRT] and $position <= $param->[STOP] | 
| 199 |  |  |  |  |  |  | ); | 
| 200 |  |  |  |  |  |  |  | 
| 201 |  |  |  |  |  |  | # record the value | 
| 202 | 225 | 100 |  |  |  | 385 | if ($param->[METH] eq 'count') { | 
|  |  | 100 |  |  |  |  |  | 
|  |  | 100 |  |  |  |  |  | 
| 203 | 44 |  |  |  |  | 134 | $pos2score{$position} += 1; | 
| 204 |  |  |  |  |  |  | } | 
| 205 |  |  |  |  |  |  | elsif ($param->[METH] eq 'ncount') { | 
| 206 | 44 |  | 50 |  |  | 134 | $pos2score{$position} ||= []; | 
| 207 | 44 |  | 33 |  |  | 45 | push @{ $pos2score{$position} }, $f->display_name || | 
|  | 44 |  |  |  |  | 75 |  | 
| 208 |  |  |  |  |  |  | $f->primary_id; | 
| 209 |  |  |  |  |  |  | } | 
| 210 |  |  |  |  |  |  | elsif ($param->[METH] eq 'pcount') { | 
| 211 | 44 | 100 | 100 |  |  | 63 | $pos2score{$position} += 1 if | 
| 212 |  |  |  |  |  |  | ($f->start >= $param->[STRT] and $f->end <= $param->[STOP]); | 
| 213 |  |  |  |  |  |  | } | 
| 214 |  |  |  |  |  |  | else { | 
| 215 |  |  |  |  |  |  | # everything else we take the score | 
| 216 | 93 |  |  |  |  | 90 | push @{ $pos2score{$position} }, $f->score; | 
|  | 93 |  |  |  |  | 215 |  | 
| 217 |  |  |  |  |  |  | } | 
| 218 |  |  |  |  |  |  | } | 
| 219 |  |  |  |  |  |  | } | 
| 220 |  |  |  |  |  |  |  | 
| 221 |  |  |  |  |  |  | # combine multiple datapoints at the same position | 
| 222 | 5 | 100 | 100 |  |  | 113 | if ($param->[METH] eq 'ncount') { | 
|  |  | 100 |  |  |  |  |  | 
|  |  | 50 |  |  |  |  |  | 
|  |  | 0 |  |  |  |  |  | 
|  |  | 0 |  |  |  |  |  | 
|  |  | 0 |  |  |  |  |  | 
|  |  | 0 |  |  |  |  |  | 
| 223 | 1 |  |  |  |  | 6 | foreach my $position (keys %pos2score) { | 
| 224 | 44 |  |  |  |  | 38 | my %name2count; | 
| 225 | 44 |  |  |  |  | 43 | foreach (@{$pos2score{$position}}) { $name2count{$_} += 1 } | 
|  | 44 |  |  |  |  | 46 |  | 
|  | 44 |  |  |  |  | 64 |  | 
| 226 | 44 |  |  |  |  | 57 | $pos2score{$position} = scalar(keys %name2count); | 
| 227 |  |  |  |  |  |  | } | 
| 228 |  |  |  |  |  |  | } | 
| 229 |  |  |  |  |  |  | elsif ($param->[METH] eq 'count' or $param->[METH] eq 'pcount') { | 
| 230 |  |  |  |  |  |  | # do nothing, these aren't arrays | 
| 231 |  |  |  |  |  |  | } | 
| 232 |  |  |  |  |  |  | elsif ($param->[METH] eq 'mean') { | 
| 233 | 2 |  |  |  |  | 12 | foreach my $position (keys %pos2score) { | 
| 234 | 93 |  |  |  |  | 113 | $pos2score{$position} = sum( @{$pos2score{$position}} ) / | 
| 235 | 93 |  |  |  |  | 82 | scalar( @{$pos2score{$position}} ); | 
|  | 93 |  |  |  |  | 123 |  | 
| 236 |  |  |  |  |  |  | } | 
| 237 |  |  |  |  |  |  | } | 
| 238 |  |  |  |  |  |  | elsif ($param->[METH] eq 'median') { | 
| 239 | 0 |  |  |  |  | 0 | foreach my $position (keys %pos2score) { | 
| 240 | 0 |  |  |  |  | 0 | $pos2score{$position} = median( @{$pos2score{$position}} ); | 
|  | 0 |  |  |  |  | 0 |  | 
| 241 |  |  |  |  |  |  | } | 
| 242 |  |  |  |  |  |  | } | 
| 243 |  |  |  |  |  |  | elsif ($param->[METH] eq 'min') { | 
| 244 | 0 |  |  |  |  | 0 | foreach my $position (keys %pos2score) { | 
| 245 | 0 |  |  |  |  | 0 | $pos2score{$position} = min( @{$pos2score{$position}} ); | 
|  | 0 |  |  |  |  | 0 |  | 
| 246 |  |  |  |  |  |  | } | 
| 247 |  |  |  |  |  |  | } | 
| 248 |  |  |  |  |  |  | elsif ($param->[METH] eq 'max') { | 
| 249 | 0 |  |  |  |  | 0 | foreach my $position (keys %pos2score) { | 
| 250 | 0 |  |  |  |  | 0 | $pos2score{$position} = max( @{$pos2score{$position}} ); | 
|  | 0 |  |  |  |  | 0 |  | 
| 251 |  |  |  |  |  |  | } | 
| 252 |  |  |  |  |  |  | } | 
| 253 |  |  |  |  |  |  | elsif ($param->[METH] eq 'sum') { | 
| 254 | 0 |  |  |  |  | 0 | foreach my $position (keys %pos2score) { | 
| 255 | 0 |  |  |  |  | 0 | $pos2score{$position} = sum( @{$pos2score{$position}} ); | 
|  | 0 |  |  |  |  | 0 |  | 
| 256 |  |  |  |  |  |  | } | 
| 257 |  |  |  |  |  |  | } | 
| 258 |  |  |  |  |  |  | else { | 
| 259 |  |  |  |  |  |  | # just take the mean for everything else | 
| 260 | 0 |  |  |  |  | 0 | foreach my $position (keys %pos2score) { | 
| 261 | 0 |  |  |  |  | 0 | $pos2score{$position} = sum( @{$pos2score{$position}} ) / | 
| 262 | 0 |  |  |  |  | 0 | scalar( @{$pos2score{$position}} ); | 
|  | 0 |  |  |  |  | 0 |  | 
| 263 |  |  |  |  |  |  | } | 
| 264 |  |  |  |  |  |  | } | 
| 265 |  |  |  |  |  |  |  | 
| 266 |  |  |  |  |  |  | # return collected data | 
| 267 | 5 | 50 |  |  |  | 25 | return wantarray ? %pos2score : \%pos2score; | 
| 268 |  |  |  |  |  |  | } | 
| 269 |  |  |  |  |  |  |  | 
| 270 |  |  |  |  |  |  |  | 
| 271 |  |  |  |  |  |  |  | 
| 272 |  |  |  |  |  |  | sub open_useq_db { | 
| 273 |  |  |  |  |  |  |  | 
| 274 |  |  |  |  |  |  | # path | 
| 275 | 2 |  |  | 2 | 1 | 3 | my $useqfile = shift; | 
| 276 | 2 |  |  |  |  | 3 | my $path = $useqfile; | 
| 277 | 2 |  |  |  |  | 6 | $path =~ s/^file://; # clean up file prefix if present | 
| 278 |  |  |  |  |  |  |  | 
| 279 |  |  |  |  |  |  | # open | 
| 280 | 2 |  |  |  |  | 2 | my $useq; | 
| 281 | 2 |  |  |  |  | 3 | eval { | 
| 282 | 2 |  |  |  |  | 10 | $useq = Bio::DB::USeq->new($path); | 
| 283 |  |  |  |  |  |  | }; | 
| 284 | 2 | 50 |  |  |  | 2923 | return unless $useq; | 
| 285 |  |  |  |  |  |  |  | 
| 286 | 2 |  |  |  |  | 6 | return $useq; | 
| 287 |  |  |  |  |  |  | } | 
| 288 |  |  |  |  |  |  |  | 
| 289 |  |  |  |  |  |  |  | 
| 290 |  |  |  |  |  |  |  | 
| 291 |  |  |  |  |  |  | ### Internal subroutine for getting the cached USeq object | 
| 292 |  |  |  |  |  |  | sub _get_useq { | 
| 293 | 12 |  |  | 12 |  | 20 | my $useqfile = shift; | 
| 294 |  |  |  |  |  |  |  | 
| 295 | 12 | 100 |  |  |  | 27 | return $OPENED_USEQ{$useqfile} if exists $OPENED_USEQ{$useqfile}; | 
| 296 |  |  |  |  |  |  |  | 
| 297 |  |  |  |  |  |  | # open and cache the USeq object | 
| 298 | 1 | 50 |  |  |  | 2 | my $useq = open_useq_db($useqfile) or | 
| 299 |  |  |  |  |  |  | croak " Unable to open USeq file '$useqfile'! $!\n"; | 
| 300 | 1 |  |  |  |  | 2 | $OPENED_USEQ{$useqfile} = $useq; | 
| 301 |  |  |  |  |  |  |  | 
| 302 |  |  |  |  |  |  | # record the chromosomes and possible variants | 
| 303 | 1 |  |  |  |  | 1 | $USEQ_CHROMOS{$useqfile} = {}; | 
| 304 | 1 |  |  |  |  | 3 | foreach my $s ($useq->seq_ids) { | 
| 305 | 1 |  |  |  |  | 7 | $USEQ_CHROMOS{$useqfile}{$s} = $s; | 
| 306 | 1 | 50 |  |  |  | 3 | if ($s =~ /^chr(.+)$/) { | 
| 307 | 1 |  |  |  |  | 3 | $USEQ_CHROMOS{$useqfile}{$1} = $s; | 
| 308 |  |  |  |  |  |  | } | 
| 309 |  |  |  |  |  |  | else { | 
| 310 | 0 |  |  |  |  | 0 | $USEQ_CHROMOS{$useqfile}{"chr$s"} = $s; | 
| 311 |  |  |  |  |  |  | } | 
| 312 |  |  |  |  |  |  | } | 
| 313 | 1 |  |  |  |  | 2 | return $useq; | 
| 314 |  |  |  |  |  |  | } | 
| 315 |  |  |  |  |  |  |  | 
| 316 |  |  |  |  |  |  |  | 
| 317 |  |  |  |  |  |  |  | 
| 318 |  |  |  |  |  |  | __END__ |