Как подсчитать время, прошедшее между двумя элементами в массиве объектов?

#javascript #arrays

#javascript #массивы

Вопрос:

У меня есть массив таких объектов:

 events: 
 [{
   eventInfo: "START_event1",
   timeStamp: "2020-11-29T22:01:53.634041 00:00"
  },
  {
   eventInfo: "END_event1",
   timeStamp: "2020-11-29T22:04:00.634041 00:00"
  },
  {
   eventInfo: "START_event1",
   timeStamp: "2020-11-29T23:00:00.634041 00:00"
  },
  {
   eventInfo: "START_event2",
   timeStamp: "2020-11-29T23:01:53.634041 00:00"
  },
  {
   eventInfo: "END_event1",
   timeStamp: "2020-11-29T23:04:50.634041 00:00"
  },
  {
   eventInfo: "END_event2",
   timeStamp: "2020-11-29T23:24:00.634041 00:00"
  }]
 

Массив будет иметь несколько вхождений события с тем же именем. Я должен вычислить общее время, прошедшее с event1, event2 и так далее.

Проблема в том, что нет другого способа узнать, какие события начинаются и заканчиваются парой, кроме строки EventInfo, имеющей начало или конец в имени. Например, последующие START_event1 и END_event1 должны быть парой, как и START_event2 и END_event2 (хотя между ними есть еще один START_event1).

Конечный результат, который я ищу, — это новый массив, в котором общее время выполнения для каждого имени события.

 [{
event1: totalRuntime
},
{
event2: totalRuntime
},
{
eventN: totalRuntime
}]
 

Комментарии:

1. Что это за тип eventInfo и ему подобные START_event1 ? Это константы или строки?

2. Ваш образец входных данных содержит синтаксические ошибки

3. EventInfo — это строка. Например, «START_make_coffee», «END_make_coffee».

Ответ №1:

Вот начало для анализа вашего массива событий и сопоставления каждого времени начала / окончания.

Хитрость заключается в том, что каждое событие времени «START_» добавляется как элемент таблицы объектов. Когда встречается соответствующее событие времени «END_», оно извлекает исходное время начала из таблицы, вычисляет разницу и добавляет текущую таблицу в другую таблицу.

Возвращаемое значение from parseEventsList — это объект (карта), который имеет общее время выполнения (в миллисекундах) каждого события. Преобразование этого объекта в нужный вам формат — это упражнение, оставшееся для вас.

Пример запуска:

 > totals = parseEventsList(events)
{ event1: 417000, event2: 1327000 }
 
 function parseEventsList(events) {
   var startTimes = {};
   var totals = {};

   for (var i = 0; i < events.length; i  ) {

       let date = new Date(events[i].timeStamp);

       if (events[i].eventInfo.substr(0,6) == "START_") {
          let eventname = events[i].eventInfo.substr(6);
          startTimes[eventname] = date;
       } else if (events[i].eventInfo.substr(0,4) == "END_") {

          let eventname = events[i].eventInfo.substr(4);
          if (startTimes[eventname]) {
             if (totals[eventname] === undefined) {
                 totals[eventname] = 0;
             }
             totals[eventname]  = (date - startTimes[eventname]); 
          } else {
             // error: end event with no matching start event
          }
       }
   }
   return totals;
}

let events =  [{
   eventInfo: "START_event1",
   timeStamp: "2020-11-29T22:01:53.634041 00:00"
  },
  {
   eventInfo: "END_event1",
   timeStamp: "2020-11-29T22:04:00.634041 00:00"
  },
  {
   eventInfo: "START_event1",
   timeStamp: "2020-11-29T23:00:00.634041 00:00"
  },
  {
   eventInfo: "START_event2",
   timeStamp: "2020-11-29T23:01:53.634041 00:00"
  },
  {
   eventInfo: "END_event1",
   timeStamp: "2020-11-29T23:04:50.634041 00:00"
  },
  {
   eventInfo: "END_event2",
   timeStamp: "2020-11-29T23:24:00.634041 00:00"
  }];
  
  let totals = parseEventsList(events);
  
  console.log(totals); 

Ответ №2:

Я предполагаю, что все данные string приведены в вашем примере.

Повторяющиеся события игнорируются

 const events = [{
    eventInfo: "START_event1",
    timeStamp: "2020-11-29T22:01:53.634041 00:00"
  },
  {
    eventInfo: "END_event1",
    timeStamp: "2020-11-29T22:04:00.634041 00:00"
  },
  {
    eventInfo: "START_event1",
    timeStamp: "2020-11-29T23:00:00.634041 00:00"
  },
  {
    eventInfo: "START_event2",
    timeStamp: "2020-11-29T23:01:53.634041 00:00"
  },
  {
    eventInfo: "END_event1",
    timeStamp: "2020-11-29T23:04:50.634041 00:00"
  },
  {
    eventInfo: "END_event2",
    timeStamp: "2020-11-29T23:24:00.634041 00:00"
  }
]

s = []
final = []

events.map(x => {
  var eventId = x.eventInfo.match(/d /)
  if (!s.some(x => x.id == eventId[0] amp;amp; (s.some(c => x.end != null)))) {
    if (x.eventInfo.includes("START")) {
      s.push({
        id: eventId[0],
        start: x.timeStamp,
        end: null
      })
    } else {
      if (s.some(x => x.id == eventId))
        s.find(x => x.id == eventId[0]).end = x.timeStamp
      else
        s.push({
          id: eventId[0],
          start: null,
          end: x.timeStamp
        })
    }
  }
})

s.map(x => {
  var time = (new Date(x.end).getTime()) - (new Date(x.start).getTime())
  final.push({
    ['event'   x.id]: time
  })
})
console.log(final)