Solved Batch File to extract certain lines begining with numbers

December 29, 2013 at 21:29:36
Specs: Windows 7
Hello, here I am with another batch challenge. I have a text file which has formatting as shown below

*Include
110_abbcasassasas.txt
*Include
120_aaacasassasac.txt
*Include
250_ababasasssasa.txt
*Include
110_abbcdffdfdffdfdf.txt
*Include
200_accbererererere.txt
*Include
350_addawswswsws.txt
*Include
320_addawswswsws.txt


I need to extract the lines which starts with a specific 3digit number like 110 , 250, etc etc with *Include as title . as shown below

*Include
110_abbcasassasas.txt
*Include
250_ababasasssasa.txt

Also I need to add *SCRIPT START in the begining of the Output text and *SCRIPT END in the END of the Output text

*SCRIPT START
*Include
110_abbcasassasas.txt
*Include
250_ababasasssasa.txt
*SCRIPT END



See More: Batch File to extract certain lines begining with numbers

Report •

✔ Best Answer
January 6, 2014 at 13:20:21
Here's another version that does not need findstr (which your version doesn't really use to best advantage anyway):

@echo off & setlocal enabledelayedexpansion
::here is the list of numbers you want to find
set list= 100_ 120_ 160_ 170_ 178_ 180_ 190_ 340_ 810_ 175_
(echo *Script_start
for /f "tokens=1* delims=_" %%a in (%1) do (
set test=!list: %%a_=!
if "!test!" neq "%list%" (
echo *include
echo %%a_%%b
)
)
echo *Script_end
)>%~dp1pr.txt
::===== end script

note that pr.txt goes to the same directory as the source file. You could put it elsewhere
by replacing "%~dp1" with some other path.



#1
December 30, 2013 at 21:00:20
I guess my only question is where you want the selected numbers to come from: commandline, textfile, or prompted input. This batch might handle #2 and #3, but easily modified to handle #1:

::==== begin batch ROHAN.BAT
@echo off>rohan.x & setlocal
if "%1"=="" goto :eof
:1
set x=
set /p x=next number:
if not defined x goto :execute
>> rohan.x echo %x%_
goto :1
:execute
(echo *SCRIPT_START
for /f "tokens=1" %%a in ('findstr /L /B /G:rohan.x %1') do (
echo *Include
echo %%a
)
echo *SCRIPT_END
)>%~dpn1.out

::===== END BATCHSCRIPT

if you want a feed-file: ROHAN<FEED
which would fill the prompts. If you want commandline, just "shift" until "%1"=="" then exit.

message edited by nbrane


Report •

#2
December 30, 2013 at 23:24:47
Thanks for the support. Actually I want to drag drop a text file to my .BAT file which will give me an output file with the specific format. My input file will be in a format like shown below

*SCRIPT_START
asdfdsfksjdfsjkfshkfsfdsf
132432131231321321321213
asd21a3d1as23d1a3sd1as321d
132123s1das32d3as21d3as2das3d3a2
*include
100_TEST_File_version_001.key
*include
120_TEST_File_version_001.key
*include
160_TEST_File_version_003.key
*include
170_TEST_File_version_007.key
*include
178_TEST_File_version_002.key
*include
180_TEST_File_version_005.key
*include
280_TEST_File_version_006.key
*include
562_TEST_File_version_001.key
*include
565_TEST_File_version_001.key
*include
567_TEST_File_version_001.key
asdfdsfksjdfsjkfshkfsfdsf
132432131231321321321213
asd21a3d1as23d1a3sd1as321d
132123s1das32d3as21d3as2das3d3a2
*SCRIPT_END

There are unwanted data's inside , I need to get out format like shown below

*SCRIPT_START
*include
180_TEST_File_version_005.key
*include
280_TEST_File_version_006.key
*include
562_TEST_File_version_001.key
*SCRIPT_END

I am looking for a function/condition which will check first 3 numeric digit followed by underscore "_" and print that entire LINE to a new file. with *include as Headding.
Everytime , this 3 Digits and underscore will be fixed like 180_, 280_ in any inputfile I drag & drop.


Report •

#3
December 31, 2013 at 11:02:53
Here you go:

@echo off
set /p outname="Output File Name: "
echo *SCRIPT_START >> %outname%
:readLine
for /f "tokens=*" %%x in (%1) do call :process %%x
echo *SCRIPT_END >> %outname%
goto :eof
:process
set ln=%*
set str=%*
set str=%str:~0,4%
echo %str%| findstr /r "^[1-9][0-9]*_">nul
if %errorlevel%==0 goto :new ln
goto :eof
:new
echo *Include >> %outname%
echo %1 >> %outname%
goto :eof

Drag and drop, but you have to specify output filename :)


Report •

Related Solutions

#4
January 1, 2014 at 15:20:12
@thephantom: Good job, but I wonder why you stopped at two digits?:
echo %str%| findstr /r "^[1-9][0-9]*_">nul

since this leaves the door open for possibility of two-digit number. You went two-thirds of the way to the goal-line then dropped the ball with that asterisk!:
echo %str%| findstr /r "^[1-9][0-9][0-9]_">nul

Also, the OP didn't specify whether leading zeros-numbers count as "3-digit" or not:
001 etc.

