110,534
社区成员
发帖
与我相关
我的任务
分享
最笨最好理解的办法是将二维数组拆成一维数组,然后遍历一维数组进行组合。
static void Main(string[] args)
{
var List0 = new int[][]
{
new int[] {0},
new int[] {1},
new int[] {2},
new int[] {3}
};
foreach (var c in List0.Combination(3))
{
foreach (var x in c.CartesianProduct())
{
Console.WriteLine(string.Join(",", x));
}
}
}
static class Extend
{
/// <summary>
/// 笛卡尔积
/// </summary>
/// <typeparam name="T"></typeparam>
/// <param name="sequences"></param>
/// <returns></returns>
public static IEnumerable<IEnumerable<T>> CartesianProduct<T>(
this IEnumerable<IEnumerable<T>> sequences)
{
IEnumerable<IEnumerable<T>> emptyProduct = new[] { Enumerable.Empty<T>() };
return sequences.Aggregate(
emptyProduct,
(accumulator, sequence) =>
from accseq in accumulator
from item in sequence
select accseq.Concat(new[] { item }));
}
/// <summary>
/// 组合
/// </summary>
/// <typeparam name="TValue"></typeparam>
/// <param name="values"></param>
/// <param name="num"></param>
/// <returns></returns>
public static IEnumerable<IEnumerable<TValue>> Combination<TValue>(
this IEnumerable<TValue> values,
// Int32 count,
Int32 num)
{
var t = Enumerable.Range(0, num).ToList();
do
{
yield return values.Where((x, i) => t.Contains(i));
}
while (NextCombination(t, values.Count(), num));
}
/// <summary>
/// C(n,m) 的下一项
/// </summary>
/// <param name="ar"></param>
/// <param name="num"></param>
/// <param name="k"></param>
/// <returns></returns>
public static bool NextCombination(List<int> ar, int n, int m)
{
if (ar.Count() != m) ar = Enumerable.Range(0, m).ToList();
bool changed = false, finished = false;
if (m > 0)
{
for (int i = m - 1; !changed && !finished; i--)
{
if (ar[i] < (n - 1) - (m - 1) + i)
{
ar[i]++;
if (i < m - 1)
{
for (int j = i + 1; j < m; j++)
{
ar[j] = ar[j - 1] + 1;
}
}
changed = true;
}
finished = (i == 0);
}
}
return changed;
}
}
static void Main(string[] args)
{
var List0 = new int[][]
{
new int[] {1, 2},
new int[] {3, 4},
new int[] {5},
new int[] {1}
};
foreach (var c in List0.Combination(3))
{
foreach (var x in c.CartesianProduct())
{
Console.WriteLine(string.Join(",", x));
}
}
}
对 List0 有 123 但无 231、321,所以不存在排列 先求 C(m, 3) (m 是第一维的长)的组合序列 在对 组合序列 的每一成员求 笛卡尔积