使用 Linq 左连接多个 IList<>

Left join multiple IList<> using Linq

我基本上有一个 post 存储库,应该 return 所有画廊项目都属于它。如果没有属于 post 的画廊,它应该仍然 return post 与 post id

不同
public List<PostLocalizedOutput> GetAllPostsWithCategories(string culture, bool? isPublished)
    {
        var query =
                from p in Context.Posts
                join pl in Context.PostsLocalized on p.Id equals pl.PostId
                from c in p.Categories
                join cl in Context.CategoriesLocalized on c.Id equals cl.CategoryId
                from g in p.Galleries.DefaultIfEmpty()
                join gi in Context.GalleryItems on g.Id equals gi.GalleryId 


                where
                  pl.Culture == culture &&
                  cl.Culture == culture
                select new PostLocalizedOutput
                {
                    PostId = pl.PostId,
                    CategoryId = cl.CategoryId,
                    Title = pl.Title,
                    FormattedCategoryName = cl.FormattedCategoryName,
                    PostContent = pl.PostContent,
                    PostType = pl.Post.PostType,
                    IOrder = pl.Post.IOrder,
                    Tags = pl.Tags,
                    PublishDate = pl.Post.PublishDate,
                    ViewCount = pl.Post.ViewCount,
                    ShowInHomePageSlider = pl.Post.ShowInHomePageSlider,
                    AllowComments = pl.Post.AllowComments,
                    Image = pl.Post.Image,
                    IsArchived = pl.Post.IsArchived,
                    IsDraft = pl.Post.IsDraft,
                    IsPublished = pl.Post.IsPublished,
                    GalleryItems = new GalleryItemOutput
                    {
                        FileName = gi.FileName,
                        GalleryId = gi.GalleryId,
                        Id = gi.Id,
                        Notes = gi.Notes,
                        Title = gi.Title
                    } (around here i feel like i should foreach something or what?)
                };

        return query.OrderBy(x => x.IOrder).ThenBy(x => x.PublishDate).DistinctBy(x => x.PostId).ToList();
    }

这是我的 postlocalizedoutput

public class PostLocalizedOutput : IOutputDto
{
    public int PostId { get; set; }

    public int CategoryId { get; set; }

    public bool IsPublished { get; set; }

    ...  
    public List<GalleryItemOutput> GalleryItems { get; set; }

}

GalleryItemOutput 应该是列表,因为我想要 post 的所有画廊项目。但是当我将它定义为存储库中的列表时,我无法设置 post 的 galleryitem 的每个字段。这段代码现在 return 我有四行,因为我有四个画廊项目 post 并且每个都有相同的 postId。我不要那个。 DefaultIfEmpty 也不起作用,即使 post 没有任何画廊项目我应该仍然能够在没有画廊项目的情况下获得 post。

有什么方法吗?

感谢所有建议。

这应该可以帮助您入门。 不知道这是否编译,请只解释为伪代码。看起来您的顶级范围变量是 PostsLocalized 而不是 Posts。此代码 assume/uses 导航属性可能已在您的 EDM 类 中设置。我在这里过度使用 let 关键字只是为了让你更清楚。在 select 新子句中,您可以将 p1.Post... 更改为仅 p。我让他们尽可能少地进行编辑。

var query =
        from pl in Context.PostsLocalized
        where pl.Culture == culture
        let p = p1.Post
        let categories = p.Categories
        let localizedCategories = categories.SelectMany(cat => cat.CategoriesLocalized).Where(cl => cl.Culture == culture)
        let galleries = p.Galleries
        let galleryItems = galleries.SelectMany(gal => gal.GalleryItems)
        let cl = localizedCategories.FirstOrDefault() // only one or zero of these i assume?

        select new PostLocalizedOutput
        {
            PostId = p1.PostId,
            CategoryId = cl.CategoryId, 
            Title = pl.Title,
            FormattedCategoryName = cl.FormattedCategoryName,
            PostContent = pl.PostContent,
            PostType = pl.Post.PostType,
            IOrder = pl.Post.IOrder,
            Tags = pl.Tags,
            PublishDate = pl.Post.PublishDate,
            ViewCount = pl.Post.ViewCount,
            ShowInHomePageSlider = pl.Post.ShowInHomePageSlider,
            AllowComments = pl.Post.AllowComments,
            Image = pl.Post.Image,
            IsArchived = pl.Post.IsArchived,
            IsDraft = pl.Post.IsDraft,
            IsPublished = pl.Post.IsPublished,

            GalleryItems = galleryItems.Select(gi => new GalleryItemOutput
            {
                FileName = gi.FileName,
                GalleryId = gi.GalleryId,
                Id = gi.Id,
                Notes = gi.Notes,
                Title = gi.Title
                })
// might need a .ToList() here on those GalleryItems

 (around here i feel like i should foreach something or what?)
            };