I have a huge file, and at some point it goes like this:
Bla bla bla
LAST ITERATION: 1780 6 12 0.689655172413793
-8708.81862246834 -8698.33572943212 -2003.09638506407
-9.912281246897692E-003
Bla bla bla
I would like to get all the numbers after "LAST ITERATION:" and put it in a line in a file. I have managed to get the two first lines with this:
awk 'a && NR==n{ print a,b,c,d,$1,$3 } /LAST ITERATION:/{ a=$3; b=$4; c=$5; d=$6; n=NR 1 }' ./$FOLDER/$NAMEDATA >> $NAMEOUTPUT
But I can't seem to find a way to get the last number which is on the 3rd line. Could anyone help me?
Thanks!
CodePudding user response:
If you are using gawk
, where RS
can be more than one character, an easier approach would be to use "LAST ITERATION:"
as the record separator, and print the first 8 fields of the second record, with a space as the output record seperator:
gawk 'BEGIN{RS="LAST ITERATION:";ORS=" "}NR==2{for(n=1;n<=8; n)print$n}'
Demo: https://ideone.com/UzwkdN
CodePudding user response:
You might use getline
Variable to access future lines, I would use GNU AWK
for this task following way, let file.txt
content be
Bla bla bla
LAST ITERATION: 1780 6 12 0.689655172413793
-8708.81862246834 -8698.33572943212 -2003.09638506407
-9.912281246897692E-003
Bla bla bla
then
awk '/LAST ITERATION/{getline x1;getline x2;line=$0 " " x1 " " x2;sub(/LAST ITERATION:[[:space:]] /,"",line);gsub(/[[:space:]] /," ",line);print line}' file.txt
gives output
1780 6 12 0.689655172413793 -8708.81862246834 -8698.33572943212 -2003.09638506407 -9.912281246897692E-003
Explanation: when LAST ITERATION is encountered I save next line to variable x1 and next next line to variable x2, then construct line
from space-sheared current line, next line and next next line, then remove LAST ITERATION: and following whitespaces characters using sub
function and alter multiple whitespace characters to single spaces using gsub
, after doing that I print
said line
. Disclaimer: this solution assumes there are always at least 2 lines after line with LAST ITERATION.
(tested in gawk 4.2.1)
CodePudding user response:
If you are using regular awk
, you can concatenate the 3 lines starting with the line with LAST ITERATION:
to a variable, and split it in the end:
awk 'BEGIN{ORS=" "}/LAST ITERATION:/{n=NR 3}NR<n{s=s$0}END{split(s,a);for(i=3;i<11; i)print(a[i])}'
CodePudding user response:
If I read your question correctly, you say you want to see an entry within a file, followed by two following lines.
Next to that, you seem to want to work with awk
.
My answer is: "Why awk? This can very easily be done using grep
.", as follows:
grep
has three switches to add more lines, next to the matching one:
-A n
: add "n" lines after the match-B n
: add "n" lines before the match-C n
: add "n" lines, combined after and before
So, you can simply use grep -A 2 "match" filename
.
Good luck
CodePudding user response:
For batch you can target lines using findstr:
The below can target single lines, consecutive lines or a list of lines.
@Echo off
REM :: CALL %0 <filepath> <integer|integer list>
Set "File.Name="
If exist "%~f1" (
Set "File.Name=%~f1"
)Else (
1>&2 Echo(File Not Found
Exit /B 1
)
If "%~2" == "" (
1>&2 Echo(Missing Arg/s for target Line/s.
Exit /B 2
)
Set Target.Lines=%*
Set "Target.Lines=%Target.Lines:"=%"
For /f "Delims=" %%G in ('CMD /V:ON /C "Echo(!Target.Lines:%~1 =!"')Do Set "Target.Lines=%%G"
Set "Line.Count=0"
Set "Highest.Target=0"
Setlocal EnableExtensions EnableDelayedExpansion
For %%G in (%Target.Lines%)Do if !Highest.Target! LSS %%G Set "Highest.Target=%%G"
Endlocal & Set "Highest.Target=%Highest.Target%"
For /f "Tokens=1* Delims=:" %%G in ('%SystemRoot%\System32\findstr.exe /VNLC:"{false.string[%~n0]}" "%File.Name%"')Do (
Set "Line.Count=%%G"
For %%i in (%Target.Lines%)Do if %%G EQU %%i Echo(%%H
)
If %Line.Count% LSS %Highest.Target% (
1>&2 Echo(Lines missing. Lines in file: %Line.Count%. Highest Target: %Highest.Target%
)
CodePudding user response:
awk '
gsub(/LAST ITERATION:/,""){
gsub(/^ */,"");
o=sprintf("%s ",$0);
while(getline && $1 ~ /^[-]?[0-9] (\.[0-9]*)?/) {
o=o sprintf("%s ", $0)
}
print gensub(/ */," ", "g", o) > "output_file"
}
' input_file
$ cat output_file
1780 6 12 0.689655172413793 -8708.81862246834 -8698.33572943212 -2003.09638506407 -9.912281246897692E-003