铸造匿名类型 [英] Cast to Anonymous Type

查看:104
本文介绍了铸造匿名类型的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

今天我有以下问题,我想知道是否有我的问题的解决方案。

I had the following problem today, and I was wondering if there is a solution for my problem.

我的想法是建立匿名类,并把它作为一个WinForm BindingSource的数据源:

My idea was to build anonymous classes and use it as a datasource for a WinForm BindingSource:

    public void Init()
    {
        var option1 = new
                      {
                          Id = TemplateAction.Update,
                          Option = "Update the Templates",
                          Description = "Bla bla 1."
                      };

        var option2 = new
                      {
                          Id = TemplateAction.Download,
                          Option = "Download the Templates",
                          Description = "Bla bla 2."
                        };

        var list = new[] {option1, option2}.ToList();

        bsOptions.DataSource = list; // my BindingSource

        // cboTemplates is a ComboBox
        cboTemplates.DataSource = bsOptions; 
        cboTemplates.ValueMember = "Id";
        cboTemplates.DisplayMember = "Option";

        lblInfoTemplates.DataBindings.Add("Text", bsOptions, "Description");
    }

这工作正常为止。

我的问题是获得标识出的BindingSource的当前的属性,因为我不能将它转换回匿名类型:

The problem I had is to get Id out of the "Current" property of the BindingSource, because I can't cast it back to the Anonymous Type:

    private void cmdOK_Click(object sender, EventArgs e)
    {
        var option = (???)bsOptions.Current;
    }

时的猜测是没有办法找出的当前的类型和访问ID属性?
也许有人有一个很好的解决方案...

Is guess there is no way to find out the type of "Current" and access the "Id" Property? Maybe someone has a good solution...

我知道还有其他的(也更好)的方法来获得ID(反思,从组合框读取值,而不是使用匿名tpyes,...)我只是courious是否有可能得到打出来在一个优雅的方式bsOptions.Current。

I know there are other (and also better) ways to get the Id (Reflection, reading the value from the ComboBox, not using anonymous tpyes,...) I'm just courious if it's possible to get the Type out of bsOptions.Current in an elegant way.

推荐答案

注意,按照评论,我只是想指出的是,我也推荐使用真正的类型,当你需要它传递这样的程序周围。匿名类型应该只有真正在当地的一个方法同时使用(在我看来),但无论如何,这是我回答的其余部分。

Note, as per the comment, I'd just like to point out that I too recommend using a real type when you need to pass it around the program like this. Anonymous types should only really be used locally in a single method at a time (in my opinion), but anyway, here's the rest of my answer.


您可以使用它一招,办通过欺骗编译成推断正确的类型为您提供:

You can do it using a trick, by tricking the compiler into inferring the right type for you:

using System;

namespace ConsoleApplication4
{
    class Program
    {
        static void Main(string[] args)
        {
            var a = new { Id = 1, Name = "Bob" };
            TestMethod(a);

            Console.Out.WriteLine("Press enter to exit...");
            Console.In.ReadLine();
        }

        private static void TestMethod(Object x)
        {
            // This is a dummy value, just to get 'a' to be of the right type
            var a = new { Id = 0, Name = "" };
            a = Cast(a, x);
            Console.Out.WriteLine(a.Id + ": " + a.Name);
        }

        private static T Cast<T>(T typeHolder, Object x)
        {
            // typeHolder above is just for compiler magic
            // to infer the type to cast x to
            return (T)x;
        }
    }
}

诀窍是,在组件内,同一匿名类型(相同的属性,相同的顺序)解析为同一类型,这使得上述工作的伎俩。

The trick is that inside the assembly, the same anonymous type (same properties, same order) resolves to the same type, which makes the trick above work.

private static T CastTo<T>(this Object value, T targetType)
{
    // targetType above is just for compiler magic
    // to infer the type to cast x to
    return (T)x;
}

用法:

var value = x.CastTo(a);

但我们真的超越极限在这里。使用真正的类型,它会看起来和感觉更清洁为好。

But we're really pushing the limits here. Use a real type, it'll look and feel cleaner as well.

这篇关于铸造匿名类型的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