使用C#在货架位置上置换项目

时间:2013-03-18 20:17:41

标签: c# linq permutation combinations

我正在尝试解决排列问题,但我遇到了一些问题。

我有一个“架子”,可以适应各种类型的物品。货架分为多个位置,物品有“尺寸等级”,表示货架本身需要多少空间。

我想生成4个位置最多(1,2,3,4)的所有填充组合,其中包含3个(A,B,C)项,其大小等级为1个位置。 (eg. AAAA, AAAB, AAAC, BBBB, BBBA, ...)

下一步,我需要生成一个带有2个位置的项目的排列。所以我需要使用(A,B,C)生成2个位置,使用(D,E,F) (eg. AAD, AAE, ABD, ...)生成1个位置

我试过使用这个库here,但我的解决方案远非好看(并没有解决第二个例子)

using System;
using System.Linq;
using System.Collections.Generic;
using Facet.Combinatorics;

namespace iCombine
{
    class MainClass
    {
        public static void Main (string[] args)
        {
            char[] inputSet = "ABCABCABCABC".ToCharArray ();
            IList<string> uniques = new List<string>(); 

            var combinations = new Combinations<char> (inputSet, 4, GenerateOption.WithoutRepetition);
            foreach (var combination in combinations) {
                var permutations = new Permutations<char> (combination, GenerateOption.WithoutRepetition);
                foreach (IList<char> permutation in permutations) {     
                    string token = new string (permutation.ToArray(), 0, 4);
                    if (!uniques.Contains(token))
                        uniques.Add(token);
                }
            }                   
        }
    }
}

欢迎任何建议:)

1 个答案:

答案 0 :(得分:3)

这将为您的第一个示例生成所有81个排列:

var items = new List<char>{'A', 'B', 'C'};

var perms = from a in items
            from b in items
            from c in items
            from d in items
            select new string(new char[]{a, b, c, d});

e.g。

AAAA 
AAAB 
AAAC 
AABA 
AABB 
...

这是你的第二个例子的27个排列:

var items = new List<char>{'A', 'B', 'C'};
var items2 = new List<char> {'D', 'E', 'F'};

var perms = from a in items
            from b in items
            from c in items2
            select new string(new char[]{a, b, c});

等效方法语法使用Enumerable.SelectMany将序列的每个元素投影到IEnumerable<T>,并将生成的序列展平为一个序列。

所以上面的查询可以写成:

var items = new List<char> { 'A', 'B', 'C' };
var items2 = new List<char> { 'D', 'E', 'F' };

var perms = items.SelectMany(a => items, (a, b) => new { a, b })
            .SelectMany(t => items2, (t, c) => new string(new[] { t.a, t.b, c }));