11

長方形のリストと点のリストがあります。ポイントのリストを対応する長方形と一致させるLINQクエリを作成したいと思います。このようなもの:

// Does not compile
var matches = from rect in rectangles
              join point in points on rect.Contains(point)
              select new { rect, point };

LINQを使用してこのようなことをどのように達成しますか?

編集:

私のリストは同じサイズです-1つの長方形と一致する1つのポイントがあり、長方形は重なりません。

ただし、問題のポイントは、この1つの特定の問題を解決することではありません。一般的に、単に「等しい」以外の条件で2つのリストを結合する方法に興味があります。

4

4 に答える 4

16

複数のfrom句を使用して結合を実現できます

 var matches = from p in points
               from r in rectangles
               where r.Contains(p)
               select new { r, p };

複数のfrom句は、結合構文よりも柔軟性があります(10個のLINQ神話のうちの神話5を参照)。これだけを学ぶ必要があり、すべての結合が簡単になります。

于 2012-05-04T20:07:00.780 に答える
3

Enumerable.ToLookupを使用して、長方形ごとにルックアップテーブルを作成できます。

var lookup = points.ToLookup(p => rectangles.First(r => r.Contains(point)));

これを使用することは、グループ化クエリに似ています。

foreach(var group in lookup)
{
    Console.WriteLine("Rectangle {0} contains:", group.Key);
    foreach(var point in group)
        Console.WriteLine("    {0}", point);
}

ちなみに、このクエリは本質的に2次式であり、非常に大きなデータセットではパフォーマンスが低下する可能性があります。多くの点や長方形に対してこれを行う必要がある場合は、空間データ構造を調べてすばやく検索することをお勧めします。ただし、この場合は問題にならない可能性があります。

于 2012-05-04T20:04:40.143 に答える
1

それらを結合する代わりに、whereステートメントを使用してみましたか?

var matches = from rectangle in rectangles
              from point in points
              where rectangle.Contains(point)
              select new { rectangle, point };
于 2012-05-04T20:08:15.170 に答える
1

欲しいものを手に入れるには2つの方法があります。

points.Select(p => new { Point = p, Rectangles = rectangles.Where(r => r.Contains(p) });

これは、ポイントが多くの長方形にある場合に対応します。

points.Select(p => new { Point = p, Rectangle = rectangles.First(r => r.Contains(p) });

これは、ポイントが正確に1つの長方形内にある場合に対応します。

2番目のケースは、シナリオで最適に機能するはずです。

于 2012-05-04T20:17:10.550 に答える