具有n^n可能性的C#字符串串联

具有n^n可能性的C#字符串串联,c#,string,arraylist,concatenation,C#,String,Arraylist,Concatenation,我有一个字符串[]数组的通用列表,我需要用这些数组中所有可能的项目组合构建一个字符串列表。我很难想出最好的方法 因此: 列表mylist=新列表;//然后我从数据库中填充它 mylist的内容如下所示: Buildings ||| Facilities ||| Fields ||| Files; Groups; Entity; ||| Controllers; FX; Steam; 管道“| | |”分隔mylist中的每个字符串数组,分号是分隔符,表示每个数组中的项。因此,数组的最小长度为1

我有一个字符串[]数组的通用列表,我需要用这些数组中所有可能的项目组合构建一个字符串列表。我很难想出最好的方法

因此: 列表mylist=新列表;//然后我从数据库中填充它

mylist的内容如下所示:

Buildings ||| Facilities ||| Fields ||| Files; Groups; Entity; ||| Controllers; FX; Steam;
管道“| | |”分隔mylist中的每个字符串数组,分号是分隔符,表示每个数组中的项。因此,数组的最小长度为1,最大长度为N。我需要构建一个由连字符“--”分隔的字符串列表,其中包含上述所有可能的组合,但保持它们在列表中的顺序。因此,以上述内容为例,我将列出以下字符串列表:

Buildings---Facilities---fields---Files---Controllers
Buildings---Facilities---fields---Groups---Controllers
Buildings---Facilities---fields---Entity---Controllers

Buildings---Facilities---fields---Files---Fx
Buildings---Facilities---fields---Groups---Fx
Buildings---Facilities---fields---Entity---Fx

Buildings---Facilities---fields---Files---Steam
Buildings---Facilities---fields---Groups---Steam
Buildings---Facilities---fields---Entity---Steam
如果列表中的第三个数组有2个项目,而不是1个(“字段”)——那么我们将有一个包含18个字符串的列表,而不是9个(3x2)

我尝试使用for循环,知道哪个数组的长度最大,并循环遍历每个列表项,但我就是无法让它工作。睡在上面并没有真正的帮助


有人吗?

让我们制作以下内容:

Buildings---Facilities---fields---Files---Controllers
Buildings---Facilities---fields---Files---Fx
Buildings---Facilities---fields---Files---Steam

Buildings---Facilities---fields---Groups---Controllers
Buildings---Facilities---fields---Groups---Fx
Buildings---Facilities---fields---Groups---Steam

Buildings---Facilities---fields---Entity---Controllers
Buildings---Facilities---fields---Entity---Fx
Buildings---Facilities---fields---Entity---Steam
首先,假设数据库中的数据采用以下格式:

List<List<string>> dataFromDb;
从数据库中列出数据;
如果某些内部集合只有一个值,这并不重要。那么,像这样的事情应该会起作用:

void ConcatString(string prefix, int index, List<List<string>> collection, List<string> output)
{
    if(index == collection.Count)
    {
        output.Add(prefix);
        return;
    }
    var subCollection = collection[index];
    foreach(var str in subCollection)
    {
        string newPrefix = ((prefix.Length > 0)? "---" : "") + str;
        ConcatString(newPrefix, index+1, collection, output);
    }
}
void ConcatString(字符串前缀、int索引、列表集合、列表输出)
{
if(index==collection.Count)
{
输出.添加(前缀);
返回;
}
var subCollection=集合[索引];
foreach(子集合中的var str)
{
字符串newPrefix=((prefix.Length>0)?“-”:”)+str;
ConcatString(newPrefix,index+1,collection,output);
}
}
被称为:

var output = new List<string>();
ConcatString("", 0, dataFromDb, output);
var输出=新列表();
ConcatString(“”,0,dataFromDb,output);

您要查找的列表应该在输出中。现在,请注意,我还没有运行这个(见鬼,我甚至还没有编译这个),所以您需要调试它,但它至少应该让您朝着正确的方向前进。

让我们来制作这个:

Buildings---Facilities---fields---Files---Controllers
Buildings---Facilities---fields---Files---Fx
Buildings---Facilities---fields---Files---Steam

Buildings---Facilities---fields---Groups---Controllers
Buildings---Facilities---fields---Groups---Fx
Buildings---Facilities---fields---Groups---Steam

Buildings---Facilities---fields---Entity---Controllers
Buildings---Facilities---fields---Entity---Fx
Buildings---Facilities---fields---Entity---Steam
首先,假设数据库中的数据采用以下格式:

List<List<string>> dataFromDb;
从数据库中列出数据;
如果某些内部集合只有一个值,这并不重要。那么,像这样的事情应该会起作用:

void ConcatString(string prefix, int index, List<List<string>> collection, List<string> output)
{
    if(index == collection.Count)
    {
        output.Add(prefix);
        return;
    }
    var subCollection = collection[index];
    foreach(var str in subCollection)
    {
        string newPrefix = ((prefix.Length > 0)? "---" : "") + str;
        ConcatString(newPrefix, index+1, collection, output);
    }
}
void ConcatString(字符串前缀、int索引、列表集合、列表输出)
{
if(index==collection.Count)
{
输出.添加(前缀);
返回;
}
var subCollection=集合[索引];
foreach(子集合中的var str)
{
字符串newPrefix=((prefix.Length>0)?“-”:”)+str;
ConcatString(newPrefix,index+1,collection,output);
}
}
被称为:

