Linq distinct record containing keywords

前端 未结 12 2090
醉话见心
醉话见心 2021-02-19 05:09

I need to return a distinct list of records based on a car keywords search like: \"Alfa 147\"

The problem is that, as I have 3 \"Alfa\" cars, it returns 1 + 3 records (i

12条回答
  •  陌清茗
    陌清茗 (楼主)
    2021-02-19 05:56

    One of the beautiful features of linq is that you can build up complicated queries in smaller and simpler steps and let linq figure out how to join them all together.

    The following is one way to get this information. I'm not sure whether this is the best and you would need to check it performs well when multiple keywords are selected.

    Assuming keywords is defined something like

    var keywords = "Alfa 147";
    var splitKeywords = keywords.Split(new char[] {' '});
    

    Stage 1

    Get a list of keywords grouped by Ad and Category and

    var subQuery = (from kac in keywordAdCategoryQuery  
        join k in keywordQuery  on kac.Keyword_Id equals k.Id 
        select new 
        {        
            kac.Ad_Id, 
            kac.Category_Id, 
            KeyWord = k.Name, 
        }); 
    
    var grouped = (from r in subQuery 
        group r by new { r.Ad_Id, r.Category_Id}  into results
        select new 
        { 
            results.Key.Ad_Id , 
            results.Key.Category_Id , 
            keywords = (from r in results select r.KeyWord) 
        });
    

    Note, the classes you posted would suggest that your database does not have foreign key relationships defined between the tables. If they did then this stage would be slightly simpler to write.

    Stage 2

    Filter out any groups that do not have each of the keywords

    foreach(var keyword in splitKeywords)
    {
        var copyOfKeyword = keyword ;   // Take copy of keyword to avoid closing over loop
        grouped = (from r in grouped where r.keywords.Contains(copyOfKeyword) select r) ;
    }
    

    Stage 3

    Group by Category and count the results per category

    var groupedByCategories = (from r in grouped 
        group r by r.Category_Id into results 
        join c in categoryQuery  on results.Key equals c.Id 
        select new 
        { 
            c.Id , 
            c.Name , 
            Count = results.Count()
        });
    

    Stage 4

    Now retrieve the information from sql. This should be done all in one query.

    var finalResults = groupedByCategories.ToList();
    

提交回复
热议问题