LINQ Union Column如果经过身份验证

时间:2010-08-29 18:47:49

标签: c# linq

我有一个项目的简单评级应用程序。主要有三个表:

Item
{
   ItemID,
   Contents
}

asp_User
{
   UserID,
   Name
}

Rating
{  
   RatingID,
   ItemID,
   UserID,
   int Rating
}

我有读取项目的linq代码:

var q = from item db.Item
        select item;

然后,我想在q后面附加一个列,其中包含当前经过身份验证的用户的每个项目行的评级。如果用户未登录或经过身份验证的用户未提供评级,则结果将为0.

如果重要的话,我正在使用SqlMembershipProvider。

实施例

q的最终结果应如下所示:

[认证]

//The currently authenticated user has commented on Item.ID = 1 and has given it a 9.
q = {ID = 1, Contents = "Whatever", Rating = 9},

//The currently Authenticated user has not commented on Item.ID = 2.
{ID = 2, Contents = "Something", Rating = 0};

[未经过身份验证]

//There is not an authenticated user
q = {ID = 1, Contents = "Whatever", Rating = 0},

//There is not an authenticated user
{ID = 2, Contents = "Something", Rating = 0};

2 个答案:

答案 0 :(得分:0)

你打算用“var q”做什么?很难说出你的意图是什么,在这种情况下它很重要。基于缺乏背景,这是我能做的最好的事情。希望这会有所帮助:

if(User.IsAuthenticated)
{
    var q = from item in db.Item
            join r in db.Rating on c.Id equals r.ItemId
            select new {ID = item.Id, Contents = item.Contents, Rating = r.Rating};

    // Do whatever you want with this here.
}
else
{
    var y = db.Item;

    // Do whatever you want with this here.
}

答案 1 :(得分:0)

从性能角度来看,Ocelots解决方案是可行的方法(特别是如果您查询多个项目)。 但是为了满足Rating应该是Item的属性的条件,您可以通过在LINQ-to-SQL数据类的同一名称空间中使用部分类来扩展Item类:

public partial class Item
{
    public int Rating
    {
        get
        {
            if (!Thread.CurrentPrincipal.Identity.IsAuthenticated)
                return 0;

            using (var db = new ApplicationDataContext())
            {
                return db.Item
                    .Where(r => r.ItemID == this.ItemID
                        && r.UserID == Thread.CurrentPrincipal.Identity.Name)
                    .Select(r => r.Rating)
                    .SingleOrDefault();
            }
        }
    }
}

如果你想用像Ocelot提出的单个SQL请求得到相同的结果,你应该使用GroupJoin(就像SQL LEFT OUTER JOIN一样工作)并选择当前的用户评级,如上所述。