cod*_*nix 2 .net c# linq collections
我必须遵循以下代码:
List<Obj> coll = new List<Obj>();
if (cond1) coll.Add(new Obj { /*...*/ });
if (cond2) coll.Add(new Obj { /*...*/ });
if (cond3) coll.Add(new Obj { /*...*/ });
Run Code Online (Sandbox Code Playgroud)
有没有办法使用LINQ或集合初始化器?
编辑:
我想在这里使用集合初始化器的原因是因为我有一个对象树,我用initialiers和LINQ完全初始化.这个地方是唯一一个不遵循这一原则的地方.
var myobj = new MyBigObj
{
Prop1 = from .. select ..,
Prop2 = from .. select ..,
...
Prop3 = new MySmallerObj
{
PropSmall1 = from .. select ..,
PropSmall2 = from .. select ..,
...
}
};
Run Code Online (Sandbox Code Playgroud)
而现在这根本不适合我的计划:
List<Obj> coll = new List<Obj>();
if (cond1) coll.Add(new Obj { /*...*/ });
if (cond2) coll.Add(new Obj { /*...*/ });
if (cond3) coll.Add(new Obj { /*...*/ });
myobj.Prop4 = coll;
Run Code Online (Sandbox Code Playgroud)
当然,我可以把这个代码放在一个单独的函数,返回IEnumerable并调用.. :)
EDIT2:
看起来我必须编写一些扩展方法,我会称之为:
new Obj[0]
.ConditionalConcat(cond1, x=>new Obj { /*...*/ })
.ConditionalConcat(cond2, x=>new Obj { /*...*/ })
.ConditionalConcat(cond3, x=>new Obj { /*...*/ })
Run Code Online (Sandbox Code Playgroud)
一个相当可怕的选择:
var conditions = new[] { cond1, cond2, cond3 };
var values = new[] { new Obj {...}, // First value
new Obj {...}, // Second value
new Obj { ...} // Third value
};
var list = conditions.Zip(values, (condition, value) => new { condition, value })
.Where(pair => pair.condition)
.Select(pair => pair.value)
.ToList();
Run Code Online (Sandbox Code Playgroud)
它并不比原始代码简单得多;)(并且它也无条件地创建所有值 - 它只是有条件地将它们包含在集合中.)
编辑:一种替代方案,它只在需要时构造值:
var conditions = new[] { cond1, cond2, cond3 };
var valueProviders = new Func<Obj>[] {
() => new Obj {...}, // First value
() => new Obj {...}, // Second value
() => new Obj { ...} // Third value
};
var list = conditions.Zip(valueProviders,
(condition, provider) => new { condition, provider })
.Where(pair => pair.condition)
.Select(pair => pair.provider())
.ToList();
Run Code Online (Sandbox Code Playgroud)
编辑:根据您的语法,这是一个相当容易的选择:
new List<Obj>()
.ConditionalConcat(cond1, x=>new Obj { /*...*/ })
.ConditionalConcat(cond2, x=>new Obj { /*...*/ })
.ConditionalConcat(cond3, x=>new Obj { /*...*/ })
Run Code Online (Sandbox Code Playgroud)
使用扩展方法:
public static List<T> ConditionalConcat<T>(this List<T> source,
bool condition,
Func<T> provider)
{
if (condition)
{
source.Add(provider);
}
return source;
}
Run Code Online (Sandbox Code Playgroud)