"일꾼이 일을 잘하려면 먼저 도구를 갈고 닦아야 한다." - 공자, 『논어』.
첫 장 > 프로그램 작성 > LINQ 전체 외부 연결 작동 방법에 대한 자세한 설명

LINQ 전체 외부 연결 작동 방법에 대한 자세한 설명

2025-03-13에 게시되었습니다
검색:140

How to Perform a Full Outer Join in LINQ?

linq- 전체 외부 연결

질문:

공통 키 필드를 기반으로 두 객체 목록간에 완전히 연결되는 방법으로, 다른 목록에 해당 일치가 없더라도 두 목록의 모든 레코드가 결과에 포함되도록하는 방법은 무엇입니까?

답변:

1. 완전히 외부 연결을위한 사용자 정의 확장 방법

LINQ에서 전체 외부 연결을 구현하려면 다음과 같이 사용자 정의 확장 메소드를 정의 할 수 있습니다.

public static IEnumerable FullOuterJoin(
    this IEnumerable a,
    IEnumerable b,
    Func selectKeyA,
    Func selectKeyB,
    Func projection,
    TA defaultA = default(TA),
    TB defaultB = default(TB),
    IEqualityComparer cmp = null)
{
    cmp = cmp ?? EqualityComparer.Default;
    var alookup = a.ToLookup(selectKeyA, cmp);
    var blookup = b.ToLookup(selectKeyB, cmp);

    var keys = new HashSet(alookup.Select(p => p.Key), cmp);
    keys.UnionWith(blookup.Select(p => p.Key));

    var join = from key in keys
               from xa in alookup[key].DefaultIfEmpty(defaultA)
               from xb in blookup[key].DefaultIfEmpty(defaultB)
               select projection(xa, xb, key);

    return join;
}

2.

제공된 예제에는 firstNames lastNames 가 있습니다. 전체 외부 연결을 수행하려면 다음 코드를 사용할 수 있습니다.

var outerJoin = from first in firstNames
                join last in lastNames
                on first.ID equals last.ID
                into temp
                from last in temp.DefaultIfEmpty()
                select new
                {
                    id = first != null ? first.ID : last.ID,
                    firstname = first != null ? first.Name : string.Empty,
                    surname = last != null ? last.Name : string.Empty
                };

3.

이 코드는 왼쪽 외부 조인을 사용합니다. 여기서

firstNames 의 각 레코드는 lastNames 의 첫 번째 일치 레코드에 연결되며 일치하지 않으면 기본값에 연결됩니다. 는 temp 문으로 lastNames 에서 일치하는 레코드의 임시 컬렉션을 생성하여 defaultifempty () 를 적용하여 불일치 레코드가 포함되도록합니다. 이것은 실제로 전체 의미에서 전체 외부 연결이 아니라 왼쪽 외부 연결을 구현합니다. 전체 외부 연결을 달성하려면 fullouterjoin 확장 메소드를 사용하여 위에서 사용자 정의해야합니다.

4.

완전히 외부 연결에 대한 예상 출력은 다음과 같습니다.

Id FirstName LastName --------------------- 1 John Doe 2 Sue 3 Smith
ID  FirstName  LastName
--  ---------  --------
1   John       Doe
2   Sue        
3             Smith
는 일치하지 않는 레코드의 기본값을 지정할 수있는 확장 방법을 제공합니다. 이 예에서는 불일치 한 이름과 불일치 ID에 대한 음의 정수에 대해

string.empty

를 지정합니다.

6. 성능 고려 사항

완전히 외부 연결의 실행 시간은 O (n m)이며, 여기서 n과 m은 두 입력 목록의 길이입니다.

tolookup ()

조작은 O (n) 시간이 걸리고 후속 작업에는 O (n m) 시간이 필요하기 때문입니다.

7. 이 완전히 외부 연결 구현은 현재 LINQ 표준의 일부가 아니지만 향후 버전에 포함하는 것이 좋습니다. 표준 LINQ는 전체 외부 연결을 직접 지원하지 않으며이를 구현하려면 사용자 정의 확장 방법이 필요합니다.

최신 튜토리얼 더>

부인 성명: 제공된 모든 리소스는 부분적으로 인터넷에서 가져온 것입니다. 귀하의 저작권이나 기타 권리 및 이익이 침해된 경우 자세한 이유를 설명하고 저작권 또는 권리 및 이익에 대한 증거를 제공한 후 이메일([email protected])로 보내주십시오. 최대한 빨리 처리해 드리겠습니다.

Copyright© 2022 湘ICP备2022001581号-3