Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/293.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/asp.net-mvc/14.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 如果在实体框架中使用延迟加载,如何序列化实体?_C#_Asp.net Mvc_Entity Framework_Serialization - Fatal编程技术网

C# 如果在实体框架中使用延迟加载,如何序列化实体?

C# 如果在实体框架中使用延迟加载,如何序列化实体?,c#,asp.net-mvc,entity-framework,serialization,C#,Asp.net Mvc,Entity Framework,Serialization,我刚刚开始学习实体框架,我面临着与生成模型的序列化相关的问题。我有一对多关系的表格,它们是国家和州,就像一个国家有许多州一样。我使用DB first方法,当我使用实体框架创建实体时,类Country有一个属性ICollection。我阅读并发现这是导航属性。让我首先显示生成的类,如下所示: //这是生成的类 public class Country { public Country() { States = new Has

我刚刚开始学习实体框架,我面临着与生成模型的序列化相关的问题。我有一对多关系的表格,它们是国家和州,就像一个国家有许多州一样。我使用DB first方法,当我使用实体框架创建实体时,类Country有一个属性ICollection。我阅读并发现这是导航属性。让我首先显示生成的类,如下所示:

//这是生成的类

 public class Country
    {
        public Country()
        {
                States = new HashSet<States>();
        }
        public int Id { get; set; }
        public string ContryCode  { get; set; } 
        public string ContryName  { get; set; }    
        public virtual ICollection<States> States{ get; set; }

    }
公共类国家
{
公共国家()
{
States=新的HashSet();
}
公共int Id{get;set;}
公共字符串控制码{get;set;}
公共字符串控件名{get;set;}
公共虚拟ICollection状态{get;set;}
}
我生成模型,然后向前一步。然后,当我通过ajax请求获取国家列表时,我遇到了序列化问题。我在谷歌上搜索了一些术语,如延迟加载、急切加载和n+1问题。我详细地读了它。我找到了一个解决方案,就是关闭延迟加载。现在的问题是如何用延迟加载序列化我的模型


我已经创建了元数据类并使用了一些属性,如ignoreXml等,但没有任何帮助。顺便说一下,我正在使用Asp.NETMVC5,我想用延迟加载序列化我的模型。有人能解释一下吗?

当您使用延迟加载时,执行会推迟到实际需要属性的值时。您可能遇到错误,因为在访问属性时上下文已被释放。考虑下面的场景:

  • 您有一个名为
    Country
    的对象,其中有一个名为
    States
    的延迟加载属性
  • 您可以从上下文中获取此对象
  • 上下文被释放
  • 您可以调用
    States
    属性
  • 属性将查找它来自的上下文
  • 抛出错误,因为“上下文已被释放”
代码示例:

using(var context = new SomeEntityContext())
{
     var country = context.Countries.First();
}

//This will throw an error because the context was disposed of.
var states = country.States; 
序列化程序还将抛出错误,因为它将遍历对象的属性,它将查找
状态
,并尝试获取其值

即使上下文仍处于活动状态,您也可能在序列化过程中遇到具有导航属性的循环。这是因为两个对象都相互引用。考虑下面的场景:

  • 您有一个名为
    Country
    的对象,其中有一个名为
    States
    的延迟加载属性
  • 序列化程序尝试序列化类型为
    Country
    的对象
  • 它读取
    状态
    集合
  • 它尝试序列化
    状态类型
    的每个对象
  • 它读取类型为
    Country
    的属性
  • 它尝试序列化类型为
    Country
    的对象
  • 它读取
    状态
    集合
  • 它尝试序列化
    状态类型
    的每个对象
  • 它读取类型为
    Country
    的属性
  • 它读取
    状态
    集合
  • 它尝试序列化
    状态类型
    的每个对象
  • 它读取类型为
    Country
    的属性
  • 它读取
    状态
    集合
  • 它尝试序列化
    状态类型
    的每个对象
  • 它读取类型为
    Country
    的属性
  • 。。。。(无休止的循环,至少在堆栈帧用完之前是这样)
或者,您可以创建一个自定义序列化程序,以避免导航属性的陷阱,但这可能需要做更多的工作。这种方法最适合序列化版本与对象显著不同的情况

这就是为什么最好使用数据传输对象(DTO)。将数据映射到此对象并通过导线发送。如果您尽可能保持结构的相似性,那么有一些组件可以为您进行映射


查看AutoMapper:

我可以理解在一些批处理或厚客户端应用程序中为什么需要延迟加载。但是对于延迟加载更可取的web应用程序,您有什么样的用例(除了不想考虑要包含什么之外)?@KyleBurns我没有任何用例。但我想知道我们是否在任何情况下使用延迟加载。那么我们如何序列化模型?你是否遇到了“上下文处理”错误?然后我遇到了问题什么问题?最有可能是循环引用,因为
状态
还包含对
国家的引用,在这种情况下,延迟加载与此无关。我的问题是“我们可以用延迟加载序列化”我们的模型吗?@Jaun感谢您的回答。我们能在没有DTO的情况下做同样的工作吗?@Umer:我扩展了我的答案来帮助你理解。