Ahmed
2024-05-24 09:57:47 UTC
Hello,
In the thread:
https://www.novabbs.com/devel/article-flat.php?group=comp.lang.forth&id=16944&first=1&last=25#start
Paul Robin posted:
For example, sin (sine) is a function, whose input is a real and
whose
output is another real. And "derivative" (d/dx) is a function whose
input is a function, and whose output is another function. So you
get
that d/dx (sin) = cos, or some numerical approximation of same. In
Python or Haskell, this is easy, e.g.:
h = 0.0001
d_over_dx f = g where { g x = (f(x+h) - f(x)) / h }
dsin = d_over_dx sin
print (dsin 0.5) -- prints 0.8775585891507287
print (cos 0.5) -- prints 0.8775825618903728
Pretty close approximation. In Forth it is a bit messier because you
want a signature like
: d/dx ( xt -- xt ) .... ;
and you may have to do some advanced or non-portable things to create
new xt's on the fly like that. But there are various ways you can
get
equivalent functionality using OOP or whatever.
minforth replied:
Clumsy but portable:
0.0001e FVALUE h
DEFER ofunc ' FSIN IS ofunc
DEFER dfunc
: D/DX {: xt f: x -- y :}
x h f+ xt execute x xt execute f- h f/ ;
:NONAME ( x -- y ) ['] ofunc D/DX ; IS dfunc
0.5e dfunc f.
0.5e fcos f.
My question is:
Why not do it directly like this:
: d/dx ( xt -- )
create ,
does> @ dup ( f: x -- y) fdup 1e-4 f+ execute fswap 1e-4 f-
execute f- 0.5e4 f* ;
and the dervative of any function can be obtained directly like this:
' func() d/dx der_func()
for example: (in gforth)
' fsin d/dx der_fsin ok
0.5e fcos f. 0.877582561890373 ok
0.5e der_fsin f. 0.877582560427637 ok
another example:
: f() ( f: x -- y) fdup fdup f* f+ ; \ f(x) = x^2+x
: df() ( f: x -- y) 2e f* 1e f+ ; \ df(x) = 2*x + 1 for comparison
' f() d/dx der_f()
5e der_f() f. 10.9999999999744 ok
5e df() f. 11. ok
Best Regards.
In the thread:
https://www.novabbs.com/devel/article-flat.php?group=comp.lang.forth&id=16944&first=1&last=25#start
Paul Robin posted:
For example, sin (sine) is a function, whose input is a real and
whose
output is another real. And "derivative" (d/dx) is a function whose
input is a function, and whose output is another function. So you
get
that d/dx (sin) = cos, or some numerical approximation of same. In
Python or Haskell, this is easy, e.g.:
h = 0.0001
d_over_dx f = g where { g x = (f(x+h) - f(x)) / h }
dsin = d_over_dx sin
print (dsin 0.5) -- prints 0.8775585891507287
print (cos 0.5) -- prints 0.8775825618903728
Pretty close approximation. In Forth it is a bit messier because you
want a signature like
: d/dx ( xt -- xt ) .... ;
and you may have to do some advanced or non-portable things to create
new xt's on the fly like that. But there are various ways you can
get
equivalent functionality using OOP or whatever.
minforth replied:
Clumsy but portable:
0.0001e FVALUE h
DEFER ofunc ' FSIN IS ofunc
DEFER dfunc
: D/DX {: xt f: x -- y :}
x h f+ xt execute x xt execute f- h f/ ;
:NONAME ( x -- y ) ['] ofunc D/DX ; IS dfunc
0.5e dfunc f.
0.5e fcos f.
My question is:
Why not do it directly like this:
: d/dx ( xt -- )
create ,
does> @ dup ( f: x -- y) fdup 1e-4 f+ execute fswap 1e-4 f-
execute f- 0.5e4 f* ;
and the dervative of any function can be obtained directly like this:
' func() d/dx der_func()
for example: (in gforth)
' fsin d/dx der_fsin ok
0.5e fcos f. 0.877582561890373 ok
0.5e der_fsin f. 0.877582560427637 ok
another example:
: f() ( f: x -- y) fdup fdup f* f+ ; \ f(x) = x^2+x
: df() ( f: x -- y) 2e f* 1e f+ ; \ df(x) = 2*x + 1 for comparison
' f() d/dx der_f()
5e der_f() f. 10.9999999999744 ok
5e df() f. 11. ok
Best Regards.