asp.net-mvc - 由 linq 查询引起的 StackOverflowException

标签 asp.net-mvc linq stack-overflow

编辑#2:问题中途解决。往下看

作为后续问题,有没有人知道一种非侵入式的方法来解决我在下面尝试做的事情(即,将对象相互链接而不触发无限循环)?


我尝试创建一个 asp.net-mvc web 应用程序,并得到一个 StackOverFlowException。 Controller 触发以下命令:

    public ActionResult ShowCountry(int id)
    {
        Country country = _gameService.GetCountry(id);
        return View(country);
    }

GameService 是这样处理的(WithCountryId 是一个扩展):

    public Country GetCountry(int id)
    {
        return _gameRepository.GetCountries().WithCountryId(id).SingleOrDefault();
    }

GameRepository 是这样处理的:

    public IQueryable<Country> GetCountries()
    {
        var countries =  from c in _db.Countries
               select new Country
               {
                   Id = c.Id,
                   Name = c.Name,
                   ShortDescription = c.ShortDescription,
                   FlagImage = c.FlagImage,
                   Game = GetGames().Where(g => g.Id == c.GameId).SingleOrDefault(),
                   SubRegion = GetSubRegions().Where(sr => sr.Id == c.SubRegionId).SingleOrDefault(),
               };
        return countries;
    }

GetGames() 方法导致 StackOverflowException:

    public IQueryable<Game> GetGames()
    {
        var games = from g in _db.Games                   
               select new Game
               {
                   Id = g.Id,
                   Name = g.Name

               };
        return games;

    }

我的业务对象与 linq2sql 类不同,这就是为什么我用一个新的选择来填充它们。

在 mscorlib.dll 中出现类型为“System.StackOverflowException”的未处理异常


编辑#1:我找到了罪魁祸首,它是以下方法,它触发了 GetCountries() 方法,该方法反过来再次触发 GetSubRegions(),令人作呕:

    public IQueryable<SubRegion> GetSubRegions()
    {
        return from sr in _db.SubRegions
               select new SubRegion
               {
                   Id = sr.Id,
                   Name = sr.Name,
                   ShortDescription = sr.ShortDescription,
                   Game = GetGames().Where(g => g.Id == sr.GameId).SingleOrDefault(),
                   Region = GetRegions().Where(r => r.Id == sr.RegionId).SingleOrDefault(),
                   Countries = new LazyList<Country>(GetCountries().Where(c => c.SubRegion.Id == sr.Id))
               };
    }

可能不得不在这里考虑其他事情:)这就是当你因为喝太多咖啡而以 OO 思维方式思考时会发生的事情

最佳答案

嗨!我认为您的模型无意中递归调用了一个方法,这会导致堆栈溢出。例如,您的 Subregion 对象正在尝试获取 Country 对象,而 Country 对象又必须获取 Subregions。

无论如何,在 StackOverflow 异常中检查堆栈总是有帮助的。如果您看到一个属性被一遍又一遍地访问,很可能是因为您正在做这样的事情:

公共(public)对象 MyProperty { 设置 { MyProperty = 值; }}

更容易发现像您这样的情况,其中方法 A 调用方法 B,方法 B 调用方法 A,因为您可以看到相同的方法在调用堆栈中出现两次或更多次。

关于asp.net-mvc - 由 linq 查询引起的 StackOverflowException,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/238490/

相关文章:

linq to sql ExecuteQuery() as IQueryable

c# - foreach + break vs linq FirstOrDefault 性能差异

c++ - g++4.8 的堆栈内容

java - 我应该写什么以避免 stackoverflow 错误?

asp.net - 从 MVC .Net 中的另一个 View 调用 View

sql-server - 在 ASP.NET MVC 中将 SQL Server 连接到 Azure 数据库

asp.net-mvc - MVC 本地化的 ResourceManager 问题

linq - 使用 Linq 对 Person 对象列表进行排序

c++ - 未处理的异常堆栈溢出 win32 控制台应用程序

javascript - 如何从 asp.net mvc 项目中的脚本正确引用图像文件?