Hi all,
this is a rather loose collection of some observations and questions that came to my mind while exploring floats and scaled decimals. Comments and patches appreciated.
1. Exponential notation in radix floats 13r0.1e2 --> 13.0 14r0.1e2 --> 14.0 15r0.1e2 --> 0.12948148148148148 "How can I specify the exponent for bases where e is treated a digit? Should this be possible in literal syntax?"
2. Exponent letters "Answer to myself re 1:" 15r0.1q2 --> 15.0 "Wow! Why is this supported in SqNumberParser>>#exponentLetters? I have seen this nowhere else. And just to uphold my question from above, think about this:" 26r0.1q2 --> 26.0 27r0.1q2 --> 0.0728039424884418
3. Limited precision in scaled decimals SpaceTally new spaceForInstance: 0.10s2 depth: 2. --> 48 SpaceTally new spaceForInstance: 0.1010101010101010101010101010101010101010101010101010101010101010s2 depth: 2. --> 128 "If not here, when is precision lost at all? Should the number parser truncate this? How can I compact my existing scaled decimal instances based on their scale?"
4. Scale in radix notation "Follow-up question for 3., so I could not really test this:" 2r0.10101s1 --> 0.6s1 2r0.10101s2 --> 0.65s2 "I would rather have expected 0.5s1 and 0.5s1 here. So, the current behavior seems to be that the scale always refers to the decimal representation of the number even though the literal is written in a different base? Does this actually make any sense or should we disallow this combination of radix and scale? Or can we translate the scale to between the numeral systems, i.e., (sourceBase ** sourceScale - 1 log: targetBase) ceiling?"
5. Printing scaled decimals in base 1s printStringBase: 2 --> error: SubclassResponsibility: My ScaledDecimal subclass should have overridden printOn:base: "Seems to be missing yet..."
6. Beyond base 36 "This is clear:" 35 printStringBase: 36 --> 'Z' 36rZ --> 35 "But then..." 36 printStringBase: 37 --> '[' 37r[ --> syntax error: a digit between 0 and [ expected ->[ "D'oh! And the error message does not really make it clearer. :) Should we disallow radix base 37 and larger? Or can we just make it so that 44r~^é evaluates to 77263?"
Best, Christoph
--- Sent from Squeak Inbox Talk
Hi Christoph,
Le lun. 26 juin 2023 à 20:42, christoph.thiede@student.hpi.uni-potsdam.de a écrit :
Hi all,
this is a rather loose collection of some observations and questions that came to my mind while exploring floats and scaled decimals. Comments and patches appreciated.
*1. Exponential notation in radix floats* 13r0.1e2 --> 13.0 14r0.1e2 --> 14.0 15r0.1e2 --> 0.12948148148148148
*"How can I specify the exponent for bases where e is treated a digit? Should this be possible in literal syntax?"*
This used to work in the past, because once upon a time, only uppercase ABCDEF were accepted as hexadecimal digits (and up to Z in base 36). But when we extended hexadecimals to lowercase, we broke it. I think that this was http://source.squeak.org/trunk/Multilingual-ar.87. http://source.squeak.org/trunk/Multilingual-ar.87.mczdiff Since this is a rarely used feature, and since this would probably require a change in literal syntax, we did not restore the feature, leaving it half broken...
What syntax would you propose for it?
*2. Exponent letters*
*"Answer to myself re 1:" *15r0.1q2 --> 15.0
*"Wow! Why is this supported in SqNumberParser>>#exponentLetters? I have seen this nowhere else. And just to uphold my question from above, think about this:" *26r0.1q2 --> 26.0 27r0.1q2 --> 0.0728039424884418
If I remember, q is in ANSI standard, you'll have to check... e = exponent d = exponent for double precision q = exponent for quadruple precision The dialect is free to implement whatever precision. In Squeak, we currently support only double precision Float, but still interpret the ANSI syntax and round to (nearest I hope) Float. Some dialects support the 3 kinds of Float (LimitedPrecisionReal) Note that long float of C is not necessarily quadruple precision, it's often the 96 bits float of legacy intel math proc (with 80 bits significand). If I remember, ANSI Smalltalk made no provision for distinguishing this kind from quadruple thru the exponent letter.
Also note that the exponent part is always a decimal 2r0.1e10 is 512, not 2 And we cannot write 2r0.1e2r10.
*3. Limited precision in scaled decimals* SpaceTally new spaceForInstance: 0.10s2 depth: 2. --> 48 SpaceTally new spaceForInstance: 0.1010101010101010101010101010101010101010101010101010101010101010s2 depth: 2. --> 128
*"If not here, when is precision lost at all? Should the number parser truncate this? How can I compact my existing scaled decimal instances based on their scale?"*
Currently ScaledDecimals don't truncate. They are just Fraction in disguise (Fractions that print differently, and approximately)
*4. Scale in radix notation **"Follow-up question for 3., so I could not really test this:"* 2r0.10101s1 --> 0.6s1 2r0.10101s2 --> 0.65s2 *"I would rather have expected 0.5s1 and 0.5s1 here. So, the current behavior seems to be that the scale always refers to the decimal representation of the number even though the literal is written in a different base? Does this actually make any sense or should we disallow this combination of radix and scale? Or can we translate the scale to between the numeral systems, i.e., (sourceBase ** sourceScale - 1 log: targetBase) ceiling?"*
I think it's all in the name, ScaledDecimals print in decimal form (which means base 10). So it's not unsurprising that the scale inst.var. specifies the number of decimal places, rather than the number of places after fraction separator in whatever base. Maybe you would like some form of FixedPointNumber of the form numerator / (base raisedTo: scale), of maybe with an absolutely arbitrary scale numerator / scale, where numerator is an Integer, and with rounding rules like round to nearest, tie to even ?
*5. Printing scaled decimals in base *1s printStringBase: 2 --> error: SubclassResponsibility: My ScaledDecimal subclass should have overridden printOn:base: *"Seems to be missing yet..."*
Yes. But how many digits are going to be printed after the fraction separator ? What are the requirements ? Enough digits so that the re-interpreted string prints as the original ?
*6. Beyond base 36 **"This is clear:"* 35 printStringBase: 36 --> 'Z' 36rZ --> 35
IMO, we should better signal an Error at this stage
*"But then..." *36 printStringBase: 37 --> '[' 37r[ --> syntax error: a digit between 0 and [ expected ->[ *"D'oh! And the error message does not really make it clearer. :) Should we disallow radix base 37 and larger? Or can we just make it so that 44r~^é evaluates to 77263?"*
Best, Christoph
*Sent from **Squeak Inbox Talk https://github.com/hpi-swa-lab/squeak-inbox-talk*
Le lun. 26 juin 2023 à 22:00, Nicolas Cellier < nicolas.cellier.aka.nice@gmail.com> a écrit :
Hi Christoph,
Le lun. 26 juin 2023 à 20:42, christoph.thiede@student.hpi.uni-potsdam.de a écrit :
Hi all,
this is a rather loose collection of some observations and questions that came to my mind while exploring floats and scaled decimals. Comments and patches appreciated.
*1. Exponential notation in radix floats* 13r0.1e2 --> 13.0 14r0.1e2 --> 14.0 15r0.1e2 --> 0.12948148148148148
*"How can I specify the exponent for bases where e is treated a digit? Should this be possible in literal syntax?"*
This used to work in the past, because once upon a time, only uppercase ABCDEF were accepted as hexadecimal digits (and up to Z in base 36). But when we extended hexadecimals to lowercase, we broke it. I think that this was http://source.squeak.org/trunk/Multilingual-ar.87. http://source.squeak.org/trunk/Multilingual-ar.87.mczdiff Since this is a rarely used feature, and since this would probably require a change in literal syntax, we did not restore the feature, leaving it half broken...
What syntax would you propose for it?
*2. Exponent letters*
*"Answer to myself re 1:" *15r0.1q2 --> 15.0
*"Wow! Why is this supported in SqNumberParser>>#exponentLetters? I have seen this nowhere else. And just to uphold my question from above, think about this:" *26r0.1q2 --> 26.0 27r0.1q2 --> 0.0728039424884418
If I remember, q is in ANSI standard, you'll have to check... e = exponent d = exponent for double precision q = exponent for quadruple precision The dialect is free to implement whatever precision. In Squeak, we currently support only double precision Float, but still interpret the ANSI syntax and round to (nearest I hope) Float. Some dialects support the 3 kinds of Float (LimitedPrecisionReal) Note that long float of C is not necessarily quadruple precision, it's often the 96 bits float of legacy intel math proc (with 80 bits significand). If I remember, ANSI Smalltalk made no provision for distinguishing this kind from quadruple thru the exponent letter.
Hem, must be drunk, I mean the 80 bit long float with 64 bits significan, sorry.
Also note that the exponent part is always a decimal 2r0.1e10 is 512, not 2 And we cannot write 2r0.1e2r10.
*3. Limited precision in scaled decimals* SpaceTally new spaceForInstance: 0.10s2 depth: 2. --> 48 SpaceTally new spaceForInstance: 0.1010101010101010101010101010101010101010101010101010101010101010s2 depth: 2. --> 128
*"If not here, when is precision lost at all? Should the number parser truncate this? How can I compact my existing scaled decimal instances based on their scale?"*
Currently ScaledDecimals don't truncate. They are just Fraction in disguise (Fractions that print differently, and approximately)
*4. Scale in radix notation **"Follow-up question for 3., so I could not really test this:"* 2r0.10101s1 --> 0.6s1 2r0.10101s2 --> 0.65s2 *"I would rather have expected 0.5s1 and 0.5s1 here. So, the current behavior seems to be that the scale always refers to the decimal representation of the number even though the literal is written in a different base? Does this actually make any sense or should we disallow this combination of radix and scale? Or can we translate the scale to between the numeral systems, i.e., (sourceBase ** sourceScale - 1 log: targetBase) ceiling?"*
I think it's all in the name, ScaledDecimals print in decimal form (which means base 10). So it's not unsurprising that the scale inst.var. specifies the number of decimal places, rather than the number of places after fraction separator in whatever base. Maybe you would like some form of FixedPointNumber of the form numerator / (base raisedTo: scale), of maybe with an absolutely arbitrary scale numerator / scale, where numerator is an Integer, and with rounding rules like round to nearest, tie to even ?
*5. Printing scaled decimals in base *1s printStringBase: 2 --> error: SubclassResponsibility: My ScaledDecimal subclass should have overridden printOn:base: *"Seems to be missing yet..."*
Yes. But how many digits are going to be printed after the fraction separator ? What are the requirements ? Enough digits so that the re-interpreted string prints as the original ?
*6. Beyond base 36 **"This is clear:"* 35 printStringBase: 36 --> 'Z' 36rZ --> 35
IMO, we should better signal an Error at this stage
*"But then..." *36 printStringBase: 37 --> '[' 37r[ --> syntax error: a digit between 0 and [ expected ->[ *"D'oh! And the error message does not really make it clearer. :) Should we disallow radix base 37 and larger? Or can we just make it so that 44r~^é evaluates to 77263?"*
Best, Christoph
*Sent from **Squeak Inbox Talk https://github.com/hpi-swa-lab/squeak-inbox-talk*
search for thread '[Pharo-project] 16rff is looking for a fix :)' around february 2010 or an even older one http://lists.squeakfoundation.org/pipermail/squeak-dev/2000-March/013368.htm...
Le lun. 26 juin 2023 à 22:05, Nicolas Cellier < nicolas.cellier.aka.nice@gmail.com> a écrit :
Le lun. 26 juin 2023 à 22:00, Nicolas Cellier < nicolas.cellier.aka.nice@gmail.com> a écrit :
Hi Christoph,
Le lun. 26 juin 2023 à 20:42, < christoph.thiede@student.hpi.uni-potsdam.de> a écrit :
Hi all,
this is a rather loose collection of some observations and questions that came to my mind while exploring floats and scaled decimals. Comments and patches appreciated.
*1. Exponential notation in radix floats* 13r0.1e2 --> 13.0 14r0.1e2 --> 14.0 15r0.1e2 --> 0.12948148148148148
*"How can I specify the exponent for bases where e is treated a digit? Should this be possible in literal syntax?"*
This used to work in the past, because once upon a time, only uppercase ABCDEF were accepted as hexadecimal digits (and up to Z in base 36). But when we extended hexadecimals to lowercase, we broke it. I think that this was http://source.squeak.org/trunk/Multilingual-ar.87. http://source.squeak.org/trunk/Multilingual-ar.87.mczdiff Since this is a rarely used feature, and since this would probably require a change in literal syntax, we did not restore the feature, leaving it half broken...
What syntax would you propose for it?
*2. Exponent letters*
*"Answer to myself re 1:" *15r0.1q2 --> 15.0
*"Wow! Why is this supported in SqNumberParser>>#exponentLetters? I have seen this nowhere else. And just to uphold my question from above, think about this:" *26r0.1q2 --> 26.0 27r0.1q2 --> 0.0728039424884418
If I remember, q is in ANSI standard, you'll have to check... e = exponent d = exponent for double precision q = exponent for quadruple precision The dialect is free to implement whatever precision. In Squeak, we currently support only double precision Float, but still interpret the ANSI syntax and round to (nearest I hope) Float. Some dialects support the 3 kinds of Float (LimitedPrecisionReal) Note that long float of C is not necessarily quadruple precision, it's often the 96 bits float of legacy intel math proc (with 80 bits significand). If I remember, ANSI Smalltalk made no provision for distinguishing this kind from quadruple thru the exponent letter.
Hem, must be drunk, I mean the 80 bit long float with 64 bits significan, sorry.
Also note that the exponent part is always a decimal 2r0.1e10 is 512, not 2 And we cannot write 2r0.1e2r10.
*3. Limited precision in scaled decimals* SpaceTally new spaceForInstance: 0.10s2 depth: 2. --> 48 SpaceTally new spaceForInstance: 0.1010101010101010101010101010101010101010101010101010101010101010s2 depth: 2. --> 128
*"If not here, when is precision lost at all? Should the number parser truncate this? How can I compact my existing scaled decimal instances based on their scale?"*
Currently ScaledDecimals don't truncate. They are just Fraction in disguise (Fractions that print differently, and approximately)
*4. Scale in radix notation **"Follow-up question for 3., so I could not really test this:"* 2r0.10101s1 --> 0.6s1 2r0.10101s2 --> 0.65s2 *"I would rather have expected 0.5s1 and 0.5s1 here. So, the current behavior seems to be that the scale always refers to the decimal representation of the number even though the literal is written in a different base? Does this actually make any sense or should we disallow this combination of radix and scale? Or can we translate the scale to between the numeral systems, i.e., (sourceBase ** sourceScale - 1 log: targetBase) ceiling?"*
I think it's all in the name, ScaledDecimals print in decimal form (which means base 10). So it's not unsurprising that the scale inst.var. specifies the number of decimal places, rather than the number of places after fraction separator in whatever base. Maybe you would like some form of FixedPointNumber of the form numerator / (base raisedTo: scale), of maybe with an absolutely arbitrary scale numerator / scale, where numerator is an Integer, and with rounding rules like round to nearest, tie to even ?
*5. Printing scaled decimals in base *1s printStringBase: 2 --> error: SubclassResponsibility: My ScaledDecimal subclass should have overridden printOn:base: *"Seems to be missing yet..."*
Yes. But how many digits are going to be printed after the fraction separator ? What are the requirements ? Enough digits so that the re-interpreted string prints as the original ?
*6. Beyond base 36 **"This is clear:"* 35 printStringBase: 36 --> 'Z' 36rZ --> 35
IMO, we should better signal an Error at this stage
*"But then..." *36 printStringBase: 37 --> '[' 37r[ --> syntax error: a digit between 0 and [ expected ->[ *"D'oh! And the error message does not really make it clearer. :) Should we disallow radix base 37 and larger? Or can we just make it so that 44r~^é evaluates to 77263?"*
Best, Christoph
*Sent from **Squeak Inbox Talk https://github.com/hpi-swa-lab/squeak-inbox-talk*
Hi Nicolas,
thanks for your detailed reply and for the pointers!
See replies inline...
On 2023-06-26T22:32:41+02:00, nicolas.cellier.aka.nice@gmail.com wrote:
search for thread '[Pharo-project] 16rff is looking for a fix :)' around february 2010 or an even older one http://lists.squeakfoundation.org/pipermail/squeak-dev/2000-March/013368.htm...
Le lun. 26 juin 2023 à 22:05, Nicolas Cellier < nicolas.cellier.aka.nice(a)gmail.com> a écrit :
Le lun. 26 juin 2023 à 22:00, Nicolas Cellier < nicolas.cellier.aka.nice(a)gmail.com> a écrit :
Hi Christoph,
Le lun. 26 juin 2023 à 20:42, < christoph.thiede(a)student.hpi.uni-potsdam.de> a écrit :
Hi all,
this is a rather loose collection of some observations and questions that came to my mind while exploring floats and scaled decimals. Comments and patches appreciated.
*1. Exponential notation in radix floats* 13r0.1e2 --> 13.0 14r0.1e2 --> 14.0 15r0.1e2 --> 0.12948148148148148
*"How can I specify the exponent for bases where e is treated a digit? Should this be possible in literal syntax?"*
This used to work in the past, because once upon a time, only uppercase ABCDEF were accepted as hexadecimal digits (and up to Z in base 36). But when we extended hexadecimals to lowercase, we broke it. I think that this was http://source.squeak.org/trunk/Multilingual-ar.87. http://source.squeak.org/trunk/Multilingual-ar.87.mczdiff Since this is a rarely used feature, and since this would probably require a change in literal syntax, we did not restore the feature, leaving it half broken...
What syntax would you propose for it?
I don't know. In retrospect, IMHO lowercase letters should porbbaly never have been allowed as digits. I guess I can live with the status quo, esp. since "e" in the meaning of "*16^" is pretty rare in general. But it is nice read the original discussion about it. :-)
*2. Exponent letters*
*"Answer to myself re 1:" *15r0.1q2 --> 15.0
*"Wow! Why is this supported in SqNumberParser>>#exponentLetters? I have seen this nowhere else. And just to uphold my question from above, think about this:" *26r0.1q2 --> 26.0 27r0.1q2 --> 0.0728039424884418
If I remember, q is in ANSI standard, you'll have to check... e = exponent d = exponent for double precision q = exponent for quadruple precision The dialect is free to implement whatever precision. In Squeak, we currently support only double precision Float, but still interpret the ANSI syntax and round to (nearest I hope) Float. Some dialects support the 3 kinds of Float (LimitedPrecisionReal) Note that long float of C is not necessarily quadruple precision, it's often the 96 bits float of legacy intel math proc (with 80 bits significand). If I remember, ANSI Smalltalk made no provision for distinguishing this kind from quadruple thru the exponent letter.
Hem, must be drunk, I mean the 80 bit long float with 64 bits significan, sorry.
Also note that the exponent part is always a decimal 2r0.1e10 is 512, not 2 And we cannot write 2r0.1e2r10.
Unfortunately. :-) But now we can do at least this:
(SqNumberParser on: '0.1e10' readStream) defaultBase: 2; nextNumber "2.0"
*3. Limited precision in scaled decimals* SpaceTally new spaceForInstance: 0.10s2 depth: 2. --> 48 SpaceTally new spaceForInstance: 0.1010101010101010101010101010101010101010101010101010101010101010s2 depth: 2. --> 128
*"If not here, when is precision lost at all? Should the number parser truncate this? How can I compact my existing scaled decimal instances based on their scale?"*
Currently ScaledDecimals don't truncate. They are just Fraction in disguise (Fractions that print differently, and approximately)
Wow, *that* really confuses me. I always have heard/assumed that "ScaledDecimals are more precise than floats but performant" but the opposite will be the case if you do many computations with different denominators. For example:
s := 1.00s. 10000 timesRepeat: [ s := s + (997 atRandom / 997 atRandom)]. s. "36907.94s2" SpaceTally new spaceForInstance: s depth: 3 "432"
Is this a large undocumented todo?
*4. Scale in radix notation **"Follow-up question for 3., so I could not really test this:"* 2r0.10101s1 --> 0.6s1 2r0.10101s2 --> 0.65s2 *"I would rather have expected 0.5s1 and 0.5s1 here. So, the current behavior seems to be that the scale always refers to the decimal representation of the number even though the literal is written in a different base? Does this actually make any sense or should we disallow this combination of radix and scale? Or can we translate the scale to between the numeral systems, i.e., (sourceBase ** sourceScale - 1 log: targetBase) ceiling?"*
I think it's all in the name, ScaledDecimals print in decimal form (which means base 10).
Oh, you're right. Given that, a scaled decimal in a different base does not actually make sense, does it? Should we support 2r1s at all?
So it's not unsurprising that the scale inst.var. specifies the number of decimal places, rather than the number of places after fraction separator in whatever base. Maybe you would like some form of FixedPointNumber of the form numerator / (base raisedTo: scale), of maybe with an absolutely arbitrary scale numerator / scale, where numerator is an Integer, and with rounding rules like round to nearest, tie to even ?
Exactly that would have been my prior assumptions about ScaledDecimal. Yes. Maybe someone feels like upgrading ScaledDecimal to such a class in the future, i.e. by implementation truncation and a configurable base/numerator? :-)
*5. Printing scaled decimals in base *1s printStringBase: 2 --> error: SubclassResponsibility: My ScaledDecimal subclass should have overridden printOn:base: *"Seems to be missing yet..."*
Yes. But how many digits are going to be printed after the fraction separator ? What are the requirements ? Enough digits so that the re-interpreted string prints as the original ?
Good question. Yes? To avoid a DNU at all, I guess I would even be fine with (self asFloat printStringBase: base) , 's' , scale ...
*6. Beyond base 36 **"This is clear:"* 35 printStringBase: 36 --> 'Z' 36rZ --> 35
IMO, we should better signal an Error at this stage
Agreed. No bases >36. :-)
*"But then..." *36 printStringBase: 37 --> '[' 37r[ --> syntax error: a digit between 0 and [ expected ->[ *"D'oh! And the error message does not really make it clearer. :) Should we disallow radix base 37 and larger? Or can we just make it so that 44r~^é evaluates to 77263?"*
Best, Christoph
*Sent from **Squeak Inbox Talk https://github.com/hpi-swa-lab/squeak-inbox-talk*
Best, Christoph
--- Sent from Squeak Inbox Talk
squeak-dev@lists.squeakfoundation.org