How to write function where argument is type but not typed value?
我想将几十个枚举类型的字符串表示形式转换为枚举值。
将字符串转换为具体类型很容易:
1 | Enum.Parse(typeof<FontStyle>,"Bold") |> unbox<FontStyle> |
但现在我想编写类型和字符串作为参数的函数。
我能写的最好的是:
1 2 3 4 | > let s2e (_: 'a) s = Enum.Parse(typeof<'a>,s) |> unbox<'a>;; val s2e : 'a -> string -> 'a > s2e FontStyle.Regular"Bold";; val it : FontStyle = Bold |
有没有什么办法可以写出这样的东西,但将类型本身作为第一个参数?
该函数需要接受一个类型参数,这将是返回的枚举的类型。但是,您不需要使用代码中任何地方都没有使用的"假"参数来指定类型 - 您可以在调用函数时使用与调用
以下修改后的函数采用仅出现在返回类型中的单个类型参数(为避免混淆 SO 代码格式化程序,我将代码中的 ' 替换为 '):
1 2 | > let parseEnum<′a> s = Enum.Parse(typeof<′a>,s) |> unbox<′a>;; val parseEnum : string -> ′a |
调用函数时,需要明确指定类型:
1 2 | > parseEnum<FontStyle>"Bold";; val it : FontStyle = Bold |
您的解决方案非常接近这一点 - 唯一的变化是您可以显式指定类型参数,而不是提供见证值来指导类型推断。
托马斯的回答很好。此外,请注意,您可以应用 F# 的
1 2 | let parseEnum<'t,'u when 't:enum<'u>> s = System.Enum.Parse(typeof<'t>, s) :?> 't (parseEnum"Class" : System.AttributeTargets) |
现在调用
编辑
因为我们实际上并没有对底层类型
1 2 | let parseEnum<'t when 't :> System.Enum and 't : struct> s = System.Enum.Parse(typeof<'t>, s) :?> 't |
请注意,