我对C#的新手很友善,并且正在某种日期范围内的逻辑上工作(假设一个月,即2018-06-01至2018-06-30)。
我有一个次要日期范围的列表:
STARTDATE ENDDATE
2018-06-04 2018-06-06
2018-06-11 2018-06-14
2018-06-17 2018-06-20
让我们假设需要将上述日期从原始的一个月范围2018-06-01 to 2018-06-30
中屏蔽。因此,作为输出,我需要一些逻辑以返回未被阻止的可用日期范围!
所以输出需要像:
STARTDATE ENDDATE
2018-06-01 2018-06-03
2018-06-07 2018-06-10
2018-06-15 2018-06-16
2018-06-18 2018-06-19
2018-06-21 2018-06-30
因此,我需要一些C#专家指南以了解如何实现此目标。我不是在问代码,但是也许如果有人写了类似的逻辑,那么请分享这个想法或提供任何参考。
我主要关心的是我应该使用列表,字典,数据表还是其他东西?
答案 0 :(得分:0)
您可以使用Linq,但FilteredList = BiggerList.Except(SmallerList).ToList()
答案 1 :(得分:0)
我会列出排除日期的列表,列出允许日期的列表。 然后如@PiJei所说,只需按排除日期过滤月份列表即可。
答案 2 :(得分:0)
我从皮杰的建议中借来了。然后使用方法扩展该范围以获取起始范围的日期,并使用一种方法构建日期的最终范围。
首先,让我们构建示例数据: var month = EveryDay(start,end);
var start1 = new DateTime(2018, 06, 04);
var end1 = new DateTime(2018, 06, 06);
var sub1 = EachDay(start1, end1);
var start2 = new DateTime(2018, 06, 11);
var end2 = new DateTime(2018, 06, 14);
var sub2 = EachDay(start2, end2);
var start3 = new DateTime(2018, 06, 17);
var end3 = new DateTime(2018, 06, 20);
var sub3 = EachDay(start3, end3);
为此,我使用的是从this answer借来的EachDay
方法。
public static IEnumerable<DateTime> EachDay(DateTime from, DateTime thru)
{
for (var day = from.Date; day.Date <= thru.Date; day = day.AddDays(1))
yield return day;
}
要获得我称为withoutExcluded
的最终列表,我只需运行以下命令即可:
var withoutExcluded = month.Except(sub1).Except(sub2).Except(sub3);
最后,我将使用此列表并构建结果范围。
var ranges = GetRanges(withoutExcluded);
为此,我创建了一个简单的帮助器Range
类和GetRanges
方法来分析日期,如果它们是连续的日期,则会建立一个单一范围。
助手Range
类:
public class Range
{
public DateTime Start { get; set; }
public DateTime End { get; set; }
}
助手GetRanges
方法:
public static IEnumerable<Range> GetRanges(IEnumerable<DateTime> dates)
{
var start = dates.First();
var end = dates.First();
var prev = dates.First();
var next = DateTime.Now;
foreach(var d in dates.Skip(1))
{
next = d;
var diff = next - prev;
if (diff.TotalDays > 1)
{
yield return new Range { Start = start, End = end };
start = d;
}
prev = d;
end = d;
}
yield return new Range { Start = start, End = end };
}
最终结果如下:
range: 01/06/2018 00:00:00 03/06/2018 00:00:00
range: 07/06/2018 00:00:00 10/06/2018 00:00:00
range: 15/06/2018 00:00:00 16/06/2018 00:00:00
range: 21/06/2018 00:00:00 30/06/2018 00:00:00
我将给您适当的结果格式。但是逻辑是正确的。 以防万一您忘了下面粘贴整个解决方案时发生的情况:
class Program
{
static void Main(string[] args)
{
var start = new DateTime(2018, 06, 01);
var end = new DateTime(2018, 06, 30);
var month = EachDay(start, end);
var start1 = new DateTime(2018, 06, 04);
var end1 = new DateTime(2018, 06, 06);
var sub1 = EachDay(start1, end1);
var start2 = new DateTime(2018, 06, 11);
var end2 = new DateTime(2018, 06, 14);
var sub2 = EachDay(start2, end2);
var start3 = new DateTime(2018, 06, 17);
var end3 = new DateTime(2018, 06, 20);
var sub3 = EachDay(start3, end3);
var withoutExcluded = month.Except(sub1).Except(sub2).Except(sub3);
var ranges = GetRanges(withoutExcluded);
foreach (var r in ranges)
{
Console.WriteLine($"range: {r.Start} {r.End}");
}
}
//https://stackoverflow.com/a/1847601/3330348
public static IEnumerable<DateTime> EachDay(DateTime from, DateTime thru)
{
for (var day = from.Date; day.Date <= thru.Date; day = day.AddDays(1))
yield return day;
}
public static IEnumerable<Range> GetRanges(IEnumerable<DateTime> dates)
{
var start = dates.First();
var end = dates.First();
var prev = dates.First();
var next = DateTime.Now;
foreach (var d in dates.Skip(1))
{
next = d;
var diff = next - prev;
if (diff.TotalDays > 1)
{
yield return new Range { Start = start, End = end };
start = d;
}
prev = d;
end = d;
}
yield return new Range { Start = start, End = end };
}
public class Range
{
public DateTime Start { get; set; }
public DateTime End { get; set; }
}
}