Bruno Rigoni
Bruno Rigoni

Reputation: 45

How to group in LINQ

Goodmorning I need help for make a LINQ query on this object

    public class Equipment
    { 
            public string Id { get; set; }
            public string Description{ get; set; }
            public string Productor{ get; set; }
            public List<Movement> Movements{ get; set; }
            public double DailyNeeding { get; set; }
    }

The class Movement is this

public class Movement
{
    public double Quantity{ get; set; }
    public DateTime MovementDate { get; set; }
    public string Note { get; set; }
    public DateTime Expiry { get; set; }
    public string Destination { get; set; }
}

I need to retrieve some data according this model

public class EquipmentModels
    {
        public string Id { get; set; }
        public string Description{ get; set; }
        public string Productor { get; set; }
        public double Amount { get; set; }
        public DateTime ExhaustionDate { get; set; }
        public string Place { get; set; }
    }

For the moment I have done so

    List<Equipment> mat = //code for retrieve list

    List<EquipmentModels> matList = new List<EquipmentModels>();
    foreach(Equipment m in mat)
    {
         EquipmentModels lm = new EquipmentModels();

         foreach(Movement mov in m.Movements)
         {
              if(mov.Destination == id) //id of place
              {
                   lm.Amount += mov.Quantity;
                   lm.Description = m.Description;
                   lm.ExhaustionDate = DateTime.Now.AddDays(lm.Amount / m.DailyNeeding);
                   lm.Id = m.Id;
                   lm.Productor = m.Productor;
                   lm.Place = "Pippo";
               }
          }

          if (lm.Amount> 0) matList.Add(lm);
      }

How can i do with LINQ?

Thank you very much

Upvotes: 0

Views: 86

Answers (3)

Pavel Anikhouski
Pavel Anikhouski

Reputation: 23218

It seems, that you'll need just a Select method, because your current solution doesn't show anything to group by

var id = "test";
var mat = new List<Equipment>();
var result = mat.Select(e =>
    {
        var amount = e.Movements.Where(m => m.Destination == id).Sum(m => m.Quantity);
        return new EquipmentModels
        {
            Description = e.Description,
            Id = e.Id,
            Productor = e.Productor,
            Amount = amount,
            ExhaustionDate = DateTime.Now.AddDays(amount / e.DailyNeeding)
        };
    })
    .Where(m => m.Amount > 0);

Get the amount value for Movements first, then map properties of every Equipment instance to new EquipmentModels instance. Finally, filter the result with Amount greater then 0

Upvotes: 1

Tomas Chabada
Tomas Chabada

Reputation: 3019

This is query syntax with LINQ grouping:

List<Equipment> mat = new List<Equipment>();//code for retrieve list

List<EquipmentModels> matList =
    (from equipment in mat
     group equipment by new
     { equipment.Id, equipment.Productor, equipment.DailyNeeding, equipment.Description }
        into groupped
     select new EquipmentModels
     {
         Id = groupped.Key.Id,
         Productor = groupped.Key.Productor,
         Place = "Pippo",
         Amount = groupped.Sum(i => i.Movements
             .Where(m => m.Destination == destinationId)
             .Sum(m => m.Quantity)),
         Description = groupped.Key.Description,
         ExhaustionDate =
             DateTime.Now.AddDays(groupped.Sum(i => i.Movements
                                      .Where(m => m.Destination == destinationId)
                                      .Sum(m => m.Quantity)) /
                                  groupped.Key.DailyNeeding),

     }).Where(i => i.Amount > 0)
    .ToList();

Upvotes: 1

Support Ukraine
Support Ukraine

Reputation: 1026

It will be smth like this

        mat.Select(x =>
        {
            var amount = x.Movements.Where(move => move.Destination == id).Sum(mv => mv.Quantity);
            return new EquipmentModels
            {
                Amount = amount,
                Description = x.Description,
                ExhaustionDate = System.DateTime.Now.AddDays(amount / x.DailyNeeding),
                Id = x.Id,
                Productor = x.Productor,
                Place = "Pippo",
            };
        }).Where(x => x.Amount > 0).ToList();

Upvotes: 1

Related Questions