【问题标题】:Type.GetType(string) using "Generic<T>" syntax?Type.GetType(string) 使用“Generic<T>”语法?
【发布时间】:2009-05-24 02:53:50
【问题描述】:

我正在构建一个通用 ASP.NET 服务器控件,该控件具有用于指定类型名称的属性。我正在使用控件生成器通过将属性值传递给Type.GetType(string) 来生成我的控件的通用版本。这很好用。但是,如果我要指定的类型是通用的,我必须使用这样的语法:

<gwb:GenericControl runat="server" 
    TypeName="System.Collections.Generic.List`1[System.String]" />

我希望能够这样输入:

<gwb:GenericControl runat="server"
    TypeName="System.Collections.Generic.List<System.String>" />

我知道我可以手动解析尖括号的值并将它们转换为方括号,并添加适当的反引号数字前缀,但是 我想知道是否有任何内置方法可以进行这种转换? 我假设Generic&lt;T&gt; 语法特定于 C#(或至少在 VB.NET 中不同),所以我猜我还必须解析任何其他特定于语言的语法。

我注意到 ASP.NET MVC 在 Page 指令的 Inherits 属性中执行此操作,但我不确定如何。

<%@ Page Title="" Language="C#" MasterPageFile="~/Views/Shared/Site.Master"
    Inherits="System.Web.Mvc.ViewPage<MyModel>" %>

【问题讨论】:

    标签: c# asp.net generics reflection


    【解决方案1】:

    不,没有内置的方法可以做到这一点。原因是像 Generic&lt;T&gt; 这样的类型名称确实特定于 C#。它们实际上在元数据中以不同的方式写出。

    简短的版本是类型名称,后跟一个`,然后是一个与泛型参数计数相对应的数字。例如,Generic&lt;T&gt; 将被写为 Generic`1,Generic&lt;T1,T2&gt; 将被写为 Generic`2。数组给语法增加了一些复杂性,但这是一般规则。

    当您使用 Type.GetType 时,您实际上是在执行元数据查询与 C# 查询。因此必须提供类型名称,因为它出现在 MetaData 中。

    【讨论】:

      【解决方案2】:

      没有内置的方法可以做到这一点。你需要把它解析出来。这大概就是MVC框架内部在做的事情吧。

      【讨论】:

        【解决方案3】:

        您实际上无法使用该特定语法。由于 xml 的性质,您的实际语法必须如下:

        <gwb:GenericControl runat="server"
            TypeName="System.Collections.Generic.List&lt;System.String>" />
        

        如果对应的 > 存在,则不能在属性值中使用

        第一种形式是标准的 IL 形式(即 Namespace.GenericClass`1[[System.String]]),对于任何精通 .NET 语言的用户都应该有些熟悉,并且是通用的,而第二种仅有效对于 C#。

        【讨论】:

        • 难道 ASP.NET MVC 框架也违反了这条规则,还是 Page 指令不被视为 XML 文档的一部分?
        • Page 指令不是 XML 文档的一部分。包装它的 有点把它放在内联代码的类别中,就像强制性的 之间的东西,这一切都由 ASPX 编译器处理。在通过 xml 验证器发送页面之前,所有这些都已被处理并被剥离或变成更多标记。
        猜你喜欢
        • 2011-03-08
        • 1970-01-01
        • 2011-11-18
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2011-01-01
        • 2018-09-02
        • 2012-09-23
        相关资源
        最近更新 更多