25

次のように ObjA と ObjB のリストがあります。

List<ObjA> List1;
List<ObjB> List2;

ObjA と ObjB の両方に User という共通フィールドがあり、User.Id に基づいてそれらを交差させたいと考えています。

class ObjA
{ 
  User user;
  .... other properties
}

class ObjB
{ 
  User user;
  .... other properties
}

class User
{
    int Id;
     .... other props
}

User.Id でこれら 2 つのリストを linq と交差させるにはどうすればよいですか?

その結果、ユーザーのリストのみが必要です。

4

5 に答える 5

39

一般的な考え方は

var commonUsers = list1.Select(a => a.User).Intersect(list2.Select(b => b.User));

Userただし、これ自体は が実装されていることを前提としてIEquatable<User>いますが、ここではそうではないようです。したがって、この実装を追加するかIntersect、カスタムを受け入れるオーバーロードを使用する必要がありますIEqualityComparer<User>

于 2012-07-01T19:39:18.897 に答える
10

1.この簡単なコードを見てください

  var result = (from objA in objAList
                join objB in objBList on objA.user.Id equals objB.user.Id
                select objA/*or objB*/).ToList();

2.完全なコード

 class QueryJoin
{
    static void Main(string[] args)
    {
        //create users
        User user1 = new User { Id = 1, Name = "anuo1" };
        User user2 = new User { Id = 2, Name = "anuo2" };
        User user3 = new User { Id = 3, Name = "anuo3" };
        User user4 = new User { Id = 4, Name = "anuo4" };
        User user5 = new User { Id = 5, Name = "anuo5" };
        //create objAList
        List<ObjA> objAList = new List<ObjA>();
        objAList.Add(new ObjA { user = user1 });
        objAList.Add(new ObjA { user = user2 });
        objAList.Add(new ObjA { user = user3 });
        //create objBList
        List<ObjB> objBList = new List<ObjB>();
        objBList.Add(new ObjB { user = user3 });
        objBList.Add(new ObjB { user = user4 });
        objBList.Add(new ObjB { user = user5 });

        //intersect
        var result = (from objA in objAList
                      join objB in objBList on objA.user.Id equals objB.user.Id
                      select objA/*or objB*/).ToList();

    }

}

class ObjA
{
    public User user { get; set; }
}

class ObjB
{
    public User user { get; set; }
}

class User
{
    public int Id { get; set; }
    public string Name { get; set; }
}
于 2016-11-02T01:18:02.487 に答える
7

IEqualityComparer または IEquatable を必要とせずに (いずれにせよより良いでしょう)

var commonUsers = list1
                  .Select(l1 => l1.User)
                  .Where(u => list1
                       .Select(l => l.User.Id)
                       .Intersect(list2
                          .Select(l2 => l2.Id))
                       .Contains(u.Id));

また

var commonUsers = list1.Select(l1 => l1.User)
                      .Where(u=> list2.Select(l2 => l2.User.Id)
                                        .Contains(u.Id));
于 2012-07-01T19:46:54.773 に答える
2

標準的な方法は、IEqualityComparerオブジェクトを利用することです。デフォルトのものは、標準の等価比較を使用します。IEqualityComparerインターフェイスを実装し、必要な比較を実行するクラスを作成します。IEnumerable.Intersect次に、カスタム比較クラスのインスタンスを受け入れるオーバーロードを呼び出すことができます

于 2012-07-01T19:41:31.853 に答える