Форум программистов, компьютерный форум, киберфорум
Python для начинающих
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.80/25: Рейтинг темы: голосов - 25, средняя оценка - 4.80
2 / 1 / 1
Регистрация: 22.03.2020
Сообщений: 19

Считать файл и вывести число событий NOK за каждую минуту

22.03.2020, 14:04. Показов 5301. Ответов 6

Студворк — интернет-сервис помощи студентам
Здравствуйте.

Помогите пожалуйста разобраться.

Первый раз на форуме пишу, до этого как то справлялся, сейчас уже 2 день сижу над кодом...

Заранее спасибо за помощь

задание:


Имеется файл events.txt вида:
[2018-05-17 01:55:52.665804] NOK
[2018-05-17 01:56:23.665804] OK
[2018-05-17 01:56:55.665804] OK
[2018-05-17 01:57:16.665804] NOK
[2018-05-17 01:57:58.665804] OK
...
Напишите программу, которая считывает файл
и выводит число событий NOK за каждую минуту в другой файл в формате
[2018-05-17 01:57] 1234
[2018-05-17 01:58] 4321
...
Входные параметры: файл для анализа, файл результата
Требования к коду: он должен быть готовым к расширению функциональности. Делать сразу на классах.

После выполнения первого этапа нужно сделать группировку событий
- по часам
- по месяцу
- по году



баги:
при записи не записывает месяцы и годы
не корректно считаем "нок"




Python
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
import zipfile
 
 
class Log_parser():
 
    def __init__(self, file_name):
        self.file_name = file_name  # сам файл
        self.minuts = 37  # скорее всего надо прочитать первую строку и выписать значния
        self.hours = 19  # но это черновик
        self.month = 5  # и по этому пока просто вбил данные из первой строки
        self.years = 18
        self.line_prev = '[2018-05-14 19:37:47.873687] OK'
        self.count_ok = 0  # счётчик ок
        self.count_nok = 0  # счётчик нок
 
    def unzip(self):
        zfile = zipfile.ZipFile(self.file_name, 'r')
        for filename in zfile.namelist():
            zfile.extract(filename)
        self.file_name = filename
 
    def open_read(self):
 
        if self.file_name.endswith('.zip'):  # перестраховка
            self.unzip()
        f = open('file_1.txt', 'w', encoding='utf8')  # этот открываем для записи, через open - для практики
        with open(file_name, 'r', encoding='utf-8') as file:  # только для чтения
            for line in file:  # ищем по строкам
                if a == 1:  # решение если искать в мин, часах и т.д.
                    self._minutes(f, line)
                elif a == 2:
                    self._hours(f, line)
                elif a == 3:
                    self._months(f, line)
                else:
                    self._years(f, line)
        f.close()  # не забыть закрыть файл
 
    def _minutes(self, f, line):
        if int(line[15:17]) != self.minuts:  # вырезаем, переводим в инт и сравниваем
            f.write('{}]  {}\n'.format(self.line_prev[:17], self.count_nok))  # пишем
            self.minuts = int(line[15:17])  # переводим минуты
            self.count_ok = 0   # сбрасываем счётчик
            self.count_nok = 0
            self.line_prev = line  # предыдущую строку превращаем в текущую
        else:
            if line.endswith('NOK\n'):  # если строка заканчивается на нок
                self.count_nok += 1  # счётчик
            else:
                self.count_ok += 1
 
    def _hours(self, f, line):
 
        if int(line[12:14]) != self.hours:
            f.write('{}]  {}\n'.format(self.line_prev[:14], self.count_nok))
            self.hours = int(line[12:14])
            self.count_ok = 0
            self.count_nok = 0
            self.line_prev = line
        else:
            if line.endswith('NOK\n'):
                self.count_nok += 1
            else:
                self.count_ok += 1
 
    def _months(self, f, line):
        if int(line[6:8]) != self.month:
            f.write('{}]  {}\n'.format(self.line_prev[:8], self.count_nok))
            self.month = int(line[6:8])
            self.count_ok = 0
            self.count_nok = 0
            self.line_prev = line
        else:
            if line.endswith('NOK\n'):
                self.count_nok += 1
            else:
                self.count_ok += 1
 
    def _years(self, f, line):
 
        if int(line[3:5]) != self.years:
            f.write('{}]  {}\n'.format(self.line_prev[:5], self.count_nok))
            self.years = int(line[3:5])
            self.count_ok = 0
            self.count_nok = 0
            self.line_prev = line
        else:
            if line.endswith('NOK\n'):
                self.count_nok += 1
            else:
                self.count_ok += 1
 
    def act(self):
        self.open_read()  # вызывает функцию
 
 
