У меня есть файл журнала, который я преобразовываю в pandas df. Мне нужно найти конкретные строки журнала из df и рассчитать время между этими линиями, следовательно, разделить весь журнал на несколько этапов.
Df пример:
log_level timestamp message
INFO 2019-10-31 12:00 A
INFO 2019-10-31 12:02 b
INFO 2019-10-31 12:00 c
INFO 2019-10-31 12:04 d
INFO 2019-10-31 12:00 e
INFO 2019-10-31 12:06 f
INFO 2019-10-31 12:00 g
INFO 2019-10-31 12:08 h
INFO 2019-10-31 12:10 i
INFO 2019-10-31 12:12 j
INFO 2019-10-31 12:14 k
INFO 2019-10-31 12:16 l
INFO 2019-10-31 12:18 m
INFO 2019-10-31 12:18 n
msg_list = ['a', 'd','g','n', 'k']
Здесь «a» - «d» становится фазой, «d» - «g» другой и так далее до конца журнала. У меня есть около 40000 строк журнала, которые мне нужно разделить.
Каков наилучший и наиболее оптимизированный способ сделать это, поскольку мне нужно проанализировать около 400 нечетных журналов.
Я использую str.contains для поиска начального и конечного индексов и получениявремя между ними, но я чувствую, что оно недостаточно эффективно, потому что каждый раз просматривает Dataframe сверху вниз, чтобы найти строки.
Можно ли просматривать кадр данных только один раз, скажем, если я найду сообщение 'a', тогда я ищу следующее сообщение 'd' и в следующий раз перехожу от 'd' к следующему сообщению 'g',с каким-то своего рода позиционным индексом?
Часть моего кода:
@property
def start_idx(self):
if self._start_idx is None:
self._start_idx = self.main_df.index[self.main_df['message'].str.contains(self.start_message)][0]
print(self._start_idx)
return self._start_idx
@property
def end_idx(self):
if self._end_idx is None:
self._end_idx = self.main_df.index[self.main_df['message'].str.contains(self.end_message)][0]
print(self._end_idx)
return self._end_idx
@property
def start_time(self):
if self._start_time is None:
self._start_time = self.phase_df.loc[self.start_idx, 'timestamp']
return self._start_time
@property
def end_time(self):
if self._end_time is None:
self._end_time = self.phase_df.loc[self.end_idx, 'timestamp']
return self._end_time
@property
def phase_df(self):
if self._phase_df is None:
self._phase_df = self.main_df.iloc[self.start_idx: self.end_idx]
return self._phase_df
@property
def phase_time(self):
if self._phase_time is None:
self._phase_time = (self.end_time - self.start_time) / np.timedelta64(1, 's')
return int(self._phase_time)
Я вызывал эту часть кода несколько раз для разных начальных и конечных сообщений, которые я нахожу.
Ожидаемый вывод (в отдельном df):
File Phase1 Phase2 .... Phase N
Log1 120 120 120 (Time in seconds/minutes)