Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]


Groups > comp.lang.forth > #26622 > unrolled thread

Short and sweet (F.)

Started byBrad Eckert <hwfwguy@gmail.com>
First post2013-10-17 16:04 -0700
Last post2013-10-19 18:39 +0200
Articles 10 — 4 participants

Back to article view | Back to comp.lang.forth


Contents

  Short and sweet (F.) Brad Eckert <hwfwguy@gmail.com> - 2013-10-17 16:04 -0700
    Re: Short and sweet (F.) Brad Eckert <hwfwguy@gmail.com> - 2013-10-18 06:12 -0700
      Re: Short and sweet (F.) mhx@iae.nl - 2013-10-18 10:40 -0700
        Re: Short and sweet (F.) "Ed" <invalid@invalid.com> - 2013-10-19 11:58 +1000
        Re: Short and sweet (F.) Brad Eckert <hwfwguy@gmail.com> - 2013-10-20 07:12 -0700
          Re: Short and sweet (F.) Brad Eckert <hwfwguy@gmail.com> - 2013-10-20 08:51 -0700
            Re: Short and sweet (F.) Brad Eckert <hwfwguy@gmail.com> - 2013-10-20 09:20 -0700
            Re: Short and sweet (F.) "Ed" <invalid@invalid.com> - 2013-10-24 22:34 +1000
    Re: Short and sweet (F.) "Ed" <invalid@invalid.com> - 2013-10-19 11:12 +1000
      Re: Short and sweet (F.) Hans Bezemer <the.beez.speaks@gmail.com> - 2013-10-19 18:39 +0200

#26622 — Short and sweet (F.)

FromBrad Eckert <hwfwguy@gmail.com>
Date2013-10-17 16:04 -0700
SubjectShort and sweet (F.)
Message-ID<ac476f9d-1c23-49bf-aaa8-f0f32c22211f@googlegroups.com>
CREATE FPOWERS
 1E0 F, 1E1 F, 1E2 F, 1E3 F, 1E4 F, 1E5 F, 1E6 F, 1E7 F, 1E8 F, 1E9 F,
 1E10 F, 1E11 F, 1E12 F, 1E13 F, 1E14 F, 1E15 F, 1E16 F, 1E17 F, 1E18 F,

: (F.)  ( -- c_addr u ) ( float: r -- )
   FDUP F0< FABS  FDUP FLOG F>S        ( minus? log10[r] ) ( float: r )
   0 MAX                 \ for small r, trade readability for precision
   <#  >R  PRECISION 1- R@ -        ( minus? trailing ) ( R: log10[r] )
   DUP 0< IF  DROP                      \ r > 10^PRECISION
      R> 18 - 0 MAX  DUP >R             \ assuming decimal BASE,
      0 ?DO  10E0 F/  LOOP  F>D         \ reduce range if too big for #
   ELSE                                     \ ordinary numbers
      PRECISION FLOATS FPOWERS + F@ F* F>D  \ r*10^PRECISION
      R> 0 ?DO  #  LOOP  5 0 D+  #          \ round
      <# ROT 0 ?DO  #  LOOP  0 >R           \ after decimal
   THEN
   [CHAR] . HOLD
   R> 0 ?DO  [CHAR] 0 HOLD  LOOP        \ big num overflow
   #S  ROT SIGN  #>                     \ before decimal
;
: Q  ( f -- )
   CR FDUP F. CR (F.) TYPE ;

\ Improvement over typical F.
\ 1. Outputs to string
\ 2. Rounding
\ 3. Freakin' small

[toc] | [next] | [standalone]


#26630

FromBrad Eckert <hwfwguy@gmail.com>
Date2013-10-18 06:12 -0700
Message-ID<bd63bd4c-5947-441c-8336-118f4ca650a4@googlegroups.com>
In reply to#26622
On Thursday, October 17, 2013 7:04:25 PM UTC-4, Brad Eckert wrote:
> CREATE FPOWERS ...
> 
FLOG barfs on 0e0. Since FLOG isn't exact, I removed it. The following version of (F.) is a single 64x16 screen.

I wrote this to display floating point numbers by setting the text of dialog items in Windows. The built-in F. uses TYPE and EMIT.

