c# - 在 C# 中查找两个大小相等的数组的所有组合集

标签 c# asp.net

我有两个大小始终相等的数组,我想找到这两个数组的所有可能的组合集。

例如:

var names = new [] { "John", "Alex", "Peter", "Eric" };
var letters = new [] { "A", "B", "C", "D" };

我希望结果作为字典列表返回:

var combinationSets = new List<Dictionary<string, string>>
        {
            new Dictionary<string, string>
            { {"John", "A"},
            {"Alex", "B"},
            {"Peter", "C"},
            {"Eric", "D"}},
            new Dictionary<string, string>
            { {"John", "B"},
            {"Alex", "C"},
            {"Peter", "D"},
            {"Eric", "A"}},
            ...
        };

编辑:两个数组中的值都不能在字典中重复,例如:

new Dictionary<string, string>
                { {"John", "A"},
                {"Alex", "A"},
                {"Peter", "C"},
                {"Eric", "D"}}

关于如何解决这个问题有什么建议吗?

编辑: 我认为不能使用笛卡尔积,因为它会返回

var cartesianProduct= new []
{ 
new []{ "John", "A" }, 
new []{ "Alex", "B" },     
new []{ "Peter", "C" }, 
new []{ "John", "D" }, 
new []{ "John", "B" }, 
new []{ "Alex", "C" },     
new []{ "Peter", "D" }, 
new []{ "John", "A" }, 
... 
}

最佳答案

在控制台项目中,将 Program 类设为静态以启用扩展方法。 要在 ASP.NET 中使用它,请创建一个 Main 方法并为其他函数创建一个静态帮助器类。

    static void Main(string[] args)
    {
        var names = new[] { "John", "Alex", "Peter", "Eric" };
        var letters = new[] { "A", "B", "C", "D" };

        var combinationSets = new List<Dictionary<string, string>>();
        foreach (var seq in letters.Permutate(4))
        {
            var dic = new Dictionary<string, string>();
            var vals = seq.ToArray();
            for (int i = 0; i < 4; i++)
            {
                dic.Add(names[i], vals[i]);
            }
            combinationSets.Add(dic);
        }

        foreach (var dic in combinationSets)
        {
            foreach (var p in dic)
            {
                Console.WriteLine(p.Key + ": " + p.Value);
            }
            Console.WriteLine();
        }
        Console.ReadLine();
    }

public static IEnumerable<IEnumerable<T>> Permutate<T>(this IEnumerable<T> elements, int places, bool allowRepeats = false)
{
    foreach (var cur in elements)
    {
        if (places == 1) yield return cur.Yield();
        else
        {
            var sub = allowRepeats ? elements : elements.ExceptOne(cur);   
            foreach (var res in sub.Permutate(places - 1, allowRepeats))
            {
                yield return res.Prepend(cur);
            }
        }
    }
}

    public static IEnumerable<T> Yield<T>(this T item)
    {
        yield return item;
    }

    static IEnumerable<T> Prepend<T>(this IEnumerable<T> rest, T first)
    {
        yield return first;
        foreach (var item in rest)
            yield return item;
    }


    public static IEnumerable<T> ExceptOne<T>(this IEnumerable<T> src, T e, int n = 1)
    {
        foreach (var x in src)
            if (!x.Equals(e) || n-- == 0) yield return x;
    }

ps 你确实需要排列而不是组合

关于c# - 在 C# 中查找两个大小相等的数组的所有组合集,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/37698191/

相关文章:

C#.NET : how to pause and resume a program execution on a keypress?

c# - ASP.NET C# 代码中的互斥释放问题

asp.net - LINQ:按匿名类型排序

c# - 如何获取当前用户,以及如何在 MVC5 中使用 User 类?

c# - 创建 C# 属性类/为不同类型返回特定属性的策略是什么?

c# - ASP.Net MVC : A potentially dangerous Request. 从客户端检测到文件值

c# - 是什么导致了这个语法错误? oledb INSERT 语句

c# - 矩形角度属性

asp.net - Elmah 不保存错误

c# - 如何使用 LINQ 从实体加载最后一条记录?