【问题标题】:Get Sums of All Instances of an Id From Two Tables从两个表中获取一个 id 的所有实例的总和
【发布时间】:2018-08-28 18:46:38
【问题描述】:

我想显示 QualificationBatch 中所有 CompendiumId 实例的 Sum.Slots 以及 SAP 中所有 CompendiumId 实例的 Sum.Slots,并将其显示在如下表格中:

纲要 |Sum.Seats |Sum.Slots

Id1 |Seats1 |Slots1

Id2 |Seats2 |Slots2

经过大量阅读,我认为使用 GroupBy 可以做到这一点,但我无法让它工作,因为我对所有东西都很陌生,即使是操作 List 或 IEnumerable 等基础知识。这是我目前所拥有的:

模型

public class Compendium
{
    public int Id { get; set; }
    public string Name { get; set; }

    public virtual ICollection<QualificationBatch> QualificationBatches { get; set; }        
    public virtual ICollection<SAP> SAPs { get; set; }
}


public class QualificationBatch
{
    public int Id { get; set; }
    public int CompendiumId { get; set; }
    public int Slots { get; set; }

    public virtual Compendium Compendium { get; set; }
}

public class SAP
{
    public int Id { get; set; }
    public int CompendiumId { get; set; }
    public int Seats { get; set; }

    public virtual Compendium Compendium { get; set; }
}

视图模型

public class SAPSummaryViewModel
    {        
        public int Id { get; set; } //Compendium
        public int Slots { get; set; } //QualificationBatch
        public int Seats { get; set; } //SAP
    }

控制器

public ActionResult Index()
        {
            List<SAPSummaryViewModel> SAPSummaryViewModelList = new List<SAPSummaryViewModel>();
            var sapsummarylist = (from SP in db.SAPs
                                  join Comp in db.Compendia on SP.CompendiumId equals Comp.Id                                  
                                  select new {Comp.Id, SP.Seats });
            sapsummarylist.GroupBy(i => i.Id).Select(group =>
                                              new
                                              {
                                                  Id = group.Key,
                                                  Sum = group.Sum(item => item.Seats)
                                              });          
            foreach (var item in sapsummarylist)
            {                
                SAPSummaryViewModel objcvm = new SAPSummaryViewModel();              
                objcvm.Id = item.Id;
                objcvm.Seats = item.Seats;                
                SAPSummaryViewModelList.Add(objcvm);
            }
            return View(SAPSummaryViewModelList);
        }

我对其他方法持开放态度,我只是将我的控制器的代码放在上面以显示我一直在尝试的内容。在这里,我试图让它首先为一张桌子工作,但我已经卡在这里了,因为它不起作用。

【问题讨论】:

    标签: asp.net-mvc linq group-by ienumerable


    【解决方案1】:

    所以每个 QualificationBatch 都有 CompendiumId 属性和 int 属性 Slots。

    每个 SAP 也有一个属性 CompendiumId。它还有一个 int 属性 Seats。

    现在显然您有 QualificationBatches 和 SAP 的序列,并且您希望每个 compendiumId 的 Slots 和 Seats 的值

    小步走:

    IQueryable<QualificationBatch> qualificationBatches = db.QualificationBatches;
    IQueryable<SAP> saps = db.Saps;
    
    var result = qualificationBatches    // join qualificationbatches
        .Join(saps,                      // with saps
        qualificationBatch => qualificationBatch.CompendiumId,
                                         // from every q-batch take the CompendiumId,
        sap => sap.CompendiumId,         // from every sap take the CompendiumId,
        (qualificationBatch, sap)  => new SapSummaryViewModel()
        {                                // when they match make a new SapSummaryViewModel
             Id = qualificationBatch.Id,
             Slots =  qualificationBatch.Slots,
             Seats = qualificationBatch.Seats,
         });
    

    TODO:做一个声明

    请注意,这是一个内部联接:如果您的 SAP 的 CompendiumId 未被任何 QualificationBatch 使用,您将不会在最终结果中得到它。如果您还希望在最终结果中包含这些项目,您将需要一个左外连接或一个完全外连接,具体取决于您想要什么。 LINQ 不支持它们,但您可以通过为其编写方法来扩展 LINQ。见Stackoverflow LINQ full outer join

    【讨论】:

    • 感谢您非常有见地的回复。这正是我现在的问题,因为我没有得到带有 sp.Seats 但没有 sp.Slots 的 CompendiumId 实例的行,我不知道这是否合适,但我已经在这里提出了一个新问题,专门描述了我的结果:@ 987654322@
    【解决方案2】:

    以下代码将对您有所帮助,

    var sapsummarylist = ( from cmp in Compendium
                           join sp in SAP on cmp.Id equals sp.CompendiumId
                           join qb in QualificationBatch on  on cmp.Id equals qb.CompendiumId
                           group  new { cmp.Id , sp.Seats, qb.Slots } by new { cmp.Id } into mgrp           
                           from grp in mgrp.DefaultIfEmpty() 
                           select new SAPSummaryViewModel { 
                                    Id = grp.Id,
                                    Seats = mgrp.Sum(x=>x.Seats),
                                    Slots = mgrp.Sum(x=>x.Slots)                                    
                            });  
    

    【讨论】:

    • 我在显示 dbquery 时也遇到了问题,如果我有这样的视图,我该如何实现呢? @model IEnumerable
    • 我还不知道结果,因为我不知道如何将此查询转换为我的视图的 IEnumarable
    • 尝试使用return View(sapsummarylist);
    • 您更新的答案让我的观点生效。好吧,起初我尝试不使用任何带有插槽的代码,所以只是座位的总和,它返回了正确的总和,但重复了与实例一样多的总和。当我包括插槽时,座位的总和增加了一倍,插槽的值不正确,我仍在试图弄清楚如果我这边有错误,它是如何到达这些值的
    • 没有机会将座位加倍,因为您包括插槽。无论如何检查您的条目。如果它对您有用,请接受它作为您的答案。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2010-11-26
    • 2014-11-27
    • 2020-10-09
    • 2019-01-17
    • 1970-01-01
    • 2021-11-19
    相关资源
    最近更新 更多