繁体   English   中英

Type.GetType()在C#代码中不适用于F#类型

[英]Type.GetType() not working for F# type in C# code

我有一个名为Assembly1的F#程序集

我有以下模块:

namespace Assembly1

module MyModule =
   type MyClass(x: int, y: int) =
   new() = MyClass(0, 0)

在引用此F#程序集的C#程序集中,以下代码为我提供了一个'null'值:

var myType = Type.GetType("Assembly1.MyModule.MyClass, Assembly1");

我想做的不可能吗?

要添加Mark的答案 ,还值得注意的是,F#中的许多模块由IL(因此非F#语言)中的不同名称表示,而不是F#本身中显示的。

例如,这段代码:

open System
open System.Reflection
open Microsoft.FSharp.Reflection

let private core =
    AppDomain.CurrentDomain.GetAssemblies()
    |> Seq.find (fun a -> a.GetName().Name = "FSharp.Core")

let private seqMod =
    core.GetTypes()
    |> Seq.filter FSharpType.IsModule
    |> Seq.find (fun t -> 
                   t.FullName = "Microsoft.FSharp.Collections.SeqModule")

将在FSharp.Core中找到Seq模块。

FSharp.Reflection命名空间有一堆辅助方法,可以使用System.Reflection来处理F#特定类型,但是在FSI中加载几个程序集并且如果你要去的话那么可以玩它们。使用F#代码进行大量的反射工作。

您可以使用CompiledName属性自己创建具有“不匹配”名称的模块 - 这对于您希望类型和模块具有相同名称的时间尤其有用。 常规约定(如Seq类型/模块所示)是使用Compiled name注释模块。

[<CompiledName("MyTypeModule")>]
module MyType =
    let getString m =
        match m with
        | MyType s -> s

由于您已将MyClass放入模块中,因此将其编译为嵌套类。 它的名字是Assembly1.MyModule+MyClass

从C#开始,您应该可以像这样加载它:

var myType = Type.GetType("Assembly1.MyModule+MyClass, Assembly1");

如果您不想拥有嵌套类(在C#中通常不赞成),您可以直接在命名空间中定义它:

namespace Assembly1.LibraryXyz

type MyClass(x: int, y: int) = class end

该类的名称为Assembly1.LibraryXyz.MyClass

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM