From d3887853727b9c949b2a7295afa05c1631bfa152 Mon Sep 17 00:00:00 2001 From: Paul Irwin Date: Fri, 13 Dec 2024 10:19:49 -0700 Subject: [PATCH] PR feedback --- .../Support/Threading/AtomicDouble.cs | 58 +++++++++++++------ 1 file changed, 39 insertions(+), 19 deletions(-) diff --git a/src/Lucene.Net/Support/Threading/AtomicDouble.cs b/src/Lucene.Net/Support/Threading/AtomicDouble.cs index 814cf0fe9e..62225e7ab9 100644 --- a/src/Lucene.Net/Support/Threading/AtomicDouble.cs +++ b/src/Lucene.Net/Support/Threading/AtomicDouble.cs @@ -39,6 +39,10 @@ namespace Lucene.Net.Support.Threading /// It does not have the increment, decrement, and add methods because those operations are not atomic /// due to the conversion to/from . /// + /// + /// Note that this class is set up to mimic double in Java, rather than the J2N class. + /// This may cause differences in comparing NaN values. + /// #if FEATURE_SERIALIZABLE [Serializable] #endif @@ -60,7 +64,7 @@ public AtomicDouble() /// The initial value. public AtomicDouble(double value) { - this.value = BitConversion.DoubleToInt64Bits(value); + this.value = BitConversion.DoubleToRawInt64Bits(value); } /// @@ -78,7 +82,7 @@ public AtomicDouble(double value) public double Value { get => BitConversion.Int64BitsToDouble(Interlocked.Read(ref this.value)); - set => Interlocked.Exchange(ref this.value, BitConversion.DoubleToInt64Bits(value)); + set => Interlocked.Exchange(ref this.value, BitConversion.DoubleToRawInt64Bits(value)); } /// @@ -88,7 +92,7 @@ public double Value /// The previous value. public double GetAndSet(double newValue) { - return BitConversion.Int64BitsToDouble(Interlocked.Exchange(ref value, BitConversion.DoubleToInt64Bits(newValue))); + return BitConversion.Int64BitsToDouble(Interlocked.Exchange(ref value, BitConversion.DoubleToRawInt64Bits(newValue))); } /// @@ -101,8 +105,8 @@ public double GetAndSet(double newValue) /// was not equal to the expected value. public bool CompareAndSet(double expect, double update) { - long expectLong = BitConversion.DoubleToInt64Bits(expect); - long updateLong = BitConversion.DoubleToInt64Bits(update); + long expectLong = BitConversion.DoubleToRawInt64Bits(expect); + long updateLong = BitConversion.DoubleToRawInt64Bits(update); long rc = Interlocked.CompareExchange(ref value, updateLong, expectLong); return rc == expectLong; } @@ -118,7 +122,7 @@ public bool Equals(AtomicDouble? other) return false; // NOTE: comparing long values rather than floating point comparison - return value == other.value; + return Interlocked.Read(ref value) == Interlocked.Read(ref other.value); } /// @@ -129,7 +133,7 @@ public bool Equals(AtomicDouble? other) public bool Equals(double other) { // NOTE: comparing long values rather than floating point comparison - return value == BitConversion.DoubleToInt64Bits(other); + return Interlocked.Read(ref value) == BitConversion.DoubleToRawInt64Bits(other)); } /// @@ -303,10 +307,14 @@ public static implicit operator double(AtomicDouble atomicInt64) /// The first number. /// The second number. /// true if the given numbers are equal; otherwise, false. - public static bool operator ==(AtomicDouble a1, AtomicDouble a2) + public static bool operator ==(AtomicDouble? a1, AtomicDouble? a2) { - // NOTE: comparing long values rather than floating point comparison - return a1.value == a2.value; + if (a1 is null) + return a2 is null; + if (a2 is null) + return false; + + return a1.Equals(a2); } /// @@ -315,7 +323,7 @@ public static implicit operator double(AtomicDouble atomicInt64) /// The first number. /// The second number. /// true if the given numbers are not equal; otherwise, false. - public static bool operator !=(AtomicDouble a1, AtomicDouble a2) + public static bool operator !=(AtomicDouble? a1, AtomicDouble? a2) { return !(a1 == a2); } @@ -326,8 +334,11 @@ public static implicit operator double(AtomicDouble atomicInt64) /// The first number. /// The second number. /// true if the given numbers are equal; otherwise, false. - public static bool operator ==(AtomicDouble a1, double a2) + public static bool operator ==(AtomicDouble? a1, double a2) { + if (a1 is null) + return false; + return a1.Value.Equals(a2); } @@ -337,7 +348,7 @@ public static implicit operator double(AtomicDouble atomicInt64) /// The first number. /// The second number. /// true if the given numbers are not equal; otherwise, false. - public static bool operator !=(AtomicDouble a1, double a2) + public static bool operator !=(AtomicDouble? a1, double a2) { return !(a1 == a2); } @@ -348,8 +359,11 @@ public static implicit operator double(AtomicDouble atomicInt64) /// The first number. /// The second number. /// true if the given numbers are equal; otherwise, false. - public static bool operator ==(double a1, AtomicDouble a2) + public static bool operator ==(double a1, AtomicDouble? a2) { + if (a2 is null) + return false; + return a1.Equals(a2.Value); } @@ -359,7 +373,7 @@ public static implicit operator double(AtomicDouble atomicInt64) /// The first number. /// The second number. /// true if the given numbers are not equal; otherwise, false. - public static bool operator !=(double a1, AtomicDouble a2) + public static bool operator !=(double a1, AtomicDouble? a2) { return !(a1 == a2); } @@ -370,8 +384,11 @@ public static implicit operator double(AtomicDouble atomicInt64) /// The first number. /// The second number. /// true if the given numbers are equal; otherwise, false. - public static bool operator ==(AtomicDouble a1, double? a2) + public static bool operator ==(AtomicDouble? a1, double? a2) { + if (a1 is null) + return !a2.HasValue; + return a1.Value.Equals(a2.GetValueOrDefault()); } @@ -381,7 +398,7 @@ public static implicit operator double(AtomicDouble atomicInt64) /// The first number. /// The second number. /// true if the given numbers are not equal; otherwise, false. - public static bool operator !=(AtomicDouble a1, double? a2) + public static bool operator !=(AtomicDouble? a1, double? a2) { return !(a1 == a2); } @@ -392,8 +409,11 @@ public static implicit operator double(AtomicDouble atomicInt64) /// The first number. /// The second number. /// true if the given numbers are equal; otherwise, false. - public static bool operator ==(double? a1, AtomicDouble a2) + public static bool operator ==(double? a1, AtomicDouble? a2) { + if (!a1.HasValue) + return a2 is null; + return a1.GetValueOrDefault().Equals(a2.Value); } @@ -403,7 +423,7 @@ public static implicit operator double(AtomicDouble atomicInt64) /// The first number. /// The second number. /// true if the given numbers are not equal; otherwise, false. - public static bool operator !=(double? a1, AtomicDouble a2) + public static bool operator !=(double? a1, AtomicDouble? a2) { return !(a1 == a2); }