Таким образом, вы застряли с последовательностью объектов, где каждый объект имеет свойство Date типа string в формате yyyyMM.и вы хотите извлечь из него некоторые данные.
Ваш формат даты не зависит от языка.Не имеет значения, является ли ваш компьютер британским или китайским.Свойство Date всегда будет иметь формат yyyyMM.
Это позволяет довольно легко преобразовать его в формат DateTime, что упрощает доступ к году и месяцу.
const string dateTimeFormat = "yyyyMM";
CultureInfo provider = CultureInfo.InvariantCulture;
var dateList = ... // your original list of items with the string Date property
var itemsWithYearMonth = dateList.Select(item => new
{
DateTime = DateTime.ParseExact(item, dateTimeFormat, provider)
... // select other items you need for your bar chart
});
Сейчасс учетом StartYear / Month, NrOfYears и NrOfMonths, которые вы хотите сгруппировать dateTimeItems в группы одного и того же месяца.
Например, начиная с 2018-11, я хочу группы с четырьмя месяцами в течение трех лет подряд (да, да, я знаю, что в вашем первоначальном запросе это было всего 3 месяца, 2 года, но зачем ограничиваться этим, давайте сделаем ваш код многократно используемым):
group 1: 2018-11, 2019-11, 2020-11, 2021-11
group 2: 2018-12, 2019-12, 2020-12, 2021-12
group 3: 2019-01, 2020-01, 2021-01, 2022-01
Бонусные баллы: мы 'Пройдем границу года!
Итак, введите:
var itemsWithYearMonth = ... // see above
int startYear = ...
int startMonth = ...
int nrOfMonths = ...
int nrOfYears = ...
Мы создадим группы предметов с одинаковыми месяцами.Мы не хотим все месяцы года, мы хотим только несколько месяцев.Если мы хотим, чтобы 3 месяца начинались с 11 месяца, нам нужно сохранить группы с месяцами 11, 12, 1.
var desiredMonths = Enumerable.Range(startMonth, nrOfMonths) // example: 11, 12, 13
.Select(monthNr => 1 + ((monthNr-1) % 12)); // 11, 12, 1
Исходя из вашего ввода, мы не хотим все месяцы, нам нужны толькогод / месяц больше, чем начальный месяц.
DateTime startMonth = new DateTime(startYear, startMonth, 1);
Самый простой способ - сохранить только источник ввода элементов с датой, равной или большей, чем startMonth, и взять только первые элементы NumberOfYears из каждой группы.Таким образом, вы получите правильное количество элементов, если вы пройдете границу года, как я делал в моем примере.
var result = itemsWithYearMonth
// keep only the items newer than startMonth
.Where(item => item.DateTime >= startMonth)
// group by same month:
.GroupBy(item => item.DateTime.Month,
(month, itemsWithThisMonth) => new
{
Month = month, // in my example: 11, 12, 1, ...
// in every group: take the first nrOfYears items:
Items = itemsWithThisMonth
// order by ascending year
.OrderBy(itemWithThisMonth => itemWithThisMonth.Year)
// no need to order by Month, all Months are equal in this group
.Take(nrOfYears)
.ToList(),
})
// keep only the desired months:
.Select(group => desiredMonth.Contains(group.Month));
Итак, теперь у вас есть группы:
group of month 11, with data of years 2018, 2019, 2020, 2021
group of month 12, with data of years 2018, 2019, 2020, 2021
group of month 01, with data of years 2019, 2020, 2021, 2022