Форум программистов, компьютерный форум, киберфорум
Наши страницы

Batch (CMD/BAT)

Войти
Регистрация
Восстановить пароль
 
Рейтинг: Рейтинг темы: голосов - 11, средняя оценка - 4.82
surer
0 / 0 / 0
Регистрация: 08.10.2012
Сообщений: 13
#1

Парсер лога - CMD/BAT

08.10.2012, 10:33. Просмотров 1542. Ответов 14
Метки нет (Все метки)

Доброе утро!

Подскажите, пожалуйста, как можно с помощью CMD распарсить лог вида:
Bash
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
TN   008 0 00 01 
TYPE 3905
CDEN 8D
CTYP XDLC
CUST 0 
MRT  
ERL  0 
FDN  
TGAR 0 
LDN  NO
NCOS 1 
SGRP 0 
RNPG 0 
SCI  0 
SSU  
LNRS 16 
XLST 2 
SFLT NO
CAC_CIS 3 
CAC_MFC 0
Командой findstr(findstr /b /g:stroki.txt original.log >parsed.txt) нахожу строки, начинающиеся с необходимых мне.
Получается что-то вида (строки повторяются, так как они содержатся в каждом блоке, а их больше 1000):
Bash
1
2
3
4
5
6
7
8
9
10
11
12
CTYP XDLC
NCOS 1 
SGRP 0 
RNPG 0
CTYP XDLC
NCOS 2 
SGRP 0 
RNPG 1
CTYP XDLC
NCOS 3 
SGRP 0 
RNPG 0
Так вот задача в том, чтоб на выходе получились только значения (разделитель точка с запятой, запятая или табуляция, не суть), причем 1 блок = 1 строка.
Для данного примера должно быть так:
Bash
1
2
3
XDLC;1;0;0
XDLC;2;0;1
XDLC;3;0;0
В чем сложность? В том, что в некоторых блоках значения пустые или такой строки вообще нет. Тогда должно быть что-то вроде:
Bash
1
2
3
XDLC;1;;0
XDLC;2;0;1
XDLC;3;0;0
для того, чтобы не терялся столбец в том же Excel

Заранее благодарен за помощь
0
Лучшие ответы (1)
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
08.10.2012, 10:33
Здравствуйте! Я подобрал для вас темы с ответами на вопрос Парсер лога (CMD/BAT):

Ведение лога bat - CMD/BAT
Вообщем существует огромное количество директорий с разными структурированными путями к директориям, программа BAT опрашивает эти пути...

PSexec, запись лога с условием - CMD/BAT
Всем привет , есть такая внештатная ситуация Нужно проверить на подсети ip адресов ,будет-ли работать psexec , собственно проверкой...

Проверка наличия каталогов и ведение лога - CMD/BAT
При помощи цикла For написать командный файл, который: после запуска перебирает содержимое каталога i:\temp у каждого файла в...

Убрать скобки при парсинге лога - CMD/BAT
Возникла необходимость написать очередной парсер :) Есть файл-лог (например, card.log), в нём пишутся записи вида - , т.е. в квадратных...

Батник для разбора лога (фильтрации текста) - CMD/BAT
Здравствуйте, форумчане! Я - новичек и на форуме и в программировании тоже, поэтому просьба не кидаться помидорами и иже с ними......

Создание лога только в случае существования директории - CMD/BAT
Здравствуйте не подправите код он создает файл log.txt в любом случаи если папка нет ее , а мне надо чтобы если есть папка то писался...

14
Somebody
2792 / 1603 / 148
Регистрация: 03.12.2007
Сообщений: 4,200
Завершенные тесты: 3
08.10.2012, 14:19 #2
Лучший ответ Сообщение было отмечено автором темы, экспертом или модератором как ответ
CTYP или какое-то первое значение всегда есть? Или как определять, где следующий блок? В общем типа такого:
Код
setlocal enableextensions enabledelayedexpansion

set nKeys=4
set keyNames[0]=CTYP
set keyNames[1]=NCOS
set keyNames[2]=SGRP
set keyNames[3]=RNPG
set input=in.txt
set output=out.txt

set /a lastKeyIndex=nKeys-1

