は私がIEnumerable <T>のすべてのサブコレクションを生成できますか?私は何を意味
{ 1, 2, 3 }
のようなセットを持っている場合、すべてのサブセットがセットのサイズ3
を持っているので、それらの2^3
ある
{ },
{ 1 },
{ 2 },
{ 3 },
{ 1, 2 },
{ 2, 3 },
{ 1, 3 },
{ 1, 2, 3 }
であるということです。私が思うどんな解決策も、サイズがn - 1
までの以前のサブセットを「覚えている」必要があります。ここで、n
はセットの長さです。例えば、私はそれはそれはsource
が配列に合うことができると仮定し、そしてHashSet
が前のサブコレクションを保持できることを前提としてどのように
public static IEnumerable<IEnumerable<T>> AllSubcollections<T>(this IEnumerable<T> source)
{
// The empty set is always a subcollection
yield return new List<T>() { };
T[] arr = source.ToArray();
IEnumerable<int> indices = Enumerable.Range(0, arr.Length);
var last = new List<HashSet<int>>(new List<HashSet<int>>() { new HashSet<int>() });
for(int k = 1; k < arr.Length; ++k)
{
var next = new List<HashSet<int>>(new List<HashSet<int>>());
foreach(HashSet<int> hs in last)
{
foreach(int index in indices)
{
if(!hs.Contains(index))
{
var addition = hs.Concat(new List<int> { index });
yield return addition.Select(i => arr[i]);
next.Add(new HashSet<int>(addition));
}
}
}
}
}
お知らせのように見える書いたソリューションを持っています。
IEnumerable<T>
はyield
であり、任意の数の結果(無限の場合もあります)がある場合、サブセットの問題に対してこれを行う解を書くことは可能でしょうか?
:彼の解決策は、その入力に.ToArray()を呼び出し、その可能性は無限のフィードにすぐに爆発していない、このためのアルゴリズムを記述するかどうかを知りたいです。 – Joshua