File tree 2 files changed +11
-31
lines changed
src/libraries/System.Runtime.Numerics 2 files changed +11
-31
lines changed Original file line number Diff line number Diff line change @@ -3481,42 +3481,19 @@ public static BigInteger TrailingZeroCount(BigInteger value)
3481
3481
3482
3482
ulong result = 0 ;
3483
3483
3484
- if ( value . _sign >= 0 )
3485
- {
3486
- // When the value is positive, we simply need to do a tzcnt for all bits until we find one set
3487
-
3488
- uint part = value . _bits [ 0 ] ;
3484
+ // Both positive values and their two's-complement negative representation will share the same TrailingZeroCount,
3485
+ // so the sign of value does not matter and both cases can be handled in the same way
3489
3486
3490
- for ( int i = 1 ; ( part == 0 ) && ( i < value . _bits . Length ) ; i ++ )
3491
- {
3492
- part = value . _bits [ i ] ;
3493
- result += ( sizeof ( uint ) * 8 ) ;
3487
+ uint part = value . _bits [ 0 ] ;
3494
3488
3495
- i ++ ;
3496
- }
3497
-
3498
- result += uint . TrailingZeroCount ( part ) ;
3499
- }
3500
- else
3489
+ for ( int i = 1 ; ( part == 0 ) && ( i < value . _bits . Length ) ; i ++ )
3501
3490
{
3502
- // When the value is negative, we need to tzcnt the two's complement representation
3503
- // We'll do this "inline" to avoid needing to unnecessarily allocate.
3504
-
3505
- uint part = ~ value . _bits [ 0 ] + 1 ;
3506
-
3507
- for ( int i = 1 ; ( part == 0 ) && ( i < value . _bits . Length ) ; i ++ )
3508
- {
3509
- // Simply process bits, adding the carry while the previous value is zero
3510
-
3511
- part = ~ value . _bits [ i ] + 1 ;
3512
- result += ( sizeof ( uint ) * 8 ) ;
3513
-
3514
- i ++ ;
3515
- }
3516
-
3517
- result += uint . TrailingZeroCount ( part ) ;
3491
+ part = value . _bits [ i ] ;
3492
+ result += ( sizeof ( uint ) * 8 ) ;
3518
3493
}
3519
3494
3495
+ result += uint . TrailingZeroCount ( part ) ;
3496
+
3520
3497
return result ;
3521
3498
}
3522
3499
Original file line number Diff line number Diff line change @@ -366,6 +366,9 @@ public static void TrailingZeroCountTest()
366
366
367
367
Assert . Equal ( ( BigInteger ) 63 , BinaryIntegerHelper < BigInteger > . TrailingZeroCount ( Int64MaxValuePlusOne ) ) ;
368
368
Assert . Equal ( ( BigInteger ) 0 , BinaryIntegerHelper < BigInteger > . TrailingZeroCount ( UInt64MaxValue ) ) ;
369
+
370
+ Assert . Equal ( ( BigInteger ) 1000 , BinaryIntegerHelper < BigInteger > . TrailingZeroCount ( BigInteger . Pow ( 2 , 1000 ) ) ) ;
371
+ Assert . Equal ( ( BigInteger ) 1000 , BinaryIntegerHelper < BigInteger > . TrailingZeroCount ( - BigInteger . Pow ( 2 , 1000 ) ) ) ;
369
372
}
370
373
371
374
[ Fact ]
You can’t perform that action at this time.
0 commit comments