Linq中等效的DISTINCT(sql server)是什么

时间:2013-07-22 06:25:26

标签: sql linq

我有一个表(发送)列(Id,UserId,SendDate)和另一个表(Receive)列(Id,SendId,UserName)。

我希望使用所有RecieveUserName显示SendTable中的所有记录。

例如。

(Send)
1   1   2013
2   2   2013


(Recieve)
1   1   Jack
2   1   Ema
3   2   Alex
4   2   Sara


Result
1   1   2013  Jack, Ema
2   2   2013  Alex, Sara

我在SqlServer中使用此查询(DISTINCT关键字从SELECT语句的结果中删除重复的行)

SELECT DISTINCT c2.Id,
(SELECT    STR( UserName )+ ','
 FROM         dbo.Reciver c1
 WHERE     c1.SendId = c2.id FOR XML PATH('')) Concatenated, c2.SendDate, c2.UserId
 FROM         dbo.Send AS c2 INNER JOIN
 dbo.Reciver ON c2.Id = dbo.Reciver.SendId

如何在Linq中查询?

3 个答案:

答案 0 :(得分:2)

Distinct也可在LINQ中找到。

例如

public class Product
{
    public string Name { get; set; }
    public int Code { get; set; }
}

Product[] products = { new Product { Name = "apple", Code = 9 }, 
                   new Product { Name = "orange", Code = 4 }, 
                   new Product { Name = "apple", Code = 10 }, 
                   new Product { Name = "lemon", Code = 9 } };
var lstDistProduct = products.Distinct();
foreach (Product p in list1)
{
    Console.WriteLine(p.Code + " : " + p.Name);
}

将返回所有行。

var list1 = products.DistinctBy(x=> x.Code);

foreach (Product p in list1)
{
    Console.WriteLine(p.Code + " : " + p.Name);
}

将返回9和4

答案 1 :(得分:1)

在我看来,您不需要在此Linq查询中使用Distinct。假设你在linq datacontext上设置了表之间的关系,你可以这样做:

var result = from s in context.Send
             select new {
                 id = s.Id,
                 userId = s.UserId,
                 date = s.SendDate,
                 users = s.Receive.Select(u => u.UserName)
             }

注意:usersIEnumerable<String> - 您可以在客户端上使用string.Join()将名称加入字符串。

<强>更新

要将用户作为字符串返回,首先需要通过调用AsEnumerable()ToList()以及Linq to Sql查询来“切换”到Linq To Objects。

var output = from s in result.AsEnumerable()
             select new {
                 id = s.id,
                 userId = s.userId,
                 date = s.date,
                 users = string.Join(", ", s.users)
             }

另请参阅Gert Arnolds answer以获得更好的解释。

答案 2 :(得分:1)

您想要的只能分两步完成。不是因为DISTINCT,而是因为FOR XML。后者的C#等价物是String.Join(),但您不能直接在linq to entity语句中使用它。所以你必须首先收集所需的数据,然后切换到linq到对象(通过应用AsEnumerable),然后进行连接和区分:

 db.Sends
   .Where(s => s.Receivers.Any())
   .Select(s => new { 
                       s.Id, 
                       Concatenated = s.Receivers.Select(r => r.UserName)
                       s.SendDate,
                       s.UserId
                    })
   .AsEnumerable()
   .Select(x => new { 
                       s.Id, 
                       Concatenated = String.Join(", ", x.Concatenated)
                       s.SendDate,
                       s.UserId
                    })
   .Distinct()