Can a BigInt be a type parameter?

I am able to define a type struct foo{N} where N is an Int, but can I do this with N being a BigInt?

Yes, it should be possible with any type.

Or did you encounter an issue with it?

Yes. I’m still struggling. Is there a good example on the web?

struct MyType{T}
x:: T
end

MyType(big(42))

Here’s where I’m having a problem:

struct Mod{N}
    val
    function Mod(x::T, N::S) where {S<:Integer, T<:Integer}
        new{N}(mod(x,N))
    end
end

julia> Mod(10,20)
Mod{20}(10)

julia> Mod(10,big(20))
ERROR: TypeError: in Type, in parameter, expected Int64, got BigInt
Stacktrace:
 [1] Mod(::Int64, ::BigInt) at ./REPL[1]:8
 [2] top-level scope at REPL[14]:1

I don’t think this is true. The manual says:

Both abstract and concrete types can be parameterized by other types. They can also be parameterized by symbols, by values of any type for which isbits returns true (essentially, things like numbers and bools that are stored like C types or struct s with no pointers to other objects), and also by tuples thereof. Type parameters may be omitted when they do not need to be referenced or restricted.

7 Likes

Alas:

julia> isbits(big(100))

false
1 Like
struct Mod{N}
    val:: N
    function Mod(x::T, N::S) where {S<:Integer, T<:Integer}
        new{S}(mod(x,N))
    end
end

Mod(10,big(20))

You need to give the type parameter S as type to new.
In addition, you shoud define the type of val to be N, otherwise it would be of type Any.

1 Like

I’m pretty sure this is a solution to the wrong problem. Unless I’m mistaken, @scheinerman is trying to make the value big(20) a type parameter, not the type BigInt. That’s not possible for the reasons posted above.

7 Likes

Thanks for the clarification and sorry for the misunderstanding on my side!

BigInt is technically mutable (because that’s how GMP works), so it can’t be used as a type parameter, which must be immutable. However, if you just need something slightly larger than 64 bits, you could look into https://github.com/rfourquet/BitIntegers.jl.

1 Like

Technically, the problem is not that the type is mutable or immutable but that if it isbits or not. An immutable type can return a false value for isbits and therefore not be eligible to be a value parameter.

Yes, but the semantic problem is mostly mutability (or pointers to mutable things). The isbits is a bit of an implementation detail that I would like to change: https://github.com/JuliaLang/julia/issues/33387

2 Likes

Very interesting. I did not consider the Union case, in fact. I was just pointing that an immutable struct can have, in fact, fields of types that are not isbits, so by consequence it becomes not isbits even being immutable itself. Unless you are using a recursive definition of immutability, of course.