使用LINQ简化foreach循环(在每次迭代中选择两个对象)

Pom*_*air 7 c# linq

给定以下接口和两个类:

public interface IMyObj
{
    int Id { get; set; }
}

public class MyObj1 : IMyObj
{
    public MyObj1(int id) { Id = id; }
    public int Id { get; set; }
    public override string ToString() => $"{GetType().Name} : {Id}";
}

public class MyObj2 : IMyObj
{
    public MyObj2(int id) { Id = id; }
    public int Id { get; set; }
    public override string ToString() => $"{GetType().Name} : {Id}";
}
Run Code Online (Sandbox Code Playgroud)

并给出以下使用它们的逻辑:

var numbers = new[] { 1, 5, 11, 17 };

var list = new List<IMyObj>();

foreach (var n in numbers)
{
    // I'd like to simplify this part with LINQ...
    list.Add(new MyObj1(n));
    list.Add(new MyObj2(n));
}

Assert.AreEqual(8, list.Count);
Run Code Online (Sandbox Code Playgroud)

测试通过了,我list完全看到了我想要的内容 - 每个数字有两个对象实例:

Count = 8
  [0]: {MyObj1 : 1}
  [1]: {MyObj2 : 1}
  [2]: {MyObj1 : 5}
  [3]: {MyObj2 : 5}
  [4]: {MyObj1 : 11}
  [5]: {MyObj2 : 11}
  [6]: {MyObj1 : 17}
  [7]: {MyObj2 : 17}
Run Code Online (Sandbox Code Playgroud)

我的问题是,如何foreach使用LINQ 简化循环逻辑?我想也许有一种优雅的方式与SelectMany操作员做同样的事情,但我无法产生相同的输出.

Jon*_*eet 15

SelectMany 确实是你想要的:

var list = numbers.SelectMany(n => new IMyObj[] { new MyObj1(n), new MyObj2(n) })
                  .ToList();
Run Code Online (Sandbox Code Playgroud)

换句话说,对于每个数字,创建一个双元素数组,然后使用to展平SelectMany.

new IMyObj[]部分是必需的,而不仅仅是new[]因为类型推断无法分辨出您想要的数组类型.如果类型相同,您可以执行以下操作:

var list = numbers.SelectMany(n => new[] { new MyObj(n), new MyObj(n) })
                  .ToList();
Run Code Online (Sandbox Code Playgroud)