'Unboxed typed int in OCaml
I would like to represent two types of integers in my OCaml program and have the compiler emit an error when one type is used in place of the other. My program converts between the two integer types, and a large fraction of the run time is spent operating on such values. If possible, I would like arithmetic operations to run on unboxed values. I implemented a module that defines such a type, and that implements the +, -, /, * operators. But my understanding is that the operations run on boxed values. Is there a way of getting the same behavior with unboxed values?
module SkipInts = struct
type t = Int of int | SkipInt of int
end
Solution 1:[1]
You could use private type abbreviations to create a distinct type for SkipInt represented as an int:
module SkipInt : sig
type t = private int
val of_int : int -> t
val to_int : t -> int
end = struct
type t = int
let of_int x = x
let to_int x = x
end
let _: SkipInt.t = SkipInt.of_int 42
let _: int = (SkipInt.of_int 42 :> int) (* :> can be used instead of SkipInt.to_int *)
let _: SkipInt.t = (42 :> SkipInt.t) (* Error: Type int is not a subtype of SkipInt.t *)
Solution 2:[2]
It sounds like you might want something like
module Make_int(): sig
type t [@@immediate]
val of_int: int -> t
val to_int: t -> int
type op := t -> t -> int
val ( + ): op
val ( * ) : op
val ( - ): op
val ( / ): op
val ( ~- ): t -> t
end = struct
type t = int
let to_int x = x
let of_int x = x
let ( + ) = ( + ) let ( - ) = ( - ) let ( * ) = ( * ) let ( / ) = ( / )
let ( ~- ) = ( ~- )
end
then any call to Make_int will create a new unboxed int type incompatible with any other type
module Int_1 = Make_int()
module Int_2 = Make_int ()
let fine = Int_1.( of_int 0 + of_int 2 )
let error = Int_1.( of_int 0 + 2 )
let also_error = Int_1.(of_int 0 + Int_2.of_int 1)
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 | glennsl |
| Solution 2 | octachron |
