Entity Framework 6 Recipes 2nd Edition(13-10)译 -> 显式创建代理

问题

你有一个POCO实体,原本在执行一个查询时动态创建代理,现在你不想EF延迟创建代理带来的代价.

 

解决方案

假设你有一个如图Figure13-15的模型

 

Figure 13-15. A model for CDs and music titles

 

         对应的POCO类如代码Listing 13-27.注:每个属性用virtual关键字和每个引用属性为Icoolection类,EF会动态为实体创建跟踪代理(更多信息,请查看Recipe 13-5 ).

Listing 13-27. The POCO Classes Along with Our Object Context

    public partial class CD

    {

        public CD()

        {

            this.Tracks = new HashSet<Track>();

        }

        public int CDId { get; set; }

        public string Title { get; set; }

        public virtual ICollection<Track> Tracks { get; set; }

    }

    public partial class Track

    {

        public string Title { get; set; }

        public string Artist { get; set; }

        public int CDId { get; set; }

}

为了让EF在有需要前(一个实体被装载前)创建代理,我们需要使用ObjectContext的CreateProxyTypes()方法,如代码Listing 13-28.

Listing 13-28. Generating the tracking proxies before loading the entities

            using (var context = new EFRecipesEntities())

            {

                // 为了触发代理创建,我们需要深入到底层的ObjectContext,因为DbContext没有暴露CreateProxyTypes() 方法

                var objectContext = ((IObjectContextAdapter)context).ObjectContext;

                objectContext.CreateProxyTypes(new Type[] { typeof(CD), typeof(Track) });

                var proxyTypes = ObjectContext.GetKnownProxyTypes();

                Console.WriteLine("{0} proxies generated!", ObjectContext.GetKnownProxyTypes().Count());

                var cds = context.CDs.Include("Tracks");

                foreach (var cd in cds)

                {

                    Console.WriteLine("Album: {0}", cd.Title);

                    foreach (var track in cd.Tracks)

                    {

                        Console.WriteLine("\t{0} by {1}", track.Title, track.Artist);

                    }

                }

            }

输出结果如下:

2 proxies generated!

Album: Abbey Road

Come Together by The Beatles

Album: Cowboy Town

Cowgirls Don't Cry by Brooks & Dunn

Album: Long Black Train

In My Dreams by Josh Turner

Jacksonville by Josh Turner

 

它是如何工作的

动态代理仅在它们被需要的时候创建,这就是说负载发生在第一个查询时,这种延迟创建方式在多数情况下工作得很好.然而你可以在实体第一个被装载前创建代理,通过调用CreateProxyTypes()方法.

         CreateProxyTypes()方法以类型数组(实体类型)做为参数,它会创建相对应的实体代理,一旦创建,代理的生命周期与应用程序域的生命周期相同,注意它是被绑定到应用程序域,而不是上下文对象,我们可以释放上下文对象,然后重新创建一个上下文对象,但代理不会被释放,你可以从应用程序域中用上下文对象的静态方法GetKnowProxyTypes()重新获取.

 

我注:性能篇完结

posted @ 2016-05-17 00:26  kid1412  阅读(614)  评论(0编辑  收藏  举报