QuadFloat.st
changeset 4983 696dd6d07736
child 4991 9d86d1eb2a65
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/QuadFloat.st	Thu Jun 06 20:51:40 2019 +0200
@@ -0,0 +1,162 @@
+"{ Package: 'stx:libbasic2' }"
+
+"{ NameSpace: Smalltalk }"
+
+LimitedPrecisionReal variableByteSubclass:#QuadFloat
+	instanceVariableNames:''
+	classVariableNames:'QuadFloatZero QuadFloatOne Pi E Epsilon NaN PositiveInfinity
+		NegativeInfinity Halfpi HalfpiNegative'
+	poolDictionaries:''
+	category:'Magnitude-Numbers'
+!
+
+!QuadFloat class methodsFor:'documentation'!
+
+documentation
+"
+    QuadFloats represent rational numbers with limited precision
+    and are mapped to IEEE quadruple precision format (128bit).
+    If the underlying cpu supports them natively, the machine format (long double) is
+    used. Otherwise, a software emulation is done, which is much slower.
+    Thus only use them, if you really need the additional precision;
+    if not, use Float (which are doubles) or LongFloats which usually have IEEE extended precision (80bit).
+
+    QuadFloats give you definite 128 bit quadruple floats,
+    thus, code using quadFloats is guaranteed to be portable from one architecture to another.
+
+    Representation:
+        gcc-sparc:
+            128bit quadruple IEEE floats (16bytes);
+            112 bit mantissa,
+            16 bit exponent,
+            34 decimal digits (approx.)
+
+    Mixed mode arithmetic:
+        quadFloat op anyFloat    -> longFloat
+        longFloat op complex     -> complex
+
+    Range and precision of storage formats: see LimitedPrecisionReal >> documentation
+
+    [author:]
+        Claus Gittinger
+
+    [see also:]
+        Number
+        Float ShortFloat LongFloat Fraction FixedPoint Integer Complex
+        FloatArray DoubleArray
+        https://en.wikipedia.org/wiki/Extended_precision
+"
+! !
+
+!QuadFloat class methodsFor:'instance creation'!
+
+basicNew
+    "return a new quadFloat - here we return 0.0
+     - QuadFloats are usually NOT created this way ...
+     Its implemented here to allow things like binary store & load
+     of quadFloats.
+     (but it is not a good idea to store the bits of a float - the reader might have a
+      totally different representation - so floats should be
+      binary stored in a device independent format)."
+
+%{  /* NOCONTEXT */
+#ifndef __SCHTEAM__
+    OBJ newFloat;
+    if (sizeof(long double) == sizeof(quadfloat)) {
+        __qMKLFLOAT(newFloat, 0.0);   /* OBJECT ALLOCATION */
+    } else {
+        __qMKQFLOAT(newFloat, 0.0);   /* OBJECT ALLOCATION */
+    }
+    RETURN (newFloat);
+#endif /* not SCHTEAM */
+%}
+
+    "Created: / 06-06-2019 / 17:18:58 / Claus Gittinger"
+!
+
+fromFloat:aFloat
+    "return a new quadFloat, given a float value"
+
+%{  /* NOCONTEXT */
+#ifndef __SCHTEAM__
+    OBJ newFloat;
+    float128 f;
+
+    if (__isFloatLike(aFloat)) {
+        float f = __floatVal(aFloat);
+        float128 qf = (LONGFLOAT)f;
+        __qMKQFLOAT(newFloat, lf);   /* OBJECT ALLOCATION */
+        RETURN (newFloat);
+    }
+#endif
+%}.
+    self error:'invalid argument'
+
+    "
+     QuadFloat fromFloat:123.0
+     123.0 asQuadFloat
+     123 asQuadFloat
+    "
+
+    "Created: / 06-06-2019 / 18:01:03 / Claus Gittinger"
+! !
+
+!QuadFloat class methodsFor:'coercing & converting'!
+
+coerce:aNumber
+    "convert the argument aNumber into an instance of the receiver's class and return it."
+
+    ^ aNumber asQuadFloat.
+
+    "Created: / 06-06-2019 / 16:51:01 / Claus Gittinger"
+! !
+
+!QuadFloat class methodsFor:'constants'!
+
+NaN
+    "return a shortFloat which represents not-a-Number (i.e. an invalid number)"
+
+    NaN isNil ifTrue:[
+        NaN := super NaN
+    ].
+    ^ NaN
+
+    "
+     self NaN
+    "
+
+    "Created: / 06-06-2019 / 16:56:09 / Claus Gittinger"
+!
+
+e
+    "return the constant e as quadFloat"
+
+    E isNil ifTrue:[
+        "/ eDigits has enough digits for 128bit IEEE quads
+        "/ do not use as a literal constant here - we cannot depend on the underlying C-compiler here...
+        E  := self readFrom:(Number eDigits)
+    ].
+    ^ E
+
+    "Created: / 06-06-2019 / 17:01:54 / Claus Gittinger"
+!
+
+pi
+    "return the constant pi as quadFloat"
+
+    Pi isNil ifTrue:[
+        "/ piDigits has enough digits for 128bit IEEE quads
+        "/ do not use as a literal constant here - we cannot depend on the underlying C-compiler here...
+        Pi  := self readFrom:(Number piDigits)
+    ].
+    ^ Pi
+
+    "Created: / 06-06-2019 / 17:09:51 / Claus Gittinger"
+! !
+
+!QuadFloat class methodsFor:'documentation'!
+
+version_CVS
+    ^ '$Header$'
+! !
+