file_name = 'events.txt'
a = 3  # 1 = минуты, 2 = часы, 3 = месяцы, 4 = года.
s = Log_parser(file_name='events.txt')
s.act()
Добавлено через 1 час 1 минуту
ошибка в функции def minutes():
но не понимаю что не так
0
Лучшие ответы (1)
Programming
Эксперт
39485 / 9562 / 3019
Регистрация: 12.04.2006
Сообщений: 41,671
Блог
22.03.2020, 14:04
Ответы с готовыми решениями:

Считать число и вывести через пробел каждую цифру отдельно
Задача 1. Простая задача. Решение в 5 строк Программа считывает число и выводит через пробел каждую цифру отдельно Формат...

Считать двузначное число и вывести через пробел каждую цифру отдельно
Программа считывает двузначное число и выводит через пробел каждую цифру отдельно. Подскажите как сделать? Я новичок в с++, желательно с...

Вирус каждую минуту создает новый tmp файл
Добрый день. Вирус создает tmp файлы приблизительно 1 раз в минуту, при этом в момент создания файла процессор загружается на 100%. Прошу...

6
2 / 1 / 1
Регистрация: 22.03.2020
Сообщений: 19
23.03.2020, 11:47  [ТС]
ошибка в записи где то... не знаю как найти

Python
1
2
3
4
5
6
7
8
9
10
11
12
def _minutes(self, f, line):
        if int(line[15:17]) != self.minuts:  # вырезаем, переводим в инт и сравниваем
            f.write('{}]  {}\n'.format(self.line_prev[:17], self.count_nok))  # пишем
            self.minuts = int(line[15:17])  # переводим минуты
            self.count_ok = 0   # сбрасываем счётчик
            self.count_nok = 0
            self.line_prev = line  # предыдущую строку превращаем в текущую
        else:
            if line.endswith('NOK\n'):  # если строка заканчивается на нок
                self.count_nok += 1  # счётчик
            else:
                self.count_ok += 1
0
Модератор
Эксперт Python
 Аватар для Fudthhh
2695 / 1601 / 513
Регистрация: 21.02.2017
Сообщений: 4,210
Записей в блоге: 1
23.03.2020, 17:06
Nexoc_80, не читабельно, такой код в будущем редактировать будет болью.

Парсить такие данные лучше при помощи регулярных выражений, и переводить в секунды.

Python
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
# -*- encoding: utf-8 -*-
import re
 
 
events_txt = """
[2018-05-17 01:55:52.665804] NOK
[2018-05-17 01:56:23.665804] OK
[2018-05-17 01:56:55.665804] OK
[2018-05-17 01:57:16.665804] NOK
[2018-05-17 01:57:58.665804] OK
"""
 
 
pattern = r"\[(\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2}\.\d{6})\] (\w{2,3})"
 
print(re.findall(pattern, events_txt))
 
# [
#     ('2018-05-17 01:55:52.665804', 'NOK'),
#     ('2018-05-17 01:56:23.665804', 'OK'),
#     ('2018-05-17 01:56:55.665804', 'OK'),
#     ('2018-05-17 01:57:16.665804', 'NOK'),
#     ('2018-05-17 01:57:58.665804', 'OK')
# ]
2
2 / 1 / 1
Регистрация: 22.03.2020
Сообщений: 19
23.03.2020, 17:54  [ТС]
Спасибо большое за ответ.
К сожалению я ещё не проходил
re
r'
d
w
findall

очень круто написано в две строчке, то что у меня в 100

смотришь и понимаешь, что надо многому учиться

ещё раз спасибо
0
Модератор
Эксперт Python
 Аватар для Fudthhh
