【发布时间】:2011-11-15 15:58:10
【问题描述】:
如何使用反射在 F# 中创建记录类型?谢谢
【问题讨论】:
-
你为什么要这样做?为什么需要专门的记录?
-
@Giuseppe:我用一个如何做到这一点的例子更新了我的答案。
标签: .net reflection f#
如何使用反射在 F# 中创建记录类型?谢谢
【问题讨论】:
标签: .net reflection f#
您可以使用FSharpValue.MakeRecord[MSDN] 创建记录实例,但我认为 F# 中没有任何内容可用于定义记录类型。但是,记录会编译为简单的类,因此您可以像在 C# 中那样构建一个类。 TypeBuilder[MSDN] 可能是一个很好的起点。
将[<CompilationMapping(SourceConstructFlags.RecordType)>] 添加到类型是使其成为记录所需的全部内容。这是一个如何在运行时执行此操作的示例。
let asmName = AssemblyName("Foo")
let asm = AppDomain.CurrentDomain.DefineDynamicAssembly(asmName, AssemblyBuilderAccess.RunAndCollect)
let moduleBldr = asm.DefineDynamicModule("Test")
let typeBldr = moduleBldr.DefineType("MyRecord", TypeAttributes.Public)
let attrBldr = CustomAttributeBuilder(
typeof<CompilationMappingAttribute>.GetConstructor([|typeof<SourceConstructFlags>|]),
[|box SourceConstructFlags.RecordType|])
typeBldr.SetCustomAttribute(attrBldr)
let typ = typeBldr.CreateType()
printfn "%b" <| FSharpType.IsRecord(typ) //true
【讨论】:
FSharpType.MakeRecordType,因为有MakeTupleType 和MakeFunctionType 方法吗?
Tuple 和 FSharpFunc)的某种组合的 System.Type,但生成记录实际上涉及发射使用反射的类型(更复杂并且有更多选项,例如将类型放入哪个程序集中......)