3 回答
TA贡献1821条经验 获得超5个赞
第一步,您必须将数据标准化为一种类型。然后你可以随意迭代它们。因此,首先创建一个方法来将特定点的值展平到任意深度:
public static class Extensions
{
public static IEnumerable<object> FlattenArrays(this IEnumerable source)
{
foreach (var item in source)
{
if (item is IEnumerable inner
&& !(item is string))
{
foreach (var innerItem in inner.FlattenArrays())
{
yield return innerItem;
}
}
yield return item;
}
}
}
现在您可以在顶层进行迭代以获得所有值的单个数组:
// Produces one array => ["1", "2", "3", "4", ...]
var allFlat = schools.FlattenArrays().OfType<string>().ToArray();
或者您可以创建更深一层的单个数组:
foreach (var item in schools)
{
// Produces an array for each top level e.g. ["5", "6", "7", "8"]
var flat = item.FlattenArrays().OfType<string>().ToArray();
}
TA贡献1780条经验 获得超1个赞
根据评论,由于您的内部数组混合了 and 的元素string[],string因此直接在 Linq 中执行此操作可能并非易事。
但是,在辅助函数(我称为Flattener)的帮助下,您可以手动对两种内部类型的处理进行分支,以返回数组中的元素(如果是string[]),或者将单个元素作为可枚举返回,如果不是。SelectMany然后可用于展平内部级别,但您似乎希望保持外级别不展平:
IE
var schools = new [] {
new object[]{new[]{"1","2"}, "3","4"},
new object[]{new[]{"5","6"}, "7","8"},
new object[]{new[]{"9","10","11"}, "12","13"}
};
var result = schools
.Select(s => s.SelectMany(o => Flattener(o)));
它返回一种类型IEnumerable<IEnumerable<string>>
凌乱的拆包位由以下人员完成:
public IEnumerable<string> Flattener(object o)
{
if (o is IEnumerable<string> strings)
{
return strings;
}
if (o is string s)
{
return new[]{s};
}
return new[]{"?"};
}
请注意,上面使用了 C#7 的模式匹配功能。
结果截图由 LinqPad 提供:

TA贡献1829条经验 获得超6个赞
如果你想通过 linq 来做,这里有一个示例
var schools = new[] {
new object[]{new[]{"1","2"}, "3","4"},
new object[]{new[]{"5","6"}, "7","8"},
new object[]{new[]{"9","10","11"}, "12","13"}
};
var result = schools.Select(z => z.SelectMany(y=> y.GetType().IsArray ? (object[])y : new object[] { y }));
- 3 回答
- 0 关注
- 207 浏览
添加回答
举报