del %output%
call :EraseKeys
for /f "tokens=1,*" %%a in (%input%) do (
  set aa=%%a
  if %%a==%keyNames[0]% if not x!key%keyNames[0]%!==x (
    call :Flush
	call :EraseKeys
  )
  set key%%a=%%b
)
call :Flush
endlocal
exit /b

:EraseKeys
for /l %%i in (1, 1, %lastKeyIndex%) do set key!keyNames[%%i]!=
exit /b

:Flush
for /f %%t in ("key!KeyNames[0]!") do set str=!%%t!
for /l %%i in (1, 1, %lastKeyIndex%) do (
  for /f %%t in ("key!KeyNames[%%i]!") do set str=!str!;!%%t!
)
echo %str% >>%output%
exit /b
0
surer
0 / 0 / 0
Регистрация: 08.10.2012
Сообщений: 13
08.10.2012, 15:30  [ТС] #3
Да, первое значение постоянно и является началом следующего блока.
Вот что получилось:
Bash
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
D:\sur\333>setlocal enableextensions enabledelayedexpansion
 
D:\sur\333>set nKeys=7
 
D:\sur\333>set keyNames[0]=TN
 
D:\sur\333>set keyNames[1]=TYPE
 
D:\sur\333>set keyNames[2]=AST
 
D:\sur\333>set keyNames[3]=IAPG
 
D:\sur\333>set keyNames[4]=KEY  00
 
D:\sur\333>set keyNames[5]=     01
 
D:\sur\333>set keyNames[6]=     02
 
D:\sur\333>set input=putty_full.log
 
D:\sur\333>set output=out.txt
 
D:\sur\333>set /a lastKeyIndex=nKeys-1
 
D:\sur\333>del out.txt
Не удается найти D:\sur\333\out.txt
 
D:\sur\333>call :EraseKeys
 
D:\sur\333>for /L %i in (1 1 6) do set key!keyNames[%i]!=
 
D:\sur\333>set key!keyNames[1]!=
 
D:\sur\333>set key!keyNames[2]!=
 
D:\sur\333>set key!keyNames[3]!=
 
D:\sur\333>set key!keyNames[4]!=
 
D:\sur\333>set key!keyNames[5]!=
 
D:\sur\333>set key!keyNames[6]!=
 
D:\sur\333>exit /b
Непредвиденное появление: !==x.
 
