我希望Balance
从当前月份开始计算未来12个月的预测,如果该月份Balance
为空,它将从最近Month
的Balance
值得到大于0的值.
void Main()
{
var firstDayMonth = new DateTime(DateTime.Now.Year, DateTime.Now.Month, 1);
var months = Enumerable.Range(0, 12)
.Select(m => new
{
Month = firstDayMonth.AddMonths(m)
});
List<SomeDate> SomeDates = new List<SomeDate>()
{
new SomeDate { Id = 1, Month = firstDayMonth.AddMonths(0), Balance = 1m },
new SomeDate { Id = 2, Month = firstDayMonth.AddMonths(2), Balance = 1m },
new SomeDate { Id = 3, Month = firstDayMonth.AddMonths(1), Balance = 6m },
new SomeDate { Id = 4, Month = firstDayMonth.AddMonths(2), Balance = 5m },
new SomeDate { Id = 5, Month = firstDayMonth.AddMonths(3), Balance = 3m },
new SomeDate { Id = 6, Month = firstDayMonth.AddMonths(2), Balance = 2m },
new SomeDate { Id = 7, Month = firstDayMonth.AddMonths(3), Balance = 4m },
new SomeDate { Id = 8, Month = firstDayMonth.AddMonths(1), Balance = 2m },
new SomeDate { Id = 9, Month = firstDayMonth.AddMonths(3), Balance = 3m },
};
var groupedMonths = SomeDates
.GroupBy(c => c.Month)
.Select(g => new
{
Month = g.Key,
SumBalance = g.Sum(s => s.Balance)
});
var Projected12MonthsBalance = from m in months
join gm in groupedMonths on m.Month equals gm.Month into mm
from gm in mm.DefaultIfEmpty()
select new
{
Month = m.Month,
Balance = gm == null ? 0m : gm.SumBalance
};
Console.WriteLine(Projected12MonthsBalance);
}
// Define other methods and classes here
public class SomeDate
{
public int Id { get; set; }
public DateTime Month { get; set; }
public decimal Balance { get; set; }
}
Run Code Online (Sandbox Code Playgroud)
这是我到目前为止所尝试的.这将导致:
Month | Balance
7/1/2015 | 1
8/1/2015 | 8
9/1/2015 | 8
10/1/2015 | 10
11/1/2015 | 0
...
6/1/2016 | 0
Run Code Online (Sandbox Code Playgroud)
有可能得到一个像这样的结果:
Month | Balance
7/1/2015 | 1
8/1/2015 | 8
9/1/2015 | 8
10/1/2015 | 10
11/1/2015 | 10 <-- gets the value from the nearest month with Balance greater than 0
...
6/1/2016 | 10 <-- gets the value from the nearest month with Balance greater than 0
Run Code Online (Sandbox Code Playgroud)
我似乎无法完成查询所以我现在设置了零.任何帮助将非常感激.谢谢!
对于LINQ,恕我直言,这似乎相当容易.
首先,我修改了months
以避免使用匿名类型(因为它没有必要).
var months =
Enumerable
.Range(0, 12)
.Select(m => firstDayMonth.AddMonths(m));
Run Code Online (Sandbox Code Playgroud)
然后我按月创建了余额数据的查找:
var lookup =
SomeDates
.ToLookup(x => x.Month, x => x.Balance);
Run Code Online (Sandbox Code Playgroud)
查找更好的是分组或字典,您可以询问查找的值,其中密钥不存在并返回空列表.它减少了在检索值之前检查密钥是否存在的需要.
我将用于.Aggregate(...)
构建最终列表,因此我需要accumulator
为聚合函数创建初始化:
var accumulator =
months
.Take(1)
.Select(m => new { Month = m, Balance = lookup[m].Sum() })
.ToList();
Run Code Online (Sandbox Code Playgroud)
这只是计算第一个月余额并将其添加到列表中的结果.这是一个匿名类型的列表.
现在最后的查询非常简单:
var Projected12MonthsBalance =
months
.Skip(1)
.Aggregate(
accumulator,
(a, m) =>
{
var b = lookup[m].Sum();
b = b == 0 ? a.Last().Balance : b;
a.Add(new { Month = m, Balance = b });
return a;
});
Run Code Online (Sandbox Code Playgroud)
此查询会跳过第一个月,因为我们已将其添加到累加器中.lamdba函数现在只计算每个月的余额,如果它为零,则取代前一个月的余额.
这是我得到的结果:
归档时间: |
|
查看次数: |
466 次 |
最近记录: |