Skip to content

Commit

Permalink
Ensure Hypot for double handles insignificant results
Browse files Browse the repository at this point in the history
  • Loading branch information
tannergooding committed Jun 22, 2024
1 parent 753df42 commit 09dd755
Show file tree
Hide file tree
Showing 3 changed files with 16 additions and 8 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,7 @@ public static Vector128<T> Invoke(Vector128<T> x, Vector128<T> y)
|| (typeof(T) == typeof(nint)));

return Vector128.ConditionalSelect(
(Vector128.GreaterThan(xMag, yMag) & IsPositive(yMag)) | IsNegative(xMag),
(Vector128.GreaterThan(xMag, yMag) & IsPositive(yMag)) | (Vector128.Equals(xMag, yMag) & IsNegative(y)) | IsNegative(xMag),
x,
y
);
Expand Down Expand Up @@ -95,7 +95,7 @@ public static Vector256<T> Invoke(Vector256<T> x, Vector256<T> y)
|| (typeof(T) == typeof(nint)));

return Vector256.ConditionalSelect(
(Vector256.GreaterThan(xMag, yMag) & IsPositive(yMag)) | IsNegative(xMag),
(Vector256.GreaterThan(xMag, yMag) & IsPositive(yMag)) | (Vector256.Equals(xMag, yMag) & IsNegative(y)) | IsNegative(xMag),
x,
y
);
Expand Down Expand Up @@ -137,7 +137,7 @@ public static Vector512<T> Invoke(Vector512<T> x, Vector512<T> y)
|| (typeof(T) == typeof(nint)));

return Vector512.ConditionalSelect(
(Vector512.GreaterThan(xMag, yMag) & IsPositive(yMag)) | IsNegative(xMag),
(Vector512.GreaterThan(xMag, yMag) & IsPositive(yMag)) | (Vector512.Equals(xMag, yMag) & IsNegative(y)) | IsNegative(xMag),
x,
y
);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,7 @@ public static Vector128<T> Invoke(Vector128<T> x, Vector128<T> y)
|| (typeof(T) == typeof(nint)));

return Vector128.ConditionalSelect(
(Vector128.LessThan(xMag, yMag) & IsPositive(xMag)) | IsNegative(yMag),
(Vector128.LessThan(xMag, yMag) & IsPositive(xMag)) | (Vector128.Equals(xMag, yMag) & IsNegative(x)) | IsNegative(yMag),
x,
y
);
Expand Down Expand Up @@ -94,7 +94,7 @@ public static Vector256<T> Invoke(Vector256<T> x, Vector256<T> y)
|| (typeof(T) == typeof(nint)));

return Vector256.ConditionalSelect(
(Vector256.LessThan(xMag, yMag) & IsPositive(xMag)) | IsNegative(yMag),
(Vector256.LessThan(xMag, yMag) & IsPositive(xMag)) | (Vector256.Equals(xMag, yMag) & IsNegative(x)) | IsNegative(yMag),
x,
y
);
Expand Down Expand Up @@ -136,7 +136,7 @@ public static Vector512<T> Invoke(Vector512<T> x, Vector512<T> y)
|| (typeof(T) == typeof(nint)));

return Vector512.ConditionalSelect(
(Vector512.LessThan(xMag, yMag) & IsPositive(xMag)) | IsNegative(yMag),
(Vector512.LessThan(xMag, yMag) & IsPositive(xMag)) | (Vector512.Equals(xMag, yMag) & IsNegative(x)) | IsNegative(yMag),
x,
y
);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -336,6 +336,13 @@ public static TVectorDouble HypotDouble<TVectorDouble, TVectorUInt64>(TVectorDou

TVectorUInt64 expDiff = xExp - yExp;

// Cover cases where x or y is insignifican compared to the other
TVectorDouble insignificanMask = Unsafe.BitCast<TVectorUInt64, TVectorDouble>(
TVectorUInt64.GreaterThanOrEqual(expDiff, TVectorUInt64.Create(double.SignificandLength + 1)) &
TVectorUInt64.LessThanOrEqual(expDiff, TVectorUInt64.Create(unchecked((ulong)(-double.SignificandLength - 1))))
);
TVectorDouble insignificantResult = ax + ay;

// To prevent overflow, scale down by 2^+600
TVectorUInt64 expBiasP500 = TVectorUInt64.Create(double.ExponentBias + 500);
TVectorUInt64 scaleDownMask = TVectorUInt64.GreaterThan(xExp, expBiasP500) | TVectorUInt64.GreaterThan(yExp, expBiasP500);
Expand Down Expand Up @@ -427,6 +434,7 @@ public static TVectorDouble HypotDouble<TVectorDouble, TVectorUInt64>(TVectorDou
// the inputs is NaN. Otherwise if either input
// is NaN, we return NaN

result = TVectorDouble.ConditionalSelect(insignificanMask, insignificantResult, result);
result = TVectorDouble.ConditionalSelect(nanMask, TVectorDouble.Create(double.NaN), result);
result = TVectorDouble.ConditionalSelect(infinityMask, TVectorDouble.Create(double.PositiveInfinity), result);

Expand Down Expand Up @@ -1179,7 +1187,7 @@ public static TVector MaxMagnitudeNumber<TVector, T>(TVector x, TVector y)
|| (typeof(T) == typeof(nint)));

return TVector.ConditionalSelect(
(TVector.GreaterThan(xMag, yMag) & TVector.IsPositive(yMag)) | TVector.IsNegative(xMag),
(TVector.LessThan(xMag, yMag) & TVector.IsPositive(xMag)) | (TVector.Equals(xMag, yMag) & TVector.IsNegative(x)) | TVector.IsNegative(yMag),
x,
y
);
Expand Down Expand Up @@ -1266,7 +1274,7 @@ public static TVector MinMagnitudeNumber<TVector, T>(TVector x, TVector y)
|| (typeof(T) == typeof(nint)));

return TVector.ConditionalSelect(
(TVector.LessThan(xMag, yMag) & TVector.IsPositive(xMag)) | TVector.IsNegative(yMag),
(TVector.LessThan(xMag, yMag) & TVector.IsPositive(xMag)) | (TVector.Equals(xMag, yMag) & TVector.IsNegative(x)) | TVector.IsNegative(yMag),
x,
y
);
Expand Down

0 comments on commit 09dd755

Please sign in to comment.