I’m pulling from Haskell to look into this question, but allow me to expose the zig example first.
I’d like to instantiate a type like the following:
const GenericType = struct {
aType: type,
aFun: (fn (v: aType) aType),
};
I shall explain it as well to hedge against my current lack of zig knowledge. In short, I want to make a type that contains a type aType
and a function that maps that type into itself like a unary operator aFun :: aType -> aType
in Haskell lingo. Naturally, I’m aware that those types should be compile-time determined, but am unaware of how to inform the compiler that aType
should be unified within the struct.
What I’m trying to do is functionally equivalent to the following Haskell code:
data GenericType a = GenericType
{aFun :: a -> a}
genInstance :: GenericType Int
genInstance = GenericType (int -> int + 1)
Maybe this is repetitive, but I’m wondering if it’s possible to reference that type (in the haskell example, simply named a
) in zig similar to how it’s done in Haskell, directly on the type structure. What I mean by that is I know it is possible to accomplish the same goal with a zig function by either only receiving a function type
fn functionParam(comptime aType: type, arg: aType, func: (fn (aType) aType)) aType {
// this compiles just fine and this scope contains
// aType and func with types unified, i.e., they are
// to be the same
func(arg);
}
or even returning a struct from the function to have the type available later
// line breaks on function's args and return types to improve readability
fn GenericType (comptime aType: type, func: (fn (aType) aType)) // args types
(struct { aType: type,
aFun: (fn (aType) aType) }) // return type
{
return .{
.aType = aType,
.aFun = func,
};
}
but even here the types aren’t actually unified: in the above, I’d like to enforce that aType
from the returning struct is the same aType
from the first parameter