# Bug in number? function after (require malt)

**URL:** <https://racket.discourse.group/t/bug-in-number-function-after-require-malt/3192>\
**Category:** General\
**Created:** [October 1, 2024, 11:36pm UTC](https://racket.discourse.group/t/bug-in-number-function-after-require-malt/3192 "2024-10-01T23:36:10Z")\
**Posts on this page:** 13\
**Page:** 1

<div class="post-metadata">

**Author:** ![fweyt](https://yyz2.discourse-cdn.com/free1/user_avatar/racket.discourse.group/fweyt/32/1953_2.png) [@fweyt](https://racket.discourse.group/u/fweyt)\
**Post date:** [October 1, 2024, 11:36pm UTC](https://racket.discourse.group/t/bug-in-number-function-after-require-malt/3192/1 "2024-10-01T23:36:10Z")

</div>

(number? pi) =\> #t and (number? (/ pi 1)) ==\> #t  
after (require malt) the number? function behaves different  
(number? pi) ==\> still #t but (number? (/ pi 1) ==\> #f???

---

<div class="post-metadata">

**Author:** ![shawnw](https://yyz2.discourse-cdn.com/free1/user_avatar/racket.discourse.group/shawnw/32/1031_2.png) [@shawnw](https://racket.discourse.group/u/shawnw)\
**Post date:** [October 1, 2024, 11:44pm UTC](https://racket.discourse.group/t/bug-in-number-function-after-require-malt/3192/2 "2024-10-01T23:44:06Z")

</div>

The `malt` language redefines [math functions like `/`](https://docs.racket-lang.org/malt/diffable-fns.html#%28part._overridden%29) that accept and return tensors. Doesn't look like it provides an updated `number?` that's aware of those types.

---

<div class="post-metadata">

**Author:** ![fweyt](https://yyz2.discourse-cdn.com/free1/user_avatar/racket.discourse.group/fweyt/32/1953_2.png) [@fweyt](https://racket.discourse.group/u/fweyt)\
**Post date:** [October 3, 2024, 6:32pm UTC](https://racket.discourse.group/t/bug-in-number-function-after-require-malt/3192/3 "2024-10-03T18:32:10Z")

</div>

Overwriting a function with exact the same name, makes the old function unavailable.

My workaround is to re-define /, (define div /), before calling (require malt). Not elegant at all.

Is there a possibility to put a namespace before a function in Scheme? Like math. / or malt./

How is such problem solved in scheme?  
I have no experience with libraries or modules in Scheme.

---

<div class="post-metadata">

**Author:** ![shhyou](https://avatars.discourse-cdn.com/v4/letter/s/ccd318/32.png) [@shhyou](https://racket.discourse.group/u/shhyou)\
**Post date:** [October 3, 2024, 7:11pm UTC](https://racket.discourse.group/t/bug-in-number-function-after-require-malt/3192/4 "2024-10-03T19:11:05Z")

</div>

```racket
(require (prefix-in malt: malt))

```

Then all the `malt` functions are imported with the prefix `malt:`.

---

<div class="post-metadata">

**Author:** ![shawnw](https://yyz2.discourse-cdn.com/free1/user_avatar/racket.discourse.group/shawnw/32/1031_2.png) [@shawnw](https://racket.discourse.group/u/shawnw)\
**Post date:** [October 3, 2024, 9:27pm UTC](https://racket.discourse.group/t/bug-in-number-function-after-require-malt/3192/5 "2024-10-03T21:27:19Z")

</div>

The documentation I linked to earlier mentions it in passing; you should `(require malt/base-no-overrides)` instead; that stops things like `/` from being overridden (use `d/` to get the Malt version). For more options and details see [2&nbsp;Entry points](https://docs.racket-lang.org/malt/Entry_points.html)

---

<div class="post-metadata">

**Author:** ![fweyt](https://yyz2.discourse-cdn.com/free1/user_avatar/racket.discourse.group/fweyt/32/1953_2.png) [@fweyt](https://racket.discourse.group/u/fweyt)\
**Post date:** [October 4, 2024, 3:55am UTC](https://racket.discourse.group/t/bug-in-number-function-after-require-malt/3192/6 "2024-10-04T03:55:56Z")

</div>

Indeed it's written there. Sorry, my brain shuts down on so many possibilties for using malt.

I want to calculate the (gradient-of sin (/ pi 4)).  
==\> contract violation saying that 0.7853... is no number  
because / is overridden and the number is now a tensor-0.  
After some feedback here I use the primitive-/ in malt by writing:  
(require malt/base-no-overrides)  
(gradient-of d-sin (/ pi 4))  
==\> now gradient-of is undefined?  
Why, It is not overridden?

This overriding is a nice thing to write concise code, but it comes at a cost: I have to start reading manuals, to be able to use a primitive function.

It would be nice if one could grab back to another implementation of the same funtion name, by putting a prefix before it. Like primitive-/ instead of having to change the require call and put a d- before all overriden malt functions.

Hmmm, now I'm asking Racket to be modified because I can't read the manual. That's no good.

Anyway I'm still stuck on a simple calculation.

---

<div class="post-metadata">

**Author:** ![LiberalArtist](https://yyz2.discourse-cdn.com/free1/user_avatar/racket.discourse.group/liberalartist/32/151_2.png) [@LiberalArtist](https://racket.discourse.group/u/LiberalArtist)\
**Post date:** [October 4, 2024, 1:32pm UTC](https://racket.discourse.group/t/bug-in-number-function-after-require-malt/3192/7 "2024-10-04T13:32:53Z")

</div>

> [@fweyt](#):
>
> It would be nice if one could grab back to another implementation of the same funtion name, by putting a prefix before it. Like primitive-/ instead of having to change the require call and put a d- before all overriden malt functions.

You can write something like `(require (prefix-in r: racket))` (or `racket/base`) to be able to write `r:/`.

In general, it might be helpful to keep in mind that “overridden” functions aren’t mutated or “monkey-patched” the way a function might be in Ruby, JavaScript, or Python. What happens is that bindings imported with `require` shadow bindings for the same name that come from the `#lang`, in just the same way that `let` can locally shadow bindings from some wider scope.

---

<div class="post-metadata">

**Author:** ![AlexG](https://avatars.discourse-cdn.com/v4/letter/a/ecc23a/32.png) [@AlexG](https://racket.discourse.group/u/AlexG)\
**Post date:** [October 8, 2024, 12:08am UTC](https://racket.discourse.group/t/bug-in-number-function-after-require-malt/3192/8 "2024-10-08T00:08:58Z")

</div>

> I want to calculate the (gradient-of sin (/ pi 4)).  
> ==\> contract violation saying that 0.7853... is no number

Ah, yes, I came across this sort of thing too.  
It happens because "gradient-of" expects the first argument, i.e. the function, to be able to handle tensors, not plain old numbers. IOW, to be what the text calls an "extended" function.

For instance you will see that  
`(gradient-of sqrt (/ pi 4))` works just fine, as "sqrt" is already suitably defined.  
Also, if you `(define (square x)(* x x)` then  
`(gradient-of square (/ pi 4))` will also work correctly.

This is because the arithmetic functions `+,-,*,/` are already extended to work for tensors, so any composition of them will also be "extended".

I'm not really sure what to recommend in this case, but I guess you'll have to find a way to extend the trigonometric primitives if you want to use AD on them. I need to know the system a bit better before I can recommend a method, to avoid giving you a bum steer.

It is a _malt_ issue, however, not a _Racket_ one!

PS. Interestingly enough, both `exp` and `expt` are defined in _malt_, so you can do stuff like

```scheme
> (gradient-of exp 1)
2.718281828459045
> (gradient-of (curryr expt 1/3) 27)
0.037037037037037035

```

with no problem. You could easily, e.g. define hyperbolic functions! 😃  
It's just poor old sine, cosine and tangent that have not yet joined the party.

However, here's an example of a workaround for `sin`, using complex numbers:

```scheme
(define i (sqrt -1))
(define neg-i (* -1 i))
(define (sin z) (/ (- (exp (* i z))(exp (* neg-i z))) (* 2 i)))

> (gradient-of sin (/ pi 4))
0.7071067811865476+0.0i

```

---

<div class="post-metadata">

**Author:** ![AlexG](https://avatars.discourse-cdn.com/v4/letter/a/ecc23a/32.png) [@AlexG](https://racket.discourse.group/u/AlexG)\
**Post date:** [October 8, 2024, 6:06pm UTC](https://racket.discourse.group/t/bug-in-number-function-after-require-malt/3192/9 "2024-10-08T18:06:35Z")

</div>

I also found that it will work if you define sine in terms of its Taylor expansion.  
First, some auxilliary stuff, for series...  
`foldl` will not work if used with `range` (you can't do AD on it). So we provide our own Sigma routine, `sum`, which **can** be differentiated.  
Remember, all extended functions, are in terms of `tensor`, not `number`.  
Effectively, _malt_ highjacks all numbers into tensors.

```scheme
(define ((reduce op init) term a next b)
  (define (reduce-tr a tot)
    (cond ((> a b) tot)
	  (else (reduce-tr (next a) (op tot (term a))))))
  (reduce-tr a init))

(define sum (reduce + 0))
(define prod (reduce * 1))
(define (inc n)(+ 1 n))
(define (factorial n)
  (if (< n 2) 1
      (prod identity 2.0 inc n)))

```

Now, with the above, it's easy:

```scheme
(define (sine x)
  (sum (λ(n)(/ (* (expt -1 n)(expt x (inc (* 2 n))))
               (factorial (inc (* 2 n)))))
       0 inc 20))

> (gradient-of sine (/ pi 4))
0.7071067811865475

```

Just for fun

```scheme
(define cosine (curry gradient-of sine))
> (cosine (/ pi 2))
4.253941440428854e-17
> (cosine (/ pi 6))
0.8660254037844386
> (cosine (/ pi 3))
0.5000000000000001

```

PS. However, the above does yield a bug: :beetle:

```scheme
> (cosine 0)
. . log: division by zero
> 

```

I won't bother with it for now 🙂 , the _malt_ library is newish, just define the cos Taylor series longhand, and it should work fine!

```scheme
(define (cosine x)
  (sum (λ(n)
         (/ (* (expt -1 n)(expt x (* 2 n)))
            (factorial (* 2 n))))
       0 inc 20))

```

---

<div class="post-metadata">

**Author:** ![AlexG](https://avatars.discourse-cdn.com/v4/letter/a/ecc23a/32.png) [@AlexG](https://racket.discourse.group/u/AlexG)\
**Post date:** [October 9, 2024, 12:44am UTC](https://racket.discourse.group/t/bug-in-number-function-after-require-malt/3192/10 "2024-10-09T00:44:41Z")

</div>

So I guess the quick answer is:  
For any function to be Automatically Differentiable in _malt_ it **must** be composed of primitives that have already been defined as differentiable im _malt_ (and which return tensors when applied to their args) see [here](https://docs.racket-lang.org/malt/diffable-fns.html)

Sin and cos have **not** yet been defined as diff/able primitives in _malt_, so they must be composed by other such primitives, e.g. using complex numbers or Taylor series like in the two examples above.

I am sure there is a simple way to add them as primitives (thus gaining efficiency) using the "dual" system, as I have seen implemented in other languages, notably Clojure and Julia and even Scheme. It should be very easy in Racket, I just haven't got that far yet.

---

<div class="post-metadata">

**Author:** ![SamPhillips](https://yyz2.discourse-cdn.com/free1/user_avatar/racket.discourse.group/samphillips/32/15_2.png) [@SamPhillips](https://racket.discourse.group/u/SamPhillips)\
**Post date:** [October 9, 2024, 3:24am UTC](https://racket.discourse.group/t/bug-in-number-function-after-require-malt/3192/11 "2024-10-09T03:24:48Z")

</div>

> [@AlexG](#):
>
> I am sure there is a simple way to add them as primitives (thus gaining efficiency) using the "dual" system, as I have seen implemented in other languages, notably Clojure and Julia and even Scheme. It should be very easy in Racket, I just haven't got that far yet.

The code for duals is duplicated for the different tensor implementation in the repo, but here is where the other operators are defined for `malt/learner`

[https://github.com/themetaschemer/malt/blob/main/learner/ext-ops/A-scalar-ops.rkt](https://github.com/themetaschemer/malt/blob/main/learner/ext-ops/A-scalar-ops.rkt)

---

<div class="post-metadata">

**Author:** ![AlexG](https://avatars.discourse-cdn.com/v4/letter/a/ecc23a/32.png) [@AlexG](https://racket.discourse.group/u/AlexG)\
**Post date:** [October 9, 2024, 12:53pm UTC](https://racket.discourse.group/t/bug-in-number-function-after-require-malt/3192/12 "2024-10-09T12:53:55Z")

</div>

Thanks for that! The Learner code looks really easy to extend, all the necessary functions `prim1`, `ext1`, etc, are available just with `(require malt)`, I tried it out, following the source code, but I only got to first base, there's probably something more I need to do.

(maybe the line `(* z (sin a))` should have used plain-old Racket multiplication? i.e. before it was commandeered by _malt_)

```scheme
(define sin-0
  (prim1 sin
    (λ (a z)
      (* z (cos a)))))

(define d-sin (ext1 sin-0 0))

> (d-sin 1)
0.8414709848078965
> (number? (d-sin 1))
#f
> (scalar? (d-sin 1))
#t
> (gradient-of d-sin 1.0)
. . +: contract violation
  expected: number?
  given: 0.8414709848078965
> 

```

Seems like the extension of d-sin is blocked by the failure of the multiplication.

I'll have a better look at the implementation later on, for now, I'm trying to understand ML, of which I know even less than I do about AD! 😛

---

<div class="post-metadata">

**Author:** ![AlexG](https://avatars.discourse-cdn.com/v4/letter/a/ecc23a/32.png) [@AlexG](https://racket.discourse.group/u/AlexG)\
**Post date:** [October 9, 2024, 2:11pm UTC](https://racket.discourse.group/t/bug-in-number-function-after-require-malt/3192/13 "2024-10-09T14:11:30Z")

</div>

Yup, got it all going fine now!

```scheme
(require malt)
(require (only-in racket/base
                  [* racket:*]
                  [- racket:-]
                  [sin racket:sin]
                  [cos racket:cos]                       
                  ))

(define sin-0
  (prim1 racket:sin
    (λ (a z)
      (racket:* z (racket:cos a)))))

(define cos-0
  (prim1 racket:cos
    (λ (a z)
      (racket:* z (racket:- (racket:sin a))))))

(define sin (ext1 sin-0 0))
(define cos (ext1 cos-0 0))
(define (tan x) (/ (sin x) (cos x)))

```

Try a few tests...

```scheme
> (sin 1)
0.8414709848078965
> (cos 1)
0.5403023058681398
> (sin (/ pi 4))
0.7071067811865476
> (cos (/ pi 4))
0.7071067811865476
> (tan 1)
1.557407724654902
> (tan 0)
0
> (number? (cos 1))
#f
> (number? (tan 1))
#f
> (scalar? (cos 1))
#t
> (scalar? (tan 1))
#t
> (tensor? (tan 1))
#t
> (gradient-of sin (/ pi 4))
0.7071067811865476
> (gradient-of cos (/ pi 4))
0.7071067811865475
> (gradient-of tan 0)
1.0
> (gradient-of tan 1)
3.425518820814759

```

All seems good.