2695 / 1601 / 513
Регистрация: 21.02.2017
Сообщений: 4,210
Записей в блоге: 1
24.03.2020, 08:39
Лучший ответ Сообщение было отмечено Nexoc_80 как решение

Решение

Nexoc_80, часть функций реализовал, дальше по аналогии.
Кликните здесь для просмотра всего текста

Python
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
# -*- encoding: utf-8 -*-
from __future__ import annotations
 
import re
from datetime import datetime
 
 
class Event:
 
    def __init__(self, dt: datetime, rt: str):
        self.dt, self.rt = dt, rt
    
    @classmethod
    def from_string(self, string: str, pattern: str) -> Event:
        match = re.fullmatch(pattern, string)
        self.dt = datetime.strptime(match.group(1), "%Y-%m-%d %H:%M:%S.%f")
        self.rt = match.group(2)
        return Event(self.dt, self.rt)
 
    def __repr__(self)->str:
        return self.__str__()
 
    def __str__(self) -> str:
        return f"Event(datetime={self.dt}, result={self.rt})"
 
 
class LogParser:
 
 
    def __init__(self, fileName: str):
        self.fileName = fileName
        self.events = []
 
    def read(self, pattern: str):
        with open(self.fileName, "rt") as file:
            lines = file.read().split("\n")
        self.events = [Event.from_string(line, pattern) for line in lines if line]
 
 
    @property
    def group_in_minutes(self) -> tuple:
        group_events = [[self.events[0]], ]
        for event in self.events[1:]:
            if (event.dt - group_events[-1][0].dt).seconds < 60:
                group_events[-1].append(event)
            else:
                group_events.append([event])
        return group_events
 
 
lg = LogParser("events.log")
lg.read(r"\[(\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2}\.\d{6})\] (\w{2,3})")
print(lg.events)
print(lg.group_in_minutes)
Вывод:
Кликните здесь для просмотра всего текста

Python
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
"""
[
    Event(datetime=2018-05-17 01:55:52.665804, result=NOK),
    Event(datetime=2018-05-17 01:56:23.665804, result=OK),
    Event(datetime=2018-05-17 01:56:55.665804, result=OK),
    Event(datetime=2018-05-17 01:57:16.665804, result=NOK),
    Event(datetime=2018-05-17 01:57:58.665804, result=OK)
]
 
[
    [
        Event(datetime=2018-05-17 01:55:52.665804, result=NOK),
        Event(datetime=2018-05-17 01:56:23.665804, result=OK)
    ],
    [
        Event(datetime=2018-05-17 01:56:55.665804, result=OK),
        Event(datetime=2018-05-17 01:57:16.665804, result=NOK)
    ],
    [
        Event(datetime=2018-05-17 01:57:58.665804, result=OK)
    ]
]
"""

1
2 / 1 / 1
Регистрация: 22.03.2020
Сообщений: 19
24.03.2020, 11:25  [ТС]
Огромное спасибо !!!
Буду разбираться
0
1 / 1 / 0
Регистрация: 24.06.2019
Сообщений: 5
15.07.2022, 04:45
Python
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
class Logs:
 
    def __init__(self, file_name):
        self.file = None
        self.date = None
        self.lines = None
        self.count_nok = None
        self.file_content = None
        self.file_name_logs = None
        self.file_name = file_name
 
    def open_and_clear_file(self):
        self.file = open(self.file_name, mode='w+')
        self.file_content = self.file.read()
        self.file.write('')
        self.file.close()
 
    def open_and_write_file(self):
        self.file_name = 'out1.txt'
        self.file = open(self.file_name, mode='a')
        self.file_content = f'{self.date} {self.count_nok}\n'
        self.file.write(self.file_content)
        self.file.close()
 
    def file_read(self):
        self.file_name_logs = 'events.txt'
        self.count_nok = 0
        self.date = []
        self.open_file_and_sorted()
 
    def open_file_and_sorted(self):
        with open(self.file_name_logs, 'r', encoding='cp1251') as file:
            file_contents = file.readlines()
            file_contents.sort(key=lambda line: (line.split(' ')[0]), reverse=False)
            self.append_in_list(file_contents)
 
    def append_in_list(self, file_contents):
        for line in file_contents:
            if 'NOK' not in line:
                continue
            elif line[1:17] in self.date:
                self.count_nok += 1
            elif line[1:17] not in self.date:
                self.write_file(line)
 
    def write_file(self, line):
        if self.count_nok > 0:
            self.open_and_write_file()
            self.count_reload()
            self.date[0] = (line[1:17])
        else:
            self.count_reload()
            self.date.append(line[1:17])
 
    def count_reload(self):
        self.count_nok = 0
        self.count_nok += 1
 
    def write_file_close(self):
        self.open_and_write_file()
 
 