I just used findstr to extract, but your's works just as well with the aforementioned qualification. I hardwired the output and placed it into the same directory and went with the leading-zeros possibility, which might be wrong. OP would have to clear that one up.

@echo off & setlocal
(echo *SCRIPT_START
for /f "tokens=*" %%a in ('findstr /r /B "[0-9][0-9][0-9]_"^<%1') do (
echo *Include
echo %%a
)
ECHO *SCRIPT_END)>%~dpn1.out


Report •

#5
January 2, 2014 at 01:47:14
@nbrane Yeah, I did that for a reason.

If the number starts with an 0, like 0123, It would still be counted as a 3-digit number :) But the possibility of a 2-digit number followed by an underscore won't be high...


Report •

#6
January 2, 2014 at 02:25:03
Thanks you !. This is working Good. It is printing all the Numbers. Is it possible to specify a set of numbers?? Example --> Input file may contain 3 digit numbers starting from 000 to 999 ,

*SCRIPT_START
*Include
100_rr.key
*Include
220_gi.key
*Include
550_aj.key
*Include
200_ir.key
*Include
600_rr.key
*Include
120_gi.key
*Include
150_aj.key
*Include
400_ir.key
*SCRIPT_END

and if i specify a list of numbers ( 100,120,350 & 400) , it should give those specific lines as shown below

*SCRIPT_START
*Include
100_rr.key
*Include
120_gi.key
*Include
350_aj.key
*Include
400_ir.key
*SCRIPT_END


Report •

#7
January 2, 2014 at 18:17:49
@phantom: good point. I figured you must have had a reason for your r/e construct. I'll leave it to my betters whether leading zeros constitute a "digit": mathematically not, but logically and syntactically it depends on the specific application...

@OP: see resp #1, adjusted for "drag-drop".


Report •

#8
January 3, 2014 at 04:03:25
As ever, a good solution starts with a good statement of requirement.

I avoid externals, like findstr, when I can.

[R2 will probably fire me up for bad indenting; but here goes.]


::======  script starts here  ===============
:: chk first 3 chars of each line for NUM & 4th for _
:: rohang2.bat  2014-01-03 15:23:54.82
@echo off > NEWFILE & setLocal enableDELAYedeXpansioN

> NEWFILE echo.*SCRIPT START 

:main
for /f "tokens=* delims= " %%a in (myfile) do (
set L=%%a
  set A=!L:~0,1!
  set B=!L:~1,1!
  set C=!L:~2,1!
  set D=!L:~3,1!
if !D! equ _ (
    for %%i in (A B C) do (
      for /L %%N in (0 1 9) do (
      if !%%i! equ %%N set %%i=#
    ))
if !A! equ # if !B! equ # if !C! equ # (
  echo.*Include
  echo.!L!
)
)
) >> NEWFILE
>> NEWFILE echo.*SCRIPT END
::======  script ends here  =================

=====================
M2 Golden-Triangle


Report •

#9
January 6, 2014 at 10:15:59
I have done some modification in the script and it is giving the required output for me , but the only problem is that , now it is a lot of TIME . This is the Modified version , can this be done in a simpler way ??

@echo off >RR.txt & setlocal
>> RR.txt echo *SCRIPT_START
:readLine
for /f "tokens=*" %%x in (%1) do call :process %%x
>> RR.txt echo *SCRIPT_END
goto :eof
:process
set ln=%*
set str=%*
set str=%str:~0,4%
echo %str%| findstr /r "^[1][0][0]_">nul
if %errorlevel%==0 goto :new ln
echo %str%| findstr /r "^[1][2][0]_">nul
if %errorlevel%==0 goto :new ln
echo %str%| findstr /r "^[1][6][0]_">nul
if %errorlevel%==0 goto :new ln
echo %str%| findstr /r "^[1][7][0]_">nul
if %errorlevel%==0 goto :new ln
echo %str%| findstr /r "^[1][7][8]_">nul
if %errorlevel%==0 goto :new ln
echo %str%| findstr /r "^[1][8][0]_">nul
if %errorlevel%==0 goto :new ln
echo %str%| findstr /r "^[1][9][0]_">nul
if %errorlevel%==0 goto :new ln
echo %str%| findstr /r "^[3][4][0]_">nul
if %errorlevel%==0 goto :new ln
echo %str%| findstr /r "^[8][1][0]_">nul
if %errorlevel%==0 goto :new ln
echo %str%| findstr /r "^[1][7][5]_">nul
goto :eof
:new
>> RR.txt echo *include
>> RR.txt echo %1
goto :eof


Report •

#10
January 6, 2014 at 13:20:21
✔ Best Answer
Here's another version that does not need findstr (which your version doesn't really use to best advantage anyway):

@echo off & setlocal enabledelayedexpansion
::here is the list of numbers you want to find
set list= 100_ 120_ 160_ 170_ 178_ 180_ 190_ 340_ 810_ 175_
(echo *Script_start
for /f "tokens=1* delims=_" %%a in (%1) do (
set test=!list: %%a_=!
if "!test!" neq "%list%" (
echo *include
echo %%a_%%b
)
)
echo *Script_end
)>%~dp1pr.txt
::===== end script

note that pr.txt goes to the same directory as the source file. You could put it elsewhere
by replacing "%~dp1" with some other path.


Report •

Ask Question