views:

42

answers:

2

i have a linq query that returns Articles ordered by the number of tags that match the current article

e.g

current article has tags - tag1, tag2, tag3

tagged article 1 - tag1,tag2,tag3 tagged article 2 - tag1,tag2

linq i have is

 DataTable query = (from row in dt.AsEnumerable()  
                           let tags = row.Field<string>("Tags").Split(seperator, StringSplitOptions.RemoveEmptyEntries)
                           let count = tags.Count(t => currenttags.Contains(t))
                           orderby count descending
                           select row).CopyToDataTable();

i want to add the group by ClassName which is the article type (literature, case study, download etc)

so would be

group row by {row.Field<string>("ClassDisplayName")}

however when i add this to the query i get red sqiggles

   DataTable query = (from row in dt.AsEnumerable()    
                           group row by {row.Field<string>("ClassDisplayName")}
                           let tags = row.Field<string>("Tags").Split(seperator, StringSplitOptions.RemoveEmptyEntries)
                           let count = tags.Count(t => currenttags.Contains(t))                             
                           orderby count descending                             
                           select row).CopyToDataTable();

any ideas what i'm doing wrong?

This is the current one that works with just the order by

DataTable dt = ArticleCollection(SqlClause.ToString());

        var seperator = new[] { ",", " " };
        var current = dr["Tags"].ToString();
        var currenttags = dr.Field<string>("Tags").Split(seperator, StringSplitOptions.RemoveEmptyEntries);

        DataTable query = (from row in dt.AsEnumerable()                             
                           let tags = row.Field<string>("Tags").Split(seperator, StringSplitOptions.RemoveEmptyEntries)
                           let count = tags.Count(t => currenttags.Contains(t))
                           orderby count descending
                          // group row by row.Field<string>("ClassDisplayName") into g
                           select row).CopyToDataTable();


        if (!DataHelper.DataSourceIsEmpty(query))
        {
            TagRepeaterOutter.DataSource = query;
            TagRepeaterOutter.DataBind();
        }
A: 

If you are trying to order by count, and within each value of count, group the rows by ClassDisplayName, you can try this:

DataTable query = (from row in dt.AsEnumerable()                             
                   let tags = row.Field<string>("Tags").Split(seperator, StringSplitOptions.RemoveEmptyEntries)
                   let count = tags.Count(t => currenttags.Contains(t))
                   let displayName = row.Field<string>("ClassDisplayName")
                   orderby count descending, displayName
                   select row).CopyToDataTable();
adrift
so i don't need to use "group row by row.Field<string>("ClassDisplayName") into g"? sorry new to linq
Adam Wright
if i correctly understand what you are trying to do (order by count, then by classdisplayname), then you don't need 'group'.
adrift
what i want to do with the data is bind it to nested repeater, so all casestudies will be under caserstudies and literature under literature. thats why i was thinking of usinig "group"
Adam Wright
i'm not very familiar with nested repeater controls. can you use them to display a hierarchy within a single table, or do you need to bind them to a parent table and related child table?
adrift
parent and child table i think, that why i was looking at grouping using linq. does that return more than one table?
Adam Wright
afaik, group will not return multiple data tables like this. also, looking at [this example](http://support.microsoft.com/kb/306154), a relationship must exist between the tables, so it sounds like you would need to set up a dataset with a parent table, child table, and relationship between them, and then create two linq queries - one to populate the parent table and one to populate the child table. Leaving for work now -- will not be able to respond for a while.
adrift
A: 
 IEnumerable<DataRow> types = (from row in dt.AsEnumerable()
                                      group row by row.Field<string>("ClassDisplayName") into g
                                      select g.FirstOrDefault());

        DataTable dtType = types.CopyToDataTable();

and then another query on the inner nested repeater

DataTable query = (from row in dt.AsEnumerable()
                               where (row.Field<string>("ClassDisplayName") == dr["ClassDisplayName"].ToString())
                               let tags = row.Field<string>("Tags").Split(seperator, StringSplitOptions.RemoveEmptyEntries)
                               let count = tags.Count(t => currenttags.Contains(t))                                  
                               orderby count descending                              
                               select row).CopyToDataTable();

anyone have a better solution let me know

Adam Wright