wat doet getline binnen awk?

Ik heb dit volgende awk script dat het volgende invoerbestand accepteert, input.txt en produceert de onderstaande uitvoer. Kan iemand alsjeblieft de tijd nemen om uit te zoeken hoe dit awk script werkt? Ik “heb er een beetje tijd aan besteed en het slaat nergens op.


Invoer:

$ cat input.txt

FINISHED RSYNCJOBNA 20140502 0021 2182096 2082096 6 5 2014820905820902 10:02:15 2014820905820902 10:56:42 0:54:27 INITIATED RSYNCJOBNA 20140502 0022 3282096 3182096 6 5 2014820905820902 15:31:06 0:06:04 ce eque** 

Uitvoer:

RSYNCJOBNA|0021|20140502|10:02:15|10:56:42|0:54:27|FINISHED RSYNCJOBNA|0022|20140502|15:31:06| |0:06:04|INITIATED 

Commando om de bovenstaande output te krijgen:

awk -v OFS="|" "/FINISHED|INITIATED/ { status = $1; getline; jobname = $1; getline; sequence = $2; date = $1; getline; start = $2; getline; if (status == "FINISHED") { end = $2; getline } else { end = " " } runtime = $1; print jobname, sequence, date, start, end, runtime, status; }" input.txt 

Ik heb begrepen dat /FINISHED|INITIATED/ {} betekent dat de opdrachten binnen de accolades alleen worden uitgevoerd op regels die overeenkomen met FINISHED of INITIATED maar als voor zover ik aan de uitvoer kan zien, lijkt het script te parseren vanuit alle regels. Wat is er aan de hand?

Reacties

  • Wat begrijp je ' niet precies? Niets? In dat geval: Zullen we u de awk-handleiding voorlezen? Anders: wees nauwkeurig. Gegevens worden in variabelen ingelezen en in een andere volgorde uitgevoerd.
  • Ik don ' t weet wat de getline-functie in het bovenstaande commando doet. En ook als we het patroon als dit /FINISHED|INITIATED/ geven, zoekt awk naar de corresponderende regel en voert de bewerking alleen uit op die bepaalde regel. Maar de bewerking werd op alle regels uitgevoerd. Hoe?
  • @HaukeLaging Welke Gegevens worden in variabelen ingelezen en in verschillende volgorde weergegeven betekent de regel?

Answer

De functie getline leest de volgende regel en verplaatst het script ernaar. opeenvolgende getline oproepen gaan naar de volgende regel. Dit is misschien gemakkelijker te begrijpen met een voorbeeld:

$ cat input.txt foo 1 2 $ awk "/foo/{print; getline; print; getline; print}" input.txt foo 1 2 

Zoals zoals je hierboven kunt zien, zal het script de eerste regel verwerken omdat het overeenkomt met foo. Elke aanroep naar getline leest de regel na de huidige, dus de volgende print aanroepen drukken de volgende regels af.

Antwoord

Als u “niet weet wat een awk -functie doet, dan is de gebruikelijke strategie om de man-pagina te bekijken:

getline

Stel $ 0 in vanaf het volgende invoerrecord; stel NF, NR, FNR in, RT

Het opdrachtblok wordt inderdaad slechts twee keer uitgevoerd. De andere regels worden afgehandeld via getline vanuit de block.

Dit kan worden herschreven naar:

/FINISHED|INITIATED/ { status = $1; line_number=0; next; } { line_number++; } line_number==1 { jobname = $1; } line_number==2 { sequence = $2; date = $1; } ... 

Reacties

  • Wat gebeurt er als het volgende record leeg is?
  • @AvinashRaj Noch uw code, noch mijn alternatief kijkt naar de inhoud van de regels (met uitzondering van /FINISHED|INITIATED/ ) De regels worden gewoon afgeteld De gegevens moeten exact worden gerangschikt (vanuit een awk parsi ng perspectief) op de manier die je hebt getoond, anders zal de code breken.

Geef een reactie

Het e-mailadres wordt niet gepubliceerd. Vereiste velden zijn gemarkeerd met *