logs = Logs(file_name='out1.txt')
logs.open_and_clear_file()
logs.file_read()
logs.write_file_close()
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
inter-admin
Эксперт
29715 / 6470 / 2152
Регистрация: 06.03.2009
Сообщений: 28,500
Блог
15.07.2022, 04:45
Помогаю со студенческими работами здесь

Создайте задание для cron, согласно которому каждую минуту в файл
Создайте задание для cron, согласно которому каждую минуту в файл ~/memory/stat будет добавляться информация о текущем состоянии памяти,...

Заполнить файл, считать и распечатать каждую вторую строку
Нужна помощь новичку в питоне! Есть вот такие два задания: Задать определённую переменную, dannie, заносим любые семь элементов, к...

Вывод каждую минуту
Ребят, помогите. Мне нужно собирать каждую минуту информацию о gc. У меня все инфа обернута в while(true); Как мне сделать, чтобы...

Обновление каждую минуту
Здравствуйте. Мне необходимо реализовать обновление файла каждую минуту. Что я имею ввиду: записи Xn заносятся в двусвязный список, по...

Клик по кнопке каждую минуту
Привет форумчанам) Подскажите как сделать что бы программа кликнула на кнопку через 1 минуту ) Что то вьехать не могу. Понимаю что работа с...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
7
Ответ Создать тему
Новые блоги и статьи
http://iceja.net/ математические сервисы
iceja 20.01.2026
Обновила свой сайт http:/ / iceja. net/ , приделала Fast Fourier Transform экстраполяцию сигналов. Однако предсказывает далеко не каждый сигнал (см ограничения http:/ / iceja. net/ fourier/ docs ). Также. . .
http://iceja.net/ сервер решения полиномов
iceja 18.01.2026
Выкатила http:/ / iceja. net/ сервер решения полиномов (находит действительные корни полиномов методом Штурма). На сайте документация по API, но скажу прямо VPS слабенький и 200 000 полиномов. . .
Расчёт переходных процессов в цепи постоянного тока
igorrr37 16.01.2026
/ * Дана цепь постоянного тока с R, L, C, k(ключ), U, E, J. Программа составляет систему уравнений по 1 и 2 законам Кирхгофа, решает её и находит переходные токи и напряжения на элементах схемы. . . .
Восстановить юзерскрипты Greasemonkey из бэкапа браузера
damix 15.01.2026
Если восстановить из бэкапа профиль Firefox после переустановки винды, то список юзерскриптов в Greasemonkey будет пустым. Но восстановить их можно так. Для этого понадобится консольная утилита. . .
Сукцессия микоризы: основная теория в виде двух уравнений.
anaschu 11.01.2026
https:/ / rutube. ru/ video/ 7a537f578d808e67a3c6fd818a44a5c4/
WordPad для Windows 11
Jel 10.01.2026
WordPad для Windows 11 — это приложение, которое восстанавливает классический текстовый редактор WordPad в операционной системе Windows 11. После того как Microsoft исключила WordPad из. . .
Classic Notepad for Windows 11
Jel 10.01.2026
Old Classic Notepad for Windows 11 Приложение для Windows 11, позволяющее пользователям вернуть классическую версию текстового редактора «Блокнот» из Windows 10. Программа предоставляет более. . .
Почему дизайн решает?
Neotwalker 09.01.2026
В современном мире, где конкуренция за внимание потребителя достигла пика, дизайн становится мощным инструментом для успеха бренда. Это не просто красивый внешний вид продукта или сайта — это. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru