Optimized Math.Sign
authorPent Ploompuu <kaalikas@gmail.com>
Tue, 16 May 2017 00:06:09 +0000 (03:06 +0300)
committerPent Ploompuu <kaalikas@gmail.com>
Tue, 30 May 2017 23:28:09 +0000 (02:28 +0300)
src/mscorlib/src/System/Decimal.cs
src/mscorlib/src/System/Math.cs

index ce59a99..80246cd 100644 (file)
@@ -803,6 +803,8 @@ namespace System
         [MethodImplAttribute(MethodImplOptions.InternalCall)]
         private static extern void FCallRound(ref Decimal d, int decimals);
 
+        internal static int Sign(ref decimal d) => (d.lo | d.mid | d.hi) == 0 ? 0 : (d.flags >> 31) | 1;
+
         // Subtracts two Decimal values.
         //
         public static Decimal Subtract(Decimal d1, Decimal d2)
index 6f7d731..33d0f77 100644 (file)
@@ -660,50 +660,17 @@ namespace System
         // Sign function for VB.  Returns -1, 0, or 1 if the sign of the number
         // is negative, 0, or positive.  Throws for floating point NaN's.
         [CLSCompliant(false)]
-        public static int Sign(sbyte value)
-        {
-            if (value < 0)
-                return -1;
-            else if (value > 0)
-                return 1;
-            else
-                return 0;
-        }
-
+        public static int Sign(sbyte value) => Sign((int)value);
 
         // Sign function for VB.  Returns -1, 0, or 1 if the sign of the number
         // is negative, 0, or positive.  Throws for floating point NaN's.
-        public static int Sign(short value)
-        {
-            if (value < 0)
-                return -1;
-            else if (value > 0)
-                return 1;
-            else
-                return 0;
-        }
+        public static int Sign(short value) => Sign((int)value);
 
         // Sign function for VB.  Returns -1, 0, or 1 if the sign of the number
         // is negative, 0, or positive.  Throws for floating point NaN's.
-        public static int Sign(int value)
-        {
-            if (value < 0)
-                return -1;
-            else if (value > 0)
-                return 1;
-            else
-                return 0;
-        }
+        public static int Sign(int value) => unchecked(value >> 31 | (int)((uint)-value >> 31));
 
-        public static int Sign(long value)
-        {
-            if (value < 0)
-                return -1;
-            else if (value > 0)
-                return 1;
-            else
-                return 0;
-        }
+        public static int Sign(long value) => unchecked((int)(value >> 63 | (long)((ulong)-value >> 63)));
 
         public static int Sign(float value)
         {
@@ -727,15 +694,7 @@ namespace System
             throw new ArithmeticException(SR.Arithmetic_NaN);
         }
 
-        public static int Sign(Decimal value)
-        {
-            if (value < 0)
-                return -1;
-            else if (value > 0)
-                return 1;
-            else
-                return 0;
-        }
+        public static int Sign(decimal value) => decimal.Sign(ref value);
 
         public static long BigMul(int a, int b)
         {