var output = new List<string>();
ConcatString("", 0, dataFromDb, output);
var输出=新列表();
ConcatString(“”,0,dataFromDb,output);
您要查找的列表应该在输出中。现在,请注意,我还没有运行这个(见鬼,我甚至还没有编译这个),所以您需要调试它,但它至少应该让您朝着正确的方向前进。

我会尝试递归:

private void button1_Click(object sender, EventArgs e)
        {
            List<string[]> strs = new List<string[]>();
            strs.Add(new string[] {"Buildings"});
            strs.Add(new string[] {"Facilities"});
            strs.Add(new string[] {"Fields"});
            strs.Add(new string[] {"Files", "Groups", "Entity"});
            strs.Add(new string[] {"Controllers", "FX", "Steam"});
            List<string> list = AddStringsToList(strs, 0);

        }

        List<string> AddStringsToList(List<string[]> list, int level)
        {
            List<string> listOfStrings = new List<string>();
            if (level == list.Count - 1)
            {
                foreach (string s in list[level])
                {
                    listOfStrings.Add(s);
                }
            }
            else if(level<list.Count-1)
            {
                List<string> list1 = AddStringsToList(list, level + 1);
                foreach (string s in list[level])
                {
                    foreach(string s1 in list1)
                        listOfStrings.Add(s + "---" + s1);
                }
            }
            return listOfStrings;
        }
private void按钮1\u单击(对象发送者,事件参数e)
{
列表strs=新列表();
添加(新字符串[]{“建筑物”});
添加(新字符串[]{“设施”});
添加(新字符串[]{“字段”});
添加(新字符串[]{“文件”、“组”、“实体”});
添加(新字符串[]{“Controllers”、“FX”、“Steam”});
列表=AddStringsToList(strs,0);
}
列表AddStringsToList(列表,整数级)
{
List listOfStrings=新列表();
if(level==list.Count-1)
{
foreach(列表[级别]中的字符串s)
{
listOfStrings.Add(s);
}
}
否则,如果(级别我将尝试递归:

private void button1_Click(object sender, EventArgs e)
        {
            List<string[]> strs = new List<string[]>();
            strs.Add(new string[] {"Buildings"});
            strs.Add(new string[] {"Facilities"});
            strs.Add(new string[] {"Fields"});
            strs.Add(new string[] {"Files", "Groups", "Entity"});
            strs.Add(new string[] {"Controllers", "FX", "Steam"});
            List<string> list = AddStringsToList(strs, 0);

        }

        List<string> AddStringsToList(List<string[]> list, int level)
        {
            List<string> listOfStrings = new List<string>();
            if (level == list.Count - 1)
            {
                foreach (string s in list[level])
                {
                    listOfStrings.Add(s);
                }
            }
            else if(level<list.Count-1)
            {
                List<string> list1 = AddStringsToList(list, level + 1);
                foreach (string s in list[level])
                {
                    foreach(string s1 in list1)
                        listOfStrings.Add(s + "---" + s1);
                }
            }
            return listOfStrings;
        }
private void按钮1\u单击(对象发送者,事件参数e)
{
列表strs=新列表();
添加(新字符串[]{“建筑物”});
添加(新字符串[]{“设施”});
添加(新字符串[]{“字段”});
添加(新字符串[]{“文件”、“组”、“实体”});
添加(新字符串[]{“Controllers”、“FX”、“Steam”});
列表=AddStringsToList(strs,0);
}
列表AddStringsToList(列表,整数级)
{
List listOfStrings=新列表();
if(level==list.Count-1)
{
foreach(列表[级别]中的字符串s)
{
listOfStrings.Add(s);
}
}

否则,如果(级别我认为这可能符合您的要求:

static IEnumerable<string> Combinations(IEnumerable<IEnumerable<string>> items)
{
    return items.Aggregate((outs, ins) => outs.SelectMany(o => ins.Select(i => o + "---" + i)));
}

我想指出的是,这个解决方案非常有效。它不使用递归,这使得它对于长链的情况特别有效。此外,它会延迟计算结果,如果处理许多结果组合,这将大大提高内存效率(请记住,这些组合可以随链长呈指数增长)。

我认为这可能会满足您的要求:

static IEnumerable<string> Combinations(IEnumerable<IEnumerable<string>> items)
{
    return items.Aggregate((outs, ins) => outs.SelectMany(o => ins.Select(i => o + "---" + i)));
}

我想指出的是,这个解决方案非常有效。它不使用递归,这使得它对于长链的情况特别有效。此外,它会延迟计算结果,如果处理许多结果组合,这将大大提高内存效率(请记住,这些组合可以随链长呈指数增长).

看看这个问题。可能会有帮助:你在询问某些字段的排列。看看这里的一些想法:我正在阅读这些,它们看起来很相关,但我认为我要做的是更复杂一级。我不仅仅是从列表中创建字符串,我是从列表中创建字符串…(?)但至少我现在知道什么叫排列了…看看这个问题。也许会有帮助:你在要求排列