EF LINQ는 여러 개의 중첩 된 엔티티를 포함합니다.


155

좋아, 나는 다음과 같은 계층 구조를 가진 트라이 레벨 엔티티를 가지고 있습니다 : Course-> Module-> Chapter

원래 EF LINQ 문은 다음과 같습니다.

Course course = db.Courses
                .Include(i => i.Modules.Select(s => s.Chapters))
                .Single(x => x.Id == id); 

이제 코스와 관련된 Lab이라는 다른 엔터티를 포함하고 싶습니다.

랩 엔티티를 포함 시키려면 어떻게합니까?

다음을 시도했지만 작동하지 않았습니다.

Course course = db.Courses
                .Include(i => i.Modules.Select(s => s.Chapters) && i.Lab)
                .Single(x => x.Id == id); 

두 번째 엔터티 포함에 대한 아이디어가 있습니까?

모든 조언이나 정보는 높이 평가 될 것입니다. 감사!


1
추가 .Include포함이 코스의 손자임을 의미하지 않는 한 다른 추가 는 작동합니다. 이것 또는 더 나은 선택권은 이것입니다
von v.

답변:


234

당신은 또 다른 추가 시도했다 Include:

Course course = db.Courses
                .Include(i => i.Modules.Select(s => s.Chapters))
                .Include(i => i.Lab)
                .Single(x => x.Id == id);

Include부울 연산자를 사용하지 않으므로 솔루션이 실패합니다.

Include(i => i.Modules.Select(s => s.Chapters) &&          i.Lab)
                           ^^^                  ^             ^ 
                          list           bool operator    other list

업데이트 자세한 내용을 보려면 LinqPad를 다운로드 하고 샘플을 살펴보십시오. Linq와 Lambda에 익숙해지는 가장 빠른 방법이라고 생각합니다.

시작으로 - 차이 사이에 SelectInclude있음이 선택으로 당신이 결정하는 것입니다 무엇을 당신이 (프로젝션 일명) 반환 할. 포함은 Eager 로딩 기능으로, Entity Framework에서 다른 테이블의 데이터를 포함하도록 지시합니다.

Include 구문은 문자열에있을 수도 있습니다. 이처럼 :

           db.Courses
            .Include("Module.Chapter")
            .Include("Lab")
            .Single(x => x.Id == id);

그러나 LinqPad 의 샘플은 이것을 더 잘 설명합니다.


감사합니다! 이것에 대해 더 배울 수있는 곳은 어디입니까? 특히 Include와 Select의 차이점에 관심이 있습니다.
AnimaSola

3
이 중 하나만이 나를 위해 일했습니다 : .Include("Module.Chapter"). 왜 그런지 아십니까?
Jo Smo

5
@JoSmo 확장 메소드 System.Data.Enity에 액세스하려면 네임 스페이스를 가져와야합니다 . 추가 정보를 원하시면 여기
옌스 클로스 터

using System.Data.Entity;그것을했다. 감사!
Jo Smo

1
화려한 linqpad에 대해 언급하고 Jen.
Mike

38

Entity Framework Core ( EF.core) 에서는 .ThenInclude다음 레벨을 포함 하는 데 사용할 수 있습니다 .

var blogs = context.Blogs
    .Include(blog => blog.Posts)
        .ThenInclude(post => post.Author)
    .ToList();

자세한 정보 : https://docs.microsoft.com/en-us/ef/core/querying/related-data

참고 : 말은 여러 필요 ThenInclude()blog.Posts단지를 반복 Include(blog => blog.Posts)하고 다른 작업을 수행 ThenInclude(post => post.Other).

var blogs = context.Blogs
    .Include(blog => blog.Posts)
        .ThenInclude(post => post.Author)
    .Include(blog => blog.Posts)
        .ThenInclude(post => post.Other)
 .ToList();

EF.core에서는 .Include (i => i.Modules.Select (s => s.Chapters)), 특히 .Select inside .Include를 수행 할 수없는 것 같습니다. 누구든지 확인하거나 말할 수 있습니까?
tutugates

@ttugates이 선택과 어떤 관계가 있습니까? 나는 당신이하고 싶은 것이 ThenIncludeEF 핵심에서 정확히 무엇을하고 있다고 생각합니다 . 좋은 예를 들어 질문을하면 대답 할 수있을 것입니다.
Nick N.

@Nick N - Entity Framework Linq 쿼리 : 여러 Nav 속성의 위치 및 3 차 Nav 속성에서 선택하는 방법 . 내가 선택하는 것이 내가 일치하는 것이 아니기 때문에 포함이 필요하지 않으므로 질문이 중요합니다. 내 질문은 너무 좁을 수도 있지만 도움을 주셔서 감사합니다.
14 분 32 초에 tutugates

1
아 실제로 .ThenInclude ()가 작동합니다. 지능이 관련 테이블을 표시하는 데는 시간이 오래 걸립니다.
Chris J

23

Include유창한 인터페이스의 일부이므로 Include서로를 따라 여러 문장을 작성할 수 있습니다.

 db.Courses.Include(i => i.Modules.Select(s => s.Chapters))
           .Include(i => i.Lab)
           .Single(x => x.Id == id); 

감사합니다! 이것에 대해 더 배울 수있는 곳을 알려 주시겠습니까? 감사!
AnimaSola

1
모듈에 결합하려는 테이블이 여러 개인 경우 구문이 무엇인지 알고 있습니까? 그것이 챕터들과 다른 것들과 연결되어 있다고 말합니까?
David Spence

.Net에 유창합니까 아니면 설치해야하는 라이브러리입니까?
codea

19

시도해 볼 수도 있습니다

db.Courses.Include("Modules.Chapters").Single(c => c.Id == id);

4
감사합니다-문자열의 점 표기법은 매우 유용합니다
Evert

1
이 방법이 유용 할 수 있지만 나중에 사용하지 않는 한 가지 이유는 나중에 리팩토링하기 쉽기 때문입니다. "Chapters"엔터티의 이름을 변경하면 다른 예의 이름이 자동으로 바뀝니다. 또 다른 방법은 컴파일 타임에 런타임이 아니라 오류가 더 빨리 발견된다는 것입니다.
MGOwen

2

다음과 같은 확장 메소드를 작성할 수 있습니다.

    /// <summary>
    /// Includes an array of navigation properties for the specified query 
    /// </summary>
    /// <typeparam name="T">The type of the entity</typeparam>
    /// <param name="query">The query to include navigation properties for that</param>
    /// <param name="navProperties">The array of navigation properties to include</param>
    /// <returns></returns>
    public static IQueryable<T> Include<T>(this IQueryable<T> query, params string[] navProperties)
        where T : class
    {
        foreach (var navProperty in navProperties)
            query = query.Include(navProperty);

        return query;
    }

그리고 일반적인 구현에서도 다음과 같이 사용하십시오.

string[] includedNavigationProperties = new string[] { "NavProp1.SubNavProp", "NavProp2" };

var query = context.Set<T>()
.Include(includedNavigationProperties);

귀하의 답변을 시도했지만 무한 루프로 인해 스택 오버 플로우 예외가 발생합니다.
Victoria S.

1
.는 실제에 방해가되지 않도록 @VictoriaS, 당신은 확장 메서드의 이름을 바꿀 수 있습니다Include
모흐센 아프신
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.