\ Convert float to string                         2013.10.17 BNE
CREATE FPOWERS  1E0 F, 1E1 F, 1E2 F, 1E3 F, 1E4 F, 1E5 F, 1E6 F,
   1E7 F, 1E8 F, 1E9 F, 1E10 F, 1E11 F, 1E12 F, 1E13 F, 1E14 F,
   1E15 F, 1E16 F, 1E17 F, 1E18 F, : [PRS] FLOATS FPOWERS + F@ ;
: F.RIGHT  ( .right d -- d' )  5 0 D+ # <#  ROT 0 ?DO # LOOP ;
: (F.)  ( -- c_addr u ) ( float: r -- )
   <#  FDUP F0< FABS  0
   BEGIN FDUP DUP 1+ [PRS] F< 0=  OVER 18 < AND  WHILE 1+ REPEAT
   >R PRECISION 1- R@ -               ( -? .right | r: log10[r])
   DUP 0< IF  DROP                           \ r >= 10^PRECISION
      R> 18 - 0 MAX  DUP >R             \ assuming decimal BASE,
      0 ?DO  10E0 F/  LOOP  F>D  \ reduce range if too big for #
   ELSE  PRECISION [PRS] F* F>D               \ r * 10^PRECISION
      R>  0 ?DO # LOOP  F.RIGHT  0 >R   \ rounded, after decimal
   THEN  [CHAR] . HOLD  R> 0 ?DO [CHAR] 0 HOLD LOOP  \ 0overflow
   #S  ROT SIGN  #>  ;                         \ left of decimal

\ Float to string with fixed number of digits after the decimal
: (F.F)  ( digits -- c_addr u ) ( float: r -- )
   FDUP F0< SWAP  FABS  DUP 1+ [PRS] F* F>D
   <# F.RIGHT  [CHAR] . HOLD  #S  ROT SIGN  #>
;

[toc] | [prev] | [next] | [standalone]


#26635

Frommhx@iae.nl
Date2013-10-18 10:40 -0700
Message-ID<50a120cf-fe42-419b-9177-73d3584aa648@googlegroups.com>
In reply to#26630
On Friday, October 18, 2013 3:12:22 PM UTC+2, Brad Eckert wrote:
>> CREATE FPOWERS ...
>> 
> FLOG barfs on 0e0. Since FLOG isn't exact, I removed it. 

Then there is a problem with the IEEE arithmetic implementation 
in your Forth or on your CPU.

FORTH> 0e Q
0.000000000000000000
0.00000000000000000 ok

FORTH> 0e flog +e.                         -INF ok

FORTH> 3.141592653589793235e Q
3.141592653589793235
3.14159265358979323 ok

FORTH> -3.14159265358979325569e Q
-3.141592653589793256
-3.14159265358979326 ok

FORTH> 1e-19 Q
0.000000000000000000
0.00000000000000000 ok

FORTH> 5.6e-19 Q
0.000000000000000001
0.00000000000000000 ok

FORTH> 558123456789e-19 Q
0.000000055812345679
0.00000005581234568 ok

-marcel

[toc] | [prev] | [next] | [standalone]


#26639

From"Ed" <invalid@invalid.com>
Date2013-10-19 11:58 +1000
Message-ID<l3slho$it4$1@speranza.aioe.org>
In reply to#26635
mhx@iae.nl wrote:
> On Friday, October 18, 2013 3:12:22 PM UTC+2, Brad Eckert wrote:
> >> CREATE FPOWERS ...
> >>
> > FLOG barfs on 0e0. Since FLOG isn't exact, I removed it.
>
> Then there is a problem with the IEEE arithmetic implementation
> in your Forth or on your CPU.
>
> FORTH> 0e Q
> 0.000000000000000000
> 0.00000000000000000 ok
>
> FORTH> 0e flog +e.                         -INF ok

Log(0) is an ambiguous condition so expect anything.


[toc] | [prev] | [next] | [standalone]


#26654

FromBrad Eckert <hwfwguy@gmail.com>
Date2013-10-20 07:12 -0700
Message-ID<25b4e671-a604-458f-bd6c-44766db674fd@googlegroups.com>
In reply to#26635
On Friday, October 18, 2013 1:40:18 PM UTC-4, m...@iae.nl wrote:
> 
> Then there is a problem with the IEEE arithmetic implementation 
> 

Actually, FLOG is fine. F>S throws a "divide by 0" error on -INF.

> 
> FORTH> 3.141592653589793235e Q
> 3.141592653589793235
> 3.14159265358979323 ok
> 

There's a difference between how SwiftForth and your forth interpret PRECISION.

I should probably use a variable instead of the system's PRECISION so (F.) can have different precision than F0= and friends.

[toc] | [prev] | [next] | [standalone]


#26655

FromBrad Eckert <hwfwguy@gmail.com>
Date2013-10-20 08:51 -0700
Message-ID<eb821afd-6e40-4caf-aae4-316c5afb5cbf@googlegroups.com>
In reply to#26654
On Sunday, October 20, 2013 10:12:59 AM UTC-4, Brad Eckert wrote:
> On Friday, October 18, 2013 1:40:18 PM UTC-4, m...@iae.nl wrote:
> 
>> FORTH> 3.141592653589793235e Q
>> 3.141592653589793235
>> 3.14159265358979323 ok
>  
> There's a difference between how SwiftForth and your forth interpret
> PRECISION.
> 

Leading zeros don't count in the "significant figures".

3 set-precision  ok
pi f. 3.14  ok  <--- iForth may print 3.141
pi 1e1 f/ f. 0.31  ok  <--- SwiftForth drops the 4
pi 1e2 f* f. 314.  ok
pi 1e3 f* f. 3140.  ok

[toc] | [prev] | [next] | [standalone]


#26656

FromBrad Eckert <hwfwguy@gmail.com>
Date2013-10-20 09:20 -0700
Message-ID<563d104d-0bcf-4bb4-8778-8d857f4348a4@googlegroups.com>
In reply to#26655
On Sunday, October 20, 2013 11:51:31 AM UTC-4, Brad Eckert wrote:
> 3 set-precision  ok
> pi f. 3.14  ok  <--- iForth may print 3.141
> pi 1e1 f/ f. 0.31  ok  <--- SwiftForth drops the 4
> pi 1e2 f* f. 314.  ok
> pi 1e3 f* f. 3140.  ok

I'll just follow SwiftForth on this. Handling the "<1 case" is an unnecessary hassle.

I made PRECISION variable in the following code, which is two blocks
plus shadow blocks. I've taken to putting shadow blocks to the 
side (starting at column 68) in text files and labeling them such
that formatting programs can switch back and forth between screen,
80-column text and 132-column text files.

\ Convert float to string [1/2]                   2013.10.18 BNE
CREATE FPOWERS  1E0 F, 1E1 F, 1E2 F, 1E3 F, 1E4 F, 1E5 F, 1E6 F,
   1E7 F, 1E8 F, 1E9 F, 1E10 F, 1E11 F, 1E12 F, 1E13 F, 1E14 F,
   1E15 F, 1E16 F, 1E17 F, 1E18 F,
VARIABLE FP.DIGITS  8 FP.DIGITS !  ( significant digits )
: FPWR[N]  ( idx -- r )  FLOATS FPOWERS + F@ ;
: F.RIGHT  ( .right d -- d' )  5 0 D+ # <#  ROT 0 ?DO # LOOP ;
: (F.F)  ( digits -- c_addr u ) ( float: r -- )
   FDUP F0< SWAP  FABS  DUP 1+ FPWR[N] F* F>D
   <# F.RIGHT  [CHAR] . HOLD  #S  ROT SIGN  #> ;
: FENORM  ( granularity -- exponent ) ( float: r1 -- r2 )
   >R  FDUP F0<  FABS  0               ( -? exponent | r: gran )
   BEGIN  FDUP 1E0 F<      WHILE  1E18 F*  18 -  REPEAT
   BEGIN  FDUP 1E18 F< 0=  WHILE  1E17 F/  17 +  REPEAT  18
   BEGIN  2DUP + R@ MOD  FDUP OVER FPWR[N] F< OR WHILE 1- REPEAT
   DUP FPWR[N] F/  + SWAP  R> DROP  IF FNEGATE THEN ;

\ Convert float to string [1/2]                   2013.10.18 BNE
\ Table of 10^n, where n ranges
\   from 0 to the number of digits in a signed double.

\ Digits of precision in FP output
\ Gets floating point 10^idx, where idx = 0 to 18.
\ Convert digits right of decimal, discards last digit to round.
\ Float to string with fixed number of digits after the decimal.
\   Assume total number of digits is less than 19.

\ Normalize float for scientific or engineering output.
\   Granularity is 3 for engineering format, 1 for scientific.
\   Increase r to 1.0 or above.
\   If very large, decrease to 1.0 or above.
\   Look up divisor, skipping to lower divisors to meet
\   granularity requirement. Avoids noise of multiple "10e0 F/".

\ Convert float to string [2/2]                   2013.10.18 BNE
: (F.)  ( -- c_addr u ) ( float: r -- )
   <#  FDUP F0< FABS  FLOG 0E0 FMAX F>S >R  FP.DIGITS @ 1- R@ -
   DUP 0< IF  DROP  R> 18 - 0 MAX  DUP >R
      0 ?DO  10E0 F/  LOOP  F>D
   ELSE  FP.DIGITS @  FPWR[N] F* F>D
      R>  0 ?DO # LOOP  F.RIGHT  0 >R
   THEN  [CHAR] . HOLD  R> 0 ?DO [CHAR] 0 HOLD LOOP
   #S  ROT SIGN  #>  ;
: (FES)  ( gran -- |f: r -- ) FENORM (F.) TYPE ." E" (.) TYPE ;
: FS.  ( r -- )  1 (FES) ;  : FE.  ( r -- )  3 (FES) ;

\ Convert float to string [2/2]                   2013.10.18 BNE
\ Convert float to a string using numeric output buffer.
\   Save sign, get numbers to the right of the decimal.
\   There are more digits in this number than FP.DIGITS wants.
\   Assuming decimal BASE, reduce range if too big for F>D.
\   r * 10^FP.DIGITS
\   Round up and convert the part to the right of the decimal.
\   Really big numbers have trailing zeros.
\   Convert stuff left of the decimal.
\ Simple text output of scientific numbers:
\ if you need string output, you'll need to concatenate stuff.

: Q  ( r -- )  CR  FDUP F. FDUP CR  (F.) TYPE CR ;

4 FP.DIGITS !  4 SET-PRECISION

: PIS  ( lo hi -- )  SWAP DO PI 10e0 I S>F F** F* Q LOOP ;
-3 20 PIS
 9.99999999999E0 Q
10.00000000001E0 Q

[toc] | [prev] | [next] | [standalone]


#26671

From"Ed" <invalid@invalid.com>
Date2013-10-24 22:34 +1000
Message-ID<l4b0me$dnr$1@speranza.aioe.org>
In reply to#26655
Brad Eckert wrote:
> ...
>
> 3 set-precision  ok
> pi f. 3.14  ok  <--- iForth may print 3.141
> pi 1e1 f/ f. 0.31  ok  <--- SwiftForth drops the 4

iForth interpreted PRECISION to mean 'decimal places'

> Leading zeros don't count in the "significant figures".

Clearly they do in the SwiftForth universe :)


[toc] | [prev] | [next] | [standalone]


#26638

From"Ed" <invalid@invalid.com>
Date2013-10-19 11:12 +1000
Message-ID<l3sise$e5m$1@speranza.aioe.org>
In reply to#26622
Brad Eckert wrote:
> ...
> \ Improvement over typical F.
> \ 1. Outputs to string
> \ 2. Rounding
> \ 3. Freakin' small

Compare with 'fracout' posted a year ago ...

1. Output to string
2. Rounding
3. Smaller (165 bytes vs. 248 for short&sweet)
4. No dependency on mantissa fitting a double number

    fracout:
    -1e 3e f/  15 (f.)  cr type
    -0.333333333333333

    short&sweet:
    -1e 3e f/  (f.)  cr type
    -0.00000214748365

5. No dependency on separate f.p stack
6. Optional comma'd output

Fracout is king, long live fracout!






[toc] | [prev] | [next] | [standalone]


#26648

FromHans Bezemer <the.beez.speaks@gmail.com>
Date2013-10-19 18:39 +0200
Message-ID<5262b4e8$0$15961$e4fe514c@news2.news.xs4all.nl>
In reply to#26638
Ed wrote:

> Fracout is king, long live fracout!
Agreed! Added to the 4tH library - easy (much easier than.. you know..)
port! Thx!!

Hans Bezemer

[toc] | [prev] | [standalone]


Back to top | Article view | comp.lang.forth


csiph-web