将ExpandoObject转换为匿名类型

时间:2012-10-04 14:03:38

标签: c#-4.0 asp.net-mvc-4 expandoobject

是否可以将ExpandoObject转换为匿名类型的对象?

目前我有HtmlHelper扩展名,可以将HTML属性作为参数。问题是我的扩展还需要添加一些HTML属性,所以我使用ExpandoObject来合并用户使用htmlAttributes参数传递给函数的属性和属性。现在我需要将合并的HTML属性传递给原始的HtmlHelper函数,当我发送ExpandoObject时,没有任何反应。所以我想我需要将ExpandoObject转换为匿名类型的对象或类似的东西 - 欢迎任何建议。

2 个答案:

答案 0 :(得分:4)

  

是否可以将ExpandoObject转换为匿名类型的对象?

只有在执行时自己生成匿名类型。

匿名类型通常由编译器在编译时创建,并像任何其他类型一样烘焙到程序集中。它们在任何意义上都不是动态的。因此,您必须使用CodeDOM或类似的东西来生成用于匿名类型的相同类型的代码...这不会很有趣。

我认为其他人更有可能创建了一些知道ExpandoObject的MVC助手类(或者只能使用IDictionary<string, object>)。

答案 1 :(得分:4)

我认为你不需要处理expandos来实现你的目标:

public static class HtmlExtensions
{
    public static IHtmlString MyHelper(this HtmlHelper htmlHelper, object htmlAttributes)
    {
        var builder = new TagBuilder("div");

        // define the custom attributes. Of course this dictionary
        // could be dynamically built at runtime instead of statically
        // initialized as in my example:
        builder.MergeAttribute("data-myattribute1", "value1");
        builder.MergeAttribute("data-myattribute2", "value2");

        // now merge them with the user attributes 
        // (pass "true" if you want to overwrite existing attributes):
        builder.MergeAttributes(new RouteValueDictionary(htmlAttributes), false);

        builder.SetInnerText("hello world");

        return new HtmlString(builder.ToString());
    }
}

如果你想调用一些现有的帮助器,那么一个简单的foreach循环可以完成这项工作:

public static class HtmlExtensions
{
    public static IHtmlString MyHelper(this HtmlHelper htmlHelper, object htmlAttributes)
    {
        // define the custom attributes. Of course this dictionary
        // could be dynamically built at runtime instead of statically
        // initialized as in my example:
        var myAttributes = new Dictionary<string, object>
        {
            { "data-myattribute1", "value1" },
            { "data-myattribute2", "value2" }
        };

        var attributes = new RouteValueDictionary(htmlAttributes);
        // now merge them with the user attributes
        foreach (var item in attributes)
        {
            // remove this test if you want to overwrite existing keys
            if (!myAttributes.ContainsKey(item.Key))
            {
                myAttributes[item.Key] = item.Value;
            }
        }
        return htmlHelper.ActionLink("click me", "someaction", null, myAttributes);
    }
}