按顺序生成数字

在给定startIndex,数字数和最大数量的情况下,如何使用LinQ在此序列中生成数字。例如:

Sample Numbers = 1,2,3,4 StartIndex = 1 (ie it should start from 1) Sequence number count = 3 Maximum number = 4 (ie till 4) Expected result given the above details : 1,2,3 1,3,4 1,2,4 

有没有办法用linQ做到这一点?

如果您不需要序列的长度是动态的,那么您可以使用:

 var startindex=1; var maxindex=4; var data = Enumerable.Range(startindex,maxindex); var qry = from x in data where x == startindex from y in data where x < y from z in data where y < z select new { x, y, z }; foreach (var tuple in qry) { Console.WriteLine("{0} {1} {2}", tuple.x, tuple.y, tuple.z); } 

序列长度硬编码为3,因为有3个可枚举的连接:x,y,z。

如果您想动态加入任意数量的枚举,那么您可以使用Eric Lippert的Cartesian Product Linq示例。

您传递一组N个项目的k序列,它将返回一组长度为k的所有组合。

现在,您不希望结果中包含重复的元素。 所以,我在Eric的例子中添加了以下内容:

 where accseq.All(accitem => accitem < item) 

这是最终的解决方案(为清晰起见而编辑):

 var startindex=1; var maxindex=7; var count = 3; // Make a set of count-1 sequences, whose values range from startindex+1 to maxindex List> sequences = new List>(); // We only want permutations starting with startindex. So, the first input sequence to be joined should only have the value startindex. List list1 = new List(); list1.Add(startindex); sequences.Add(list1); // The rest of the input sequences to be joined should contain the range startindex+1 .. maxindex for (int i=1; i< count; i++) { sequences.Add(Enumerable.Range(startindex+1,maxindex-startindex).ToList()); } // Generate the permutations of the input sequences IEnumerable> emptyProduct = new[] { Enumerable.Empty() }; var result = sequences.Aggregate( emptyProduct, (accumulator, sequence) => from accseq in accumulator from item in sequence where accseq.All(accitem => accitem < item) select accseq.Concat(new[] {item})); // Show the result foreach (var x in result) { Console.WriteLine(x); } 

试试这个function。

 public static IEnumerable> Permute(IEnumerable list) { if (list.Count() == 1) return new List> { list }; return list.Select((a, i1) => Permute(list.Where((b, i2) => i2 != i1)).Select(b => (new List { a }).Union(b))) .SelectMany(c => c); } 

//这里范围(startindex,count)

 List list1 = Enumerable.Range(1, 3).ToList(); 

//生成所有排列

 var permutationlist = Permute(list1); 

在此处输入图像描述

好的,首先让我们清楚地说明问题。 我假设你的数字是int但这是一个几乎无关紧要的细节,但具体性使思考更加流畅

你有一个int的序列a_0, a_1, a_2, ..., a_N

你有一个满足1 <= k <= N + 1的整数k

您有一个起始索引start >=0和一个结束索引end <= N

您希望所有子序列a_i0, a_i1, a_i2, ..., a_ik的长度为k ,使得i0 = startik = end

那你的算法很简单。 你想要生成{ start + 1, ..., end - 1 }的大小为k - 2的所有组合。 给定这样的组合j1, j2, ..., j(k-1) ,对它进行排序,调用得到的有序序列i1, i2, ..., i(k-1)并返回序列a_start, a_i1, a_i2, ..., a_i(k-1), a_end

既然您已经知道问题的正式陈述,以及您需要解决的问题,那么生成所述组合的资源比比皆是。 比照 Google搜索:生成C#或Knuth Volume 4A 组合 。