Home > Software design >  Update the count property in the same object while grouping in linq C#
Update the count property in the same object while grouping in linq C#

Time:01-17

Class:

Contact{
        public int Id { get; set; }

        public string Email { get; set; }

        public string DisplayName { get; set; }
        
        public int DocCount { get; set; }

        public string DocName { get; set; }
        

}

I have a list of contacts which look like

var contactList = new List<Contact>(){ 
                           new Contact(){1,"[email protected]","ABC",0,"testdoc1"},
                           new Contact(){1,"[email protected]","ABC",0,"testdoc2"},
                           new Contact(){1,"[email protected]","ABC",0,"testdoc3"},
                           new Contact(){2,"[email protected]","XYZ",0,"testdoc1"},
                           new Contact(){2,"[email protected]","XYZ",0,"testdoc2"},
                           new Contact(){2,"[email protected]","XYZ",0,"testdoc3"},
                           new Contact(){3,"[email protected]","MOP",0,"testdoc1"},
                           new Contact(){3,"[email protected]","MOP",0,"testdoc2"},
}

I am looking for the output where I need to update the doc count based on the count of the documents uploaded by user.

output expected is:

{1,"[email protected]","ABC",3,"testdoc1 testdoc2 testdoc3"},
{2,"[email protected]","XYZ",3,"testdoc1 testdoc2 testdoc3"},
{3,"[email protected]","MOP",2,"testdoc1 testdoc2"}

is there is any way to do so, I know we can introduce new class and do it, but looking for something minimal

CodePudding user response:

You can combine GroupBy() and Select():

var newList = contactList
        .GroupBy(p => new { p.Id, p.Email, p.DisplayName} )
        .Select(p=> new Contact(p.Key.Id,
                                p.Key.Email,
                                p.Key.DisplayName,
                                p.Count(),
                                string.Join(" ",p.Select(o=>o.DocName))))
        .ToList();

CodePudding user response:

I would argue that updating instances via LINQ is not a good practice - just create a new instance of Contact:

var result = contactList
    .GroupBy(c => c.Id)
    .Select(gr => new Contact
    {
        Id = gr.Key,
        Email = gr.First().Email,
        DisplayName = gr.First().DisplayName,
        DocCount = gr.Count(),
        DocName = string.Join(", ", gr.Select(c => c.DocName))
    })
    .ToList();

Or if you expect variance in emails/display names:

var result = contactList
    .GroupBy(c => (c.Id, c.Email, c.DisplayName))
    .Select(gr => new Contact
    {
        Id = gr.Key.Id,
        Email = gr.Key.Email,
        DisplayName = gr.Key.DisplayName,
        DocCount = gr.Count(),
        DocName = string.Join(", ", gr.Select(c => c.DocName))
    })
    .ToList();
  • Related