数组的所有组合,在三个级别停止C#

时间:2017-03-16 14:28:54

标签: c# arrays combinations

我正在尝试遍历数组并获得所有可能的组合,但我需要它在三个级别之后停止。例如:

String[] arr = ["Service1", "Service2", "Service3", "Service4"];

阵列中可能有四个以上,但是从这个例子中我希望能够生成以下组合:

Service1, Service2, Serivce3
Service1, Service2, Serivce4
Service1, Service3, Serivce2
Service1, Service3, Serivce4
Service1, Service4, Serivce2
Service1, Service4, Serivce3

Service2, Service1, Serivce3
Service2, Service1, Serivce4
Service2, Service3, Serivce1
Service2, Service3, Serivce4
Service2, Service4, Serivce3
Service2, Service4, Serivce1

Service3, Service1, Serivce2
Service3, Service1, Serivce4
Service3, Service2, Serivce1
Service3, Service2, Serivce4
Service3, Service4, Serivce2
Service3, Service4, Serivce1

Service4, Service2, Serivce3
Service4, Service2, Serivce1
Service4, Service3, Serivce2
Service4, Service3, Serivce1
Service4, Service1, Serivce2
Service4, Service1, Serivce3

到目前为止,我所尝试和研究过的并没有给我这些结果,我非常感谢您提供的任何帮助。

3 个答案:

答案 0 :(得分:1)

您可以使用this library from CodeProject并使用此示例中的Combination类:

char[] inputSet = { 'A', 'B', 'C', 'D' };

var combinations = new Combinations<char>(inputSet, 3);
var cformat = "Combinations of {{A B C D}} choose 3: size = {0}";
Console.WriteLine(String.Format(cformat, combinations.Count));

foreach(var combination in combinations)
{
    Console.WriteLine(String.Join(", ", combination);
}

答案 1 :(得分:0)

巧合的是,我昨天写了一个程序作为编码挑战finds all permutations of a string with a given length.请注意我删除重复项,例如&#34;弹出&#34;有3个! = 6个字母的安排,但是&#39; p&#39;重复两次并且难以区分,因此3!/ 2 = 3(即&#34; opp&#34;,&#34; pop&#34;,&#34; ppo&#34;)。

static HashSet<string> outputSet = new HashSet<string>();

        // this function will find all the strings of length k you can make from a set of letters N
        // e.g. "pop" --> pop, ppo, opp
        static void permuteSetLength(string prefix, string suffix, int length)
        {
            if (length == 0)
            {
                outputSet.Add(prefix);
                return;
            }

            // use dictionary to remove duplicate prefixes, to avoid permuting the same thing again
            Dictionary<string, string> newPrefixesAndSuffixes = new Dictionary<string, string>();
            // otherwise, calculate our new prefixes by adding each letter of suffix to the prefix, and decrementing length by 1
            for (int i = 0; i < suffix.Length; i++)
            {
                if (!newPrefixesAndSuffixes.ContainsKey(prefix + suffix[i])) // new key
                {
                    // remove ith character from suffix and add it to prefix 
                    permuteSetLength(prefix + suffix[i], suffix.Substring(0,i) + suffix.Substring(i+1), length - 1);
                }

            }
        }

这应该是一个很好的起点。我确定你可以看到找到一个字符串(即字符数组)的排列和一个字符串数组的排列之间的联系。

像这样调用代码:

permuteSetLength("", "abcd", 3);
string[] outputArray = new string[outputSet.Count];
outputSet.CopyTo(outputArray);
Console.WriteLine(String.Join(",", outputArray));

打印出以下内容:

  

abc,abd,acb,acd,adb,adc,bac,bad,bca,bcd,bda,bdc,cab,cad,cba,cbd,cda,cdb,dab,dac,dba,dbc,dca,dcb

24的计数,即4 * 3 * 2 = 24,与预期完全一样。现在应该很容易将每个字符映射到字符串,但我建议改为修改方法本身。

答案 2 :(得分:0)

这是另一种解决方案:

var strings = new[] { "a", "b", "c", "d" };
var combinations = (
from s1 in strings
from s2 in strings.Where(s => s != s1)
from s3 in strings.Where(s => s != s2 && s != s1)
select new { s1, s2, s3 }).Distinct();

foreach (var c in combinations)
{
    Console.WriteLine($"{c.s1}{c.s2}{c.s3}");
}

可能代码可以更加精确,但它可以工作。

希望这会有所帮助。