由于这个链接的问题标记为c#,所以我添加了这个包含c#代码的答案。
如果嵌套列表的数量已知,您必须一遍又一遍地使用SelectMany()
将所有嵌套的列表展开到字符序列中,然后从该序列制作字符串。
List<List<List<string>>> nestedList = new List<List<List<string>>>();
var result = new string(nestedList.SelectMany(x => x).SelectMany(x => x).SelectMany(x => x).ToArray());
using Microsoft.CSharp.RuntimeBinder;
//...
private static string ConcatAll<T>(T nestedList) where T : IList
{
dynamic templist = nestedList;
try
{
while (true)
{
List<dynamic> inner = new List<dynamic>(templist).SelectMany<dynamic, dynamic>(x => x).ToList();
templist = inner;
}
}
catch (RuntimeBinderException)
{
List<object> l = templist;
return l.Aggregate("", (a, b) => a + b);
}
}
这是一个测试
private static void Main(string[] args)
{
List<List<List<string>>> nestedList = new List<List<List<string>>>
{
new List<List<string>> {new List<string> {"Hello "}, new List<string> {"World "}},
new List<List<string>> {new List<string> {"Goodbye "}, new List<string> {"World ", "End "}}
};
Console.WriteLine(ConcatAll(nestedList));
}
输出:
Hello World Goodbye World End
更新:
经过一些尝试,我最终完成了这个实现。也许可以不需要 try-catch 块。
private static string ConcatAll<T>(T nestedList) where T : IList
{
dynamic templist = nestedList;
while (templist.Count > 0 && !(templist[0] is char?))
{
List<dynamic> inner = new List<dynamic>(templist).SelectMany<dynamic, dynamic>(x =>
{
var s = x as string;
if (s != null)
{
return s.Cast<dynamic>();
}
return x;
}).ToList();
templist = inner;
}
return new string(((List<object>) templist).Cast<char>().ToArray());
}
static IEnumerable<string> Flatten(IEnumerable enumerable)
{
foreach (object el in enumerable)
{
if (enumerable is IEnumerable<string>)
{
yield return (string) el;
}
else
{
IEnumerable candidate = el as IEnumerable;
if (candidate != null)
{
foreach (string nested in Flatten(candidate))
{
yield return nested;
}
}
}
}
}
使用这种方法,您可以将所有字符串连接起来:
List<List<List<string>>> nestedList = new List<List<List<string>>>
{
new List<List<string>> {new List<string> {"Hello "}, new List<string> {"World "}},
new List<List<string>> {new List<string> {"Goodbye "}, new List<string> {"World ", "End "}}
};
Console.WriteLine(String.Join(" ",Flatten(nestedList)));
这个想法来自于这篇帖子。
else
子句中的空值检查是否必要?如果是,请解释一下原因。 - Kapol
.SelectMany
来展开它,然后使用你找到的答案。 - Robert McKee