1- ##Edits to Adam and Beth's main 'fastq_splitter_editted.py' script
2- # - Reverse complement polyT sequences
1+ ##Edits to Adam and Beth's main 'fastq_splitter_editted.py' script
2+ # - Reverse complement polyT sequences
33# - Remove UMI based QC processing - UMI can be dealt with by the tallytrin count pipeline
44# - Filters reads without polyA
55# . Error tolerance - -e parameter set number of mismatches/error tolerance - 0.3-0.4 seems to be a reasonable sensitivty for current test reads
@@ -141,7 +141,7 @@ def smith_waterman_search(self, sequence: str, read_name: str, primer: str, erro
141141
142142 # Perform Parasail alignment
143143 alignment = parasail .sw_trace_striped_16 (
144- window , search_primer ,
144+ search_primer , window ,
145145 self .open_gap_score , # Gap opening penalty
146146 self .extend_gap_score , # Gap extension penalty
147147 scoring_matrix
@@ -153,35 +153,40 @@ def smith_waterman_search(self, sequence: str, read_name: str, primer: str, erro
153153 continue # Skip this pattern if alignment failed
154154
155155 # Ensure start position is valid
156- start_position = max (0 , alignment .end_query - pattern_length + 1 + start )
157- end_position = min (len (sequence ), start_position + pattern_length )
156+ aligned_ref = alignment .traceback .ref
157+ aligned_ref_length = len (aligned_ref .replace ("-" , "" ))
158+ start_position = max (0 , alignment .end_ref - aligned_ref_length + 1 + start )
159+ end_position = min (len (sequence ), start + alignment .end_ref + 1 )
158160
159161 # Create a unique identifier for each match
160- match_key = (search_primer , start_position )
162+ match_key = (search_primer , start_position , end_position , aligned_ref_length , alignment . score )
161163
162164 # Avoid adding duplicates
163165 if match_key in seen_matches :
164166 continue # Skip duplicates
165167
166- # Otherwise, add to results
167- seen_matches .add (match_key )
168+ # Otherwise, add to results - moving this to add only hits that pass threshold
169+ # seen_matches.add(match_key)
168170
169171 if alignment .score >= min_score_threshold :
170172 # Extract actual alignment details
171- aligned_query = alignment .traceback .query
172- aligned_pattern = alignment .traceback .ref
173+ aligned_ref = alignment .traceback .ref
174+ aligned_pattern = alignment .traceback .query
173175
174176 # Count mismatches and gaps
175177
176178 #counts mismatches and gaps together
177- mismatches = sum (1 for a , b in zip (aligned_query , aligned_pattern ) if a != b )
179+ mismatches = sum (1 for a , b in zip (aligned_ref , aligned_pattern ) if a != b )
178180
179- #counts mismatch and gaps separately
180- #mismatches = sum(1 for q, p in zip(aligned_query , aligned_pattern) if q != p and q != '-' and p != '-')
181- gaps = aligned_query .count ('-' ) + aligned_pattern .count ('-' )
181+ #counts mismatch and gaps separately - can be uncommented if wanting to report separately
182+ #mismatches = sum(1 for q, p in zip(aligned_ref , aligned_pattern) if q != p and q != '-' and p != '-')
183+ gaps = aligned_ref .count ('-' ) + aligned_pattern .count ('-' )
182184
183-
185+ # note - max_mismatches here is mismatches + gaps together.
184186 if mismatches <= max_mismatches :
187+ # Add match positions to seen matches to avoid duplication in future searches
188+ seen_matches .add (match_key )
189+ # Take match params for next step
185190 matches .append ({
186191 'start' : start_position ,
187192 'end' : end_position ,
@@ -460,7 +465,13 @@ def parallel_split_reads(self, input_file: str, processed_output: str, lowqual_o
460465 bin_output: Output path for binned reads
461466 stats_output: Output path for statistics
462467 """
463-
468+ stats = {
469+ 'total_sequences' : 0 ,
470+ 'total_segments' : 0 ,
471+ 'processed' : 0 ,
472+ 'lowqual' : 0 ,
473+ 'binned' : 0
474+ }
464475 stats = {
465476 'total_reads' : 0 ,
466477 'processed_reads' : 0 ,
0 commit comments