D:\sur\333>  if %a==TN    if not x!keyTN   !==x (
0
Dragokas
Эксперт WindowsАвтор FAQ
16242 / 6941 / 834
Регистрация: 25.12.2011
Сообщений: 10,722
Записей в блоге: 16
08.10.2012, 16:44 #4
Bash
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
@echo off
setlocal EnableDelayedExpansion
::Имя исходного файла
set orig=original.log
::Имя файла с подстановочными словами
set maskfile=stroki.txt
::Имя результирующего файла со значениями
set result=result.log
::Количество значений на строку
set /a nmax=4
 
if exist %result% del /f /q %result%
 
for /f "tokens=1-2*" %%a in ('findstr /b /g:%maskfile% %orig%') do (
  set /a n+=1
  set stri=!stri!%%b;
  if !n!==%nmax% (
    echo !stri:~0,-1!>>%result%
    set /a n=0
    (set stri=) 
  )
)
if n NEQ 0 echo !stri:~0,-1!>>%result%
pause>nul
1
surer
0 / 0 / 0
Регистрация: 08.10.2012
Сообщений: 13
08.10.2012, 18:10  [ТС] #5
Работает! Но не так, как хотелось бы.
Слишком много режет.
Bash
1
2
3
4
5
008;3905;00;1
00;SCR;NRD;008
3905;00;1;00
SCR;NRD;008;3905
00;1;00;SCR
Это пример из результата, а должно быть примерно так:
Bash
1
2
3
008 0 00 00 ;3905;00 01 ;1; ACD 2780261 2  36265; SCR 2780265 2     MARP; NRD 
008 0 00 01 ;3905;00 01 ;1; ACD 2780261 2  36267; SCR 2780267 2     MARP; NRD 
008 0 00 02 ;3905;00 01 ;1; ACD 2780261 2  36268; SCR 2780268 2     MARP; NRD
Отсюда вывод: режет до первого пробела. Нужно 7 значений, но где-то их всего 5 или 6, поэтому, если задавать четко 7 значений на строку, то результат уедет, после первого пустого значения.

Поправка: выставил 7 значений, вроде, выставляет пустые, но все же остается проблема, что режет после первого пробела
0
Somebody
2792 / 1603 / 148
Регистрация: 03.12.2007
Сообщений: 4,200
Завершенные тесты: 3
08.10.2012, 18:26 #6
Цитата Сообщение от surer Посмотреть сообщение
Bash
1
2
Непредвиденное появление: !==x.
D:\sur\333>  if %a==TN    if not x!keyTN   !==x (
Видимо, в конце строки set keyNames[0]=TN три пробела, которые тоже попадают в переменную.
Цитата Сообщение от surer Посмотреть сообщение
режет до первого пробела
"tokens=1*"
0
Dragokas
Эксперт WindowsАвтор FAQ
16242 / 6941 / 834
Регистрация: 25.12.2011
Сообщений: 10,722
Записей в блоге: 16
08.10.2012, 21:38 #7
Сделайте аналогично в моей строке № 14.
"tokens=1-2*" поменяйте на "tokens=1*"
0
surer
0 / 0 / 0
Регистрация: 08.10.2012
Сообщений: 13
08.10.2012, 23:02  [ТС] #8
Цитата Сообщение от Dragokas Посмотреть сообщение
Сделайте аналогично в моей строке № 14.
"tokens=1-2*" поменяйте на "tokens=1*"
Спасибо, помогло. Только вот дальше данные поплыли.
Ситуация такая:
Bash
1
2
3
4
5
6
7
8
9
10
11
DES  SOVINT
TN   008 0 07 00 
TYPE RAN 
CUST 0 
XTRK EXUT
TIMP 600 
BIMP 600 
AUTO_BIMP NO
RTMB 49 1 
CONN 14 
DATE NO DATE
Это в исходнике, то есть в этом блоке всего 2 необходимых строки TN и TYPE. Дальше таких еще десяток блоков. То есть в резалте должно быть следующее:
008 0 07 00;RAN;;;;;
И далее:
Bash
1
2
3
4
5
6
008 0 07 01;MUS;;;;;
008 0 07 02;MUS;;;;;
008 0 07 03;MUS;;;;;
008 0 07 04;MUS;;;;;
008 0 07 05;RAN;;;;;
...
А у меня вышло вот так:
Bash
1
2
3
4
5
008 0 07 00 ;RAN ;008 0 07 01 ;MUS ;008 0 07 02 ;MUS ;008 0 07 03 
MUS ;008 0 07 04 ;MUS ;008 0 07 05 ;RAN ;008 0 07 06 ;MUS 
008 0 07 07 ;MUS ;012 0 00 00 ;MUS ;012 0 00 01 ;MUS ;012 0 00 02 
RAN ;012 0 00 03 ;RAN ;012 0 00 04 ;RAN ;012 0 00 05 ;RAN 
012 0 00 06 ;RAN ;012 0 00 07 ;RAN ;012 0 01 00 ;3905;00 01
Печаль.
0
Dragokas
Эксперт WindowsАвтор FAQ
16242 / 6941 / 834
Регистрация: 25.12.2011
Сообщений: 10,722
Записей в блоге: 16
09.10.2012, 00:27 #9
Так если в строке № 10 выставить число 2, приблизительно такое, как Вы написали, и получится.

Если "всего 2 необходимых строки TN и TYPE", то откуда в планируемом результате взялись пустые значения ;;;;; в кол-ве 5 шт. (почему именно 5) ?
Прикрепите все же сюда полный файл-исходник, а то как-то неясно.
0
surer
0 / 0 / 0
Регистрация: 08.10.2012
Сообщений: 13
09.10.2012, 09:10  [ТС] #10
В строке должно быть 7 столбцов: TN, TYPE, AST, IAPG, KEY 00, KEY 01, KEY 02. Пустые значения должны подставляться, чтоб не было смещения по столбцам. Сейчас они подставляются только в том случае, если есть строка без параметра, а надо даже при отсутствии самой строки, иначе видим смещение.

Полный лог прикрепил.
0
Вложения
Тип файла: rar putty_full.rar (20.2 Кб, 4 просмотров)
surer
0 / 0 / 0
Регистрация: 08.10.2012
Сообщений: 13
10.10.2012, 11:35  [ТС] #11
UP
Так близко к решению... Есть идеи?

Печаль
0
Dragokas
Эксперт WindowsАвтор FAQ
16242 / 6941 / 834
Регистрация: 25.12.2011
Сообщений: 10,722
Записей в блоге: 16
16.10.2012, 02:44 #12
surer, а в чем проблема? - первый вариант скрипта Somebody замечательно отрабатывает на файле putty.
Bash
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
@echo off
setlocal enableextensions enabledelayedexpansion
 
set nKeys=7
set keyNames[0]=TN
set keyNames[1]=TYPE
set keyNames[2]=AST
set keyNames[3]=IAPG
set keyNames[4]=AAA
set keyNames[5]=BBB
set keyNames[6]=CCC
set input=in.txt
set output=out.txt
 
set /a lastKeyIndex=nKeys-1
 
del %output%
call :EraseKeys
for /f "tokens=1,*" %%a in (%input%) do (
  set aa=%%a
  if %%a==%keyNames[0]% if not x!key%keyNames[0]%!==x (
    call :Flush
    call :EraseKeys
  )
  set key%%a=%%b
)
call :Flush
pause
goto :eof
 
:EraseKeys
for /l %%i in (1, 1, %lastKeyIndex%) do set key!keyNames[%%i]!=
exit /b
 
:Flush
for /f %%t in ("key!KeyNames[0]!") do set str=!%%t!
for /l %%i in (1, 1, %lastKeyIndex%) do (
  for /f %%t in ("key!KeyNames[%%i]!") do set str=!str!;!%%t!
)
echo %str% >>%output%
exit /b
0
Вложения
Тип файла: rar out.rar (2.2 Кб, 6 просмотров)
surer
0 / 0 / 0
Регистрация: 08.10.2012
Сообщений: 13
16.10.2012, 10:33  [ТС] #13
Последние 3 ключа не цепляются. В них есть пробелы.
0
Dragokas
Эксперт WindowsАвтор FAQ
16242 / 6941 / 834
Регистрация: 25.12.2011
Сообщений: 10,722
Записей в блоге: 16
16.10.2012, 10:39 #14
Да, не будут цепляться. И вряд ли легко получится сделать.
Есть вариант сделать сначала предобработку списка (например, заменить ключи с пробелами - пробелы на знак подчеркивания (сейчас можете даже поэкспериментировать с простым блокнотом). Повторить выполнение скрипта, указав ключи KEY_00, KEY_01, KEY_02.

Алгоритм работы моего из 4-го поста совсем неверный, поэтому здесь он будет бесполезен.
1
surer
0 / 0 / 0
Регистрация: 08.10.2012
Сообщений: 13
16.10.2012, 10:42  [ТС] #15
Ну как вариант, кстати! Только вот в блокноте замена может занять годы
Тот же WordPad быстрее. Спасибо за совет!
0
16.10.2012, 10:42
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
16.10.2012, 10:42
Привет! Вот еще темы с ответами:

Можно ли к определённому тексту из лога батника привязать задачу? - CMD/BAT
Может не совсем правильно описал, но вопрос следующий. Допустим надо отправить файл почтой. Если не получилось то в окне cmd появляется...

Определение буквы диска по его номеру из лога, создаваемого DiskPart - CMD/BAT
Лог diskpart: Microsoft DiskPart version 6.1.7601 Copyright (C) 1999-2008 Microsoft Corporation. On computer: HP-ENG-03 Disk...

Выборка файлов по расширению, упаковка, отправка адресатам, ведение лога, резервное копирование - CMD/BAT
Всем привет Сделал следующий батник Он ищет в папке файлы aaa0000bbb*.CNG, архивирует их в aaa0000bbb*.zip, отправляет адресату, ведёт...

Создание лога копирования файлов: что, куда и сколько времени на это ушло - CMD/BAT
Привет ВСЕМ может кто знает есть ли возможность при копировании вести лог не только откуда ведется копирование но и куда плюс время...


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

Или воспользуйтесь поиском по форуму:
15
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2018, vBulletin Solutions, Inc.
Рейтинг@Mail.ru