Reputation: 3284
How can I do this in a more readable way?
foreach (var actual in actualPositions)
{
foreach (var projection in projections)
{
var position = Create(book, actual, projection);
position.TargetNett = projection.DailyProjectedNet.ToString();
yield return position;
}
}
Upvotes: 0
Views: 562
Reputation: 569
In this case Linq provides less readability. You can move the second foreach statement in a seperate method and then use Linq
return from actual in actualPositions
select GetBookPositionList(actual);
new method:
private List<BookPosition> GetBookPositionList(ActualPosition actual)
{
foreach (var projection in projections)
{
var position = Create(book, actual, projection);
position.TargetNett = projection.DailyProjectedNet.ToString();
yield return position;
}
}
Upvotes: 0
Reputation: 16981
just for fun
return
(
from actual in actualProjections
from projection in projections
select new {actual, projection}
).Select(pair =>
{
var position = Create(book, pair.actual, pair.projection);
position.TargetNett = pair.projection.DailyProjectedNet.ToString();
return position;
}
);
Upvotes: 0
Reputation: 3892
One option you can do is to implement your own cross join, and enumerate over that. However, it's still not very pretty:
actualPositions.SelectMany(actual => projections.Select(project => new { actual, project }))
However, if you're using the .NET 4.0 or higher, you can implement a cross join extension method using Tuples (default) or your own custom selector:
public static IEnumerable<Tuple<T1, T2>> CrossJoin<T1, T2>(this IEnumerable<T1> source, IEnumerable<T2> toJoin)
{
return source.CrossJoin(toJoin, Tuple.Create<T1, T2>);
}
public static IEnumerable<T3> CrossJoin<T1, T2, T3>(this IEnumerable<T1> source, IEnumerable<T2> toJoin, Func<T1, T2, T3> selector)
{
return source.SelectMany(tFirst => toJoin.Select(tSecond => selector(tFirst, tSecond)));
}
And then this can be used a lot easier:
foreach(var pair in actualPositions.CrossJoin(projections))
{
var position = Create(book, pair.Item1, pair.Item2);
position.TargetNett = pair.Item2.DailyProjectedNet.ToString();
yield return position;
}
// OR
return actionPositions.CrossJoin(projections, (actual, project) => { /*Code in foreach loop above here, without the "yield". */ });
Upvotes: 2
Reputation: 16981
return
from actual in actualProjections
from projection in projections
select Create(book, actual, projection)
.With_TargetNett(projection.DailyProjectedNet.ToString());
where With_TargetNett is extension
static Position With_TargetNett(this Position position, string targetNett)
{
position.TargetNett = targetNett;
return position;
}
Upvotes: 2
Reputation: 241601
You want to simplify that? Why? It's simple and readable and understandable. You can come up with all sorts of gobbledygook that is harder to read but sure looks cooler. Do not! Resist the urge to be fancy.
Upvotes: 12