Marko Grdinić
Marko Grdinić

Reputation: 4062

How to go from a discriminated union representation of a type to a System type for arrays?

In F#, if I want to create a System.Type of say, an array of strings, I could just write typeof<string[]> and be done with it. That is because I can specify the type in the typeof at compile time.

type Ty =
| Int32
| Float32
| String
| Array of Ty

let to_dotnet_type: Ty -> System.Type = ...

But suppose I had an union type so that the exact System.Type I am looking for is unknown at compile time, how would I go from Ty to the .NET System.Type? Arrays in particular do not even have any generic parameters so I am guessing that F# is instantiating new array types that inherit from the base System.Array on demand. I am drawing a blank on how to do it dynamically.

The reason why being able to move between my internal representation and the CLR types would be beneficial is because I am making a language that compiles to F# (in F#) and am using reflection functions such as GetMethod which take arrays of System.Types as an argument. I am using them to do interop for lack of knowledge of any better ways of doing it.

Upvotes: 1

Views: 57

Answers (1)

Lee
Lee

Reputation: 144206

You can use Type.MakeArrayType to construct array types:

let rec to_dotnet_type: Ty -> System.Type = function
| Int32 -> typeof<Int32>
| Float32 -> typeof<Single>
| String -> typeof<String>
| Array(elemTy) -> let et = to_dotnet_type(elemTy) in et.MakeArrayType()

Upvotes: 2

Related Questions