Med hjälp av awk för att skriva ut andra kolumnen och resten av texten från #

Jag har den här typen av rader i mina konfigurationsfiler,

bindsym $mod+F2 exec gnome-terminal #Open terminal bindsym $mod+p exec command /some/path" #Popup Dictionary bindsym $mod+Mod1+l exec --no-startup-id /some/path/command #Dmenu for my books collection bindsym Mod1+Control+b exec rxvt -e nnn #nnn file browser 

Jag vill awk ut den andra kolumnen och saker som är efter #. Jag använder awk som

awk "/bindsym/{print $2}" filename 

Jag är inte säker på hur jag ska få texten efter #.
Den önskade utgången är tangenterna och sedan kommentartexten som

$mod+F2 Open terminal 

Svar

$ awk -v OFS="\t" "/^bindsym/ { key = $2; sub(".*#", ""); print key, $0 }" file $mod+F2 Open terminal $mod+p Popup Dictionary $mod+Mod1+l Dmenu for my books collection Mod1+Control+b nnn file browser 

Detta använder awk för att först extrahera det andra fältet på varje rad börjar med bindsym till variabeln key. Det raderar sedan allt till och med # på raden och skriver ut key och vad som återstår av raden med en flik som avgränsare.

Alternativ utdataformatering:

$ awk "/^bindsym/ { key = $2; sub(".*#", ""); printf("%-20s\t%-20s\n", key, $0) }" file $mod+F2 Open terminal $mod+p Popup Dictionary $mod+Mod1+l Dmenu for my books collection Mod1+Control+b nnn file browser 

Logiken är densamma, men utdata tilldelar 20 tecken för var och en av de två ( vänsterjusterade) fält och placerar en flik däremellan (för gott mått).

Svar

Använd match() funktion för GNU awk för att matcha delen från # till slutet av raden

awk "/bindsym/ && match($0,/#(.+)$/,arr){print $2, arr[1]}" filep 

match() -funktionen fyller i matrisen som tillhandahålls i det tredje argumentet med det matchade mönstret från regex i det andra argumentet .

på alla POSIX awk stöds det tredje argumentet för match() , men några speciella variabler RSTART och RLENGTH som markerar start och längd för den matchade gruppen. Vi använder funktionen substr() på den aktuella raden för att få den matchade strängen

awk "/bindsym/ && match($0,/#(.+)$/){print $2, substr($0,RSTART+1,RLENGTH)}" file 

För att nättrycka utdata , kan du antingen använda printf() -funktionen som i det andra svaret.

Svar

Detta är väldigt enkelt att göra i sed; eftersom dina data inte är riktigt fältorienterade ger Awk inte en enorm fördel här:

sed "s/^[^ ]* //;s/ .*#//" inputfile 

Översättning:

s/^[^ ]* // 

Radera allt till och med det första mellanslagstecknet.

s/ .*#// 

Ta bort allt från det första (återstående) mellanslagstecknet, upp till det sista # tecknet på raden.

Svar

Step1: count=`awk "{print NR}"|sed -n "$p" filename` Step2:for ((i=1;i<=$count;i++)); do awk -v i="$i" "NR==i && $0 ~ /^bindsym/{print $2}" filename; sed -n ""$i"s/.*#//p" filename; done| sed "N;s/\n/ /g" output for ((i=1;i<=$count;i++)); do awk -v i="$i" "NR==i && $0 ~ /^bindsym/{print $2}" filename; sed -n ""$i"s/.*#//p" filename; done| sed "N;s/\n/ /g" $mod+F2 Open terminal $mod+p Popup Dictionary $mod+Mod1+l Dmenu for my books collection Mod1+Control+b nnn file browser 

Kommentarer

  • Jag ' m förutsatt att det kan finnas fler än fyra rader i inmatningsfilen. Det är inte klart vad ditt första steg skulle göra annat än att skriva ut radnumret i terminalen.
  • Korrigera koden
  • Korrigerad koden

Lämna ett svar

Din e-postadress kommer inte publiceras. Obligatoriska fält är märkta *