Reputation: 41
I am new to Asp.Net, MVC3, Linq, and everything else related to it. I'm very used to PHP and ColdFusion so pardon my ignorance! Essentially what I am trying to do is re-create the situation in ColdFusion where I can perform the equivalent of a cfoutput's group attribute. I'm so used to just calling a stored procedure and then doing
<cfoutput group="id">
and then another inner cfoutput for any columns that have non-distinct data. Works like a charm! Not so much in Asp.Net.
I would like to stay with using my stored procedure, which is returning a join from two tables with a one-to-many relationship. For example's sake let's say I have 3 columns: a full name, a title, and a graduation year. The graduation year is the column from the joined table, so my result from the stored procedure looks like this:
Jim Professor 2005
Jim Professor 2008
Jim Professor 2011
I am sending this to the View. I am assuming it's the View's job to then group the data based on one of the columns (probably the full name). I want to output an HTML table with 3 columns and in this situation I would have ONE row:
Jim Professor 2005, 2008, 2011
I have googled tons of examples that use this thing called a group key. This does not seem to help me because I'm not interested in just outputting one value "Jim" (or whatever the grouped value is), I need both "Jim" and "Professor" values to be output for each row. My thinking is I would need 2 foreach loops, the outer loop displaying the fullname and title and the inner loop going through all possible matches for the graduation years. I cannot seem to get the graduation years in a group, especially with this IGrouping syntax. The key can only store one value and I need every value on that row, I only really need one or two values to be iterated over. Should I try and create a custom view model after I perform a secondary linq grouping and then send that to a strongly typed view?
EDIT: Ok, I have code that works but it seems very inefficient as I basically have to re-define all of the columns/values that I have from my stored procedure. It almost makes me want to forget stored procedures and just use LINQ for everything. It seems what I was asking for is a kind of "group on multiple columns" and link helped immensely.
var records = db.getRecords();
var groups = from r in records
group r by new
{
r.id
}
into row
select new ListVM()
{
id = row.Key.id,
fullname = row.Select(x => x.fullname).First(),
title = row.Select(x => x.title).First(),
degrees = row.Select(x => x.degree_name).ToList(),
majors = row.Select(x => x.major_name).ToList()
};
return View(groups);
I of course had to create a ViewModel for this to work. In my view then I can use for loops to iterate over the degrees and majors lists. Is this the best way to do this? I just generally need more than just the group key to display my entire row of information, and only want to iterate over lists once or twice in a 20 column row, as opposed to only displaying the group key once and iterating over everything in most examples I see.
Upvotes: 0
Views: 1602
Reputation: 41
I believe I've finally found out how to solve what I was looking for. A "group join" seems to solve my problem with ease. The information I found on this page solved it: http://geekswithblogs.net/WillSmith/archive/2008/05/28/linq-joins-and-groupings.aspx
Upvotes: 0
Reputation: 1377
I'm not that big specialist with Linq and MVC, but faced with your problem I would:
I would use knowledge from these topics to solve your particular problem:
a) grouping by multiple columns: Group By Multiple Columns
b) Concatenation as an aggregate function: Using LINQ to concatenate strings
c) Using aggregates and grouping by multiple columns How to write a LINQ query combining group by and aggregates?
Once you have data in your view model, just display it.
Upvotes: 0