# Correctness? Factorial implementation returning unexpected result

**URL:** <https://discourse.julialang.org/t/correctness-factorial-implementation-returning-unexpected-result/85944>\
**Category:** New to Julia\
**Tags:** question\
**Created:** [August 18, 2022, 7:08pm UTC](https://discourse.julialang.org/t/correctness-factorial-implementation-returning-unexpected-result/85944 "2022-08-18T19:08:55Z")\
**Posts on this page:** 5\
**Page:** 1

<div class="post-metadata">

**Author:** ![hierophantos](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/hierophantos/32/38886_2.png) [@hierophantos](https://discourse.julialang.org/u/hierophantos)\
**Post date:** [August 18, 2022, 7:08pm UTC](https://discourse.julialang.org/t/correctness-factorial-implementation-returning-unexpected-result/85944/1 "2022-08-18T19:08:56Z")

</div>

Hi there! First day trying out Julia… so far, love it…

Implemented two versions of a simple factorial function, and ran into an unexpected result:

```julia
function fact(n)
    if n == 0
        return 1
    else
        n * fact(n - 1)
    end
end

function fact2(n)
    foldl(*, range(1, n))
end

```

checked `fact(5)` with a return of `120`… cool. That looks right. But then, when the input is around n=30 or so, I’m getting negative results, which is not what I’m expecting.

```julia
julia> fact(30)
-8764578968847253504

```

Both versions returning same erroneous values.

Expecting: `265252859812191058636308480000000`, based on other implementation and a simple calculator check.

That kind of scares me. Now that I write this, I’m realizing there’s probably a BigNum issue going on here, and … yeah, haven’t looked through the documentation on that yet… sorry… but I suppose I’m assuming that the return would simply default to the correct value, or at least return an error. What’s the correct way about going about this sort of thing, so that I don’t return something and think it’s correct when it’s not?

---

<div class="post-metadata">

**Author:** ![johnmyleswhite](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/johnmyleswhite/32/31_2.png) [@johnmyleswhite](https://discourse.julialang.org/u/johnmyleswhite)\
**Post date:** [August 18, 2022, 7:12pm UTC](https://discourse.julialang.org/t/correctness-factorial-implementation-returning-unexpected-result/85944/2 "2022-08-18T19:12:01Z")

</div>

[https://docs.julialang.org/en/v1/manual/faq/#faq-integer-arithmetic-1](https://docs.julialang.org/en/v1/manual/faq/#faq-integer-arithmetic-1)

> [@Tonight I hated julia, REPL and overflows](https://discourse.julialang.org/t/tonight-i-hated-julia-repl-and-overflows/34884/6):
>
> I have never seen an error message like that - all variables we create have concrete types. (You cannot redefine composite types without a REPL restart in the global scope, that’s true.) In most cases, you can call type names as constructors, in this case eg. BigInt(5). As jlapeyre mentioned, big(5) works here, too.

There are _a lot_ of threads on this topic if you search for machine integers, overflow and even factorial.

---

<div class="post-metadata">

**Author:** ![mikmoore](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/mikmoore/32/31109_2.png) [@mikmoore](https://discourse.julialang.org/u/mikmoore)\
**Post date:** [August 18, 2022, 7:46pm UTC](https://discourse.julialang.org/t/correctness-factorial-implementation-returning-unexpected-result/85944/3 "2022-08-18T19:46:38Z")

</div>

> [@hierophantos](#):
>
> ```julia
> julia> fact(30)
> -8764578968847253504
> 
> ```

See the above reply regarding machine arithmetic. Then try `fact(big(30))`.

---

<div class="post-metadata">

**Author:** ![nsajko](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/nsajko/32/221187_2.png) [@nsajko](https://discourse.julialang.org/u/nsajko)\
**Post date:** [August 18, 2022, 8:30pm UTC](https://discourse.julialang.org/t/correctness-factorial-implementation-returning-unexpected-result/85944/4 "2022-08-18T20:30:55Z")

</div>

> [@hierophantos](#):
>
> That kind of scares me. Now that I write this, I’m realizing there’s probably a BigNum issue going on here, and … yeah, haven’t looked through the documentation on that yet… sorry… but I suppose I’m assuming that the return would simply default to the correct value, or at least return an error. What’s the correct way about going about this sort of thing, so that I don’t return something and think it’s correct when it’s not?

Julia is basically doing what all other “big” languages except Python do here, so this shouldn’t be surprising.

As for what you should do, the simple answer is: use big integers.

---

<div class="post-metadata">

**Author:** ![digital\_carver](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/digital_carver/32/33818_2.png) [@digital\_carver](https://discourse.julialang.org/u/digital_carver)\
**Post date:** [August 18, 2022, 8:44pm UTC](https://discourse.julialang.org/t/correctness-factorial-implementation-returning-unexpected-result/85944/5 "2022-08-18T20:44:18Z")

</div>

> [@hierophantos](#):
>
> What’s the correct way about going about this sort of thing, so that I don’t return something and think it’s correct when it’s not?

These (and other options) are probably mentioned in the other threads @johnmyleswhite mentioned, but there’s modules like [SaferIntegers](https://github.com/JeffreySarnoff/SaferIntegers.jl), some inbuilt support in `Base.Checked`, etc.

In practice, since Julia is usually used where performance matters (and overflow checking is a performance killer), you might use these during development and local testing, but ultimately use normal overflowing types in production code with tests to make sure any edge cases are handled properly.
