@@ -1699,6 +1699,7 @@ custom_derive! {
16991699 /// ```
17001700 #[ cfg_attr( feature = "serde_feature" , derive( Serialize , Deserialize ) ) ]
17011701 #[ derive( NewtypeDeref ,
1702+ NewtypeDerefMut ,
17021703 NewtypeIndex ( usize ) ,
17031704 NewtypeIndexMut ( usize ) ,
17041705 NewtypeFrom ,
@@ -1911,7 +1912,7 @@ impl<'a> IntoIterator for &'a CigarString {
19111912 type IntoIter = :: std:: slice:: Iter < ' a , Cigar > ;
19121913
19131914 fn into_iter ( self ) -> Self :: IntoIter {
1914- ( & ( self . 0 ) ) . iter ( )
1915+ self . 0 . iter ( )
19151916 }
19161917}
19171918
@@ -1924,6 +1925,16 @@ impl fmt::Display for CigarString {
19241925 }
19251926}
19261927
1928+ // Get number of leading/trailing softclips if a CigarString taking hardclips into account
1929+ fn calc_softclips < ' a > ( mut cigar : impl DoubleEndedIterator < Item = & ' a Cigar > ) -> i64 {
1930+ match ( cigar. next ( ) , cigar. next ( ) ) {
1931+ ( Some ( Cigar :: HardClip ( _) ) , Some ( Cigar :: SoftClip ( s) ) ) | ( Some ( Cigar :: SoftClip ( s) ) , _) => {
1932+ * s as i64
1933+ }
1934+ _ => 0 ,
1935+ }
1936+ }
1937+
19271938#[ derive( Eq , PartialEq , Clone , Debug ) ]
19281939pub struct CigarStringView {
19291940 inner : CigarString ,
@@ -1960,24 +1971,12 @@ impl CigarStringView {
19601971
19611972 /// Get number of bases softclipped at the beginning of the alignment.
19621973 pub fn leading_softclips ( & self ) -> i64 {
1963- self . first ( ) . map_or ( 0 , |cigar| {
1964- if let Cigar :: SoftClip ( s) = cigar {
1965- * s as i64
1966- } else {
1967- 0
1968- }
1969- } )
1974+ calc_softclips ( self . iter ( ) )
19701975 }
19711976
19721977 /// Get number of bases softclipped at the end of the alignment.
19731978 pub fn trailing_softclips ( & self ) -> i64 {
1974- self . last ( ) . map_or ( 0 , |cigar| {
1975- if let Cigar :: SoftClip ( s) = cigar {
1976- * s as i64
1977- } else {
1978- 0
1979- }
1980- } )
1979+ calc_softclips ( self . iter ( ) . rev ( ) )
19811980 }
19821981
19831982 /// Get number of bases hardclipped at the beginning of the alignment.
@@ -2193,6 +2192,32 @@ mod tests {
21932192 assert_eq ! ( cigar. pos( ) , 5 ) ;
21942193 }
21952194
2195+ #[ test]
2196+ fn test_cigar_string_leading_softclips ( ) {
2197+ let cigar = CigarString ( vec ! [ Cigar :: SoftClip ( 10 ) , Cigar :: Match ( 100 ) ] ) . into_view ( 0 ) ;
2198+ assert_eq ! ( cigar. leading_softclips( ) , 10 ) ;
2199+ let cigar2 = CigarString ( vec ! [
2200+ Cigar :: HardClip ( 5 ) ,
2201+ Cigar :: SoftClip ( 10 ) ,
2202+ Cigar :: Match ( 100 ) ,
2203+ ] )
2204+ . into_view ( 0 ) ;
2205+ assert_eq ! ( cigar2. leading_softclips( ) , 10 ) ;
2206+ }
2207+
2208+ #[ test]
2209+ fn test_cigar_string_trailing_softclips ( ) {
2210+ let cigar = CigarString ( vec ! [ Cigar :: Match ( 100 ) , Cigar :: SoftClip ( 10 ) ] ) . into_view ( 0 ) ;
2211+ assert_eq ! ( cigar. trailing_softclips( ) , 10 ) ;
2212+ let cigar2 = CigarString ( vec ! [
2213+ Cigar :: Match ( 100 ) ,
2214+ Cigar :: SoftClip ( 10 ) ,
2215+ Cigar :: HardClip ( 5 ) ,
2216+ ] )
2217+ . into_view ( 0 ) ;
2218+ assert_eq ! ( cigar2. trailing_softclips( ) , 10 ) ;
2219+ }
2220+
21962221 #[ test]
21972222 fn test_cigar_read_pos ( ) {
21982223 let vpos = 5 ; // variant position
0 